x86: 64-bit, add the new split_large_page() function
[wrt350n-kernel.git] / net / ipv6 / ndisc.c
blob0d33a7d32125b80f102d28e851202c16d2f14fed
1 /*
2 * Neighbour Discovery for IPv6
3 * Linux INET6 implementation
5 * Authors:
6 * Pedro Roque <roque@di.fc.ul.pt>
7 * Mike Shaver <shaver@ingenia.com>
9 * This program is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU General Public License
11 * as published by the Free Software Foundation; either version
12 * 2 of the License, or (at your option) any later version.
16 * Changes:
18 * Pierre Ynard : export userland ND options
19 * through netlink (RDNSS support)
20 * Lars Fenneberg : fixed MTU setting on receipt
21 * of an RA.
22 * Janos Farkas : kmalloc failure checks
23 * Alexey Kuznetsov : state machine reworked
24 * and moved to net/core.
25 * Pekka Savola : RFC2461 validation
26 * YOSHIFUJI Hideaki @USAGI : Verify ND options properly
29 /* Set to 3 to get tracing... */
30 #define ND_DEBUG 1
32 #define ND_PRINTK(fmt, args...) do { if (net_ratelimit()) { printk(fmt, ## args); } } while(0)
33 #define ND_NOPRINTK(x...) do { ; } while(0)
34 #define ND_PRINTK0 ND_PRINTK
35 #define ND_PRINTK1 ND_NOPRINTK
36 #define ND_PRINTK2 ND_NOPRINTK
37 #define ND_PRINTK3 ND_NOPRINTK
38 #if ND_DEBUG >= 1
39 #undef ND_PRINTK1
40 #define ND_PRINTK1 ND_PRINTK
41 #endif
42 #if ND_DEBUG >= 2
43 #undef ND_PRINTK2
44 #define ND_PRINTK2 ND_PRINTK
45 #endif
46 #if ND_DEBUG >= 3
47 #undef ND_PRINTK3
48 #define ND_PRINTK3 ND_PRINTK
49 #endif
51 #include <linux/module.h>
52 #include <linux/errno.h>
53 #include <linux/types.h>
54 #include <linux/socket.h>
55 #include <linux/sockios.h>
56 #include <linux/sched.h>
57 #include <linux/net.h>
58 #include <linux/in6.h>
59 #include <linux/route.h>
60 #include <linux/init.h>
61 #include <linux/rcupdate.h>
62 #ifdef CONFIG_SYSCTL
63 #include <linux/sysctl.h>
64 #endif
66 #include <linux/if_addr.h>
67 #include <linux/if_arp.h>
68 #include <linux/ipv6.h>
69 #include <linux/icmpv6.h>
70 #include <linux/jhash.h>
72 #include <net/sock.h>
73 #include <net/snmp.h>
75 #include <net/ipv6.h>
76 #include <net/protocol.h>
77 #include <net/ndisc.h>
78 #include <net/ip6_route.h>
79 #include <net/addrconf.h>
80 #include <net/icmp.h>
82 #include <net/netlink.h>
83 #include <linux/rtnetlink.h>
85 #include <net/flow.h>
86 #include <net/ip6_checksum.h>
87 #include <linux/proc_fs.h>
89 #include <linux/netfilter.h>
90 #include <linux/netfilter_ipv6.h>
92 static struct socket *ndisc_socket;
94 static u32 ndisc_hash(const void *pkey, const struct net_device *dev);
95 static int ndisc_constructor(struct neighbour *neigh);
96 static void ndisc_solicit(struct neighbour *neigh, struct sk_buff *skb);
97 static void ndisc_error_report(struct neighbour *neigh, struct sk_buff *skb);
98 static int pndisc_constructor(struct pneigh_entry *n);
99 static void pndisc_destructor(struct pneigh_entry *n);
100 static void pndisc_redo(struct sk_buff *skb);
102 static struct neigh_ops ndisc_generic_ops = {
103 .family = AF_INET6,
104 .solicit = ndisc_solicit,
105 .error_report = ndisc_error_report,
106 .output = neigh_resolve_output,
107 .connected_output = neigh_connected_output,
108 .hh_output = dev_queue_xmit,
109 .queue_xmit = dev_queue_xmit,
112 static struct neigh_ops ndisc_hh_ops = {
113 .family = AF_INET6,
114 .solicit = ndisc_solicit,
115 .error_report = ndisc_error_report,
116 .output = neigh_resolve_output,
117 .connected_output = neigh_resolve_output,
118 .hh_output = dev_queue_xmit,
119 .queue_xmit = dev_queue_xmit,
123 static struct neigh_ops ndisc_direct_ops = {
124 .family = AF_INET6,
125 .output = dev_queue_xmit,
126 .connected_output = dev_queue_xmit,
127 .hh_output = dev_queue_xmit,
128 .queue_xmit = dev_queue_xmit,
131 struct neigh_table nd_tbl = {
132 .family = AF_INET6,
133 .entry_size = sizeof(struct neighbour) + sizeof(struct in6_addr),
134 .key_len = sizeof(struct in6_addr),
135 .hash = ndisc_hash,
136 .constructor = ndisc_constructor,
137 .pconstructor = pndisc_constructor,
138 .pdestructor = pndisc_destructor,
139 .proxy_redo = pndisc_redo,
140 .id = "ndisc_cache",
141 .parms = {
142 .tbl = &nd_tbl,
143 .base_reachable_time = 30 * HZ,
144 .retrans_time = 1 * HZ,
145 .gc_staletime = 60 * HZ,
146 .reachable_time = 30 * HZ,
147 .delay_probe_time = 5 * HZ,
148 .queue_len = 3,
149 .ucast_probes = 3,
150 .mcast_probes = 3,
151 .anycast_delay = 1 * HZ,
152 .proxy_delay = (8 * HZ) / 10,
153 .proxy_qlen = 64,
155 .gc_interval = 30 * HZ,
156 .gc_thresh1 = 128,
157 .gc_thresh2 = 512,
158 .gc_thresh3 = 1024,
161 /* ND options */
162 struct ndisc_options {
163 struct nd_opt_hdr *nd_opt_array[__ND_OPT_ARRAY_MAX];
164 #ifdef CONFIG_IPV6_ROUTE_INFO
165 struct nd_opt_hdr *nd_opts_ri;
166 struct nd_opt_hdr *nd_opts_ri_end;
167 #endif
168 struct nd_opt_hdr *nd_useropts;
169 struct nd_opt_hdr *nd_useropts_end;
172 #define nd_opts_src_lladdr nd_opt_array[ND_OPT_SOURCE_LL_ADDR]
173 #define nd_opts_tgt_lladdr nd_opt_array[ND_OPT_TARGET_LL_ADDR]
174 #define nd_opts_pi nd_opt_array[ND_OPT_PREFIX_INFO]
175 #define nd_opts_pi_end nd_opt_array[__ND_OPT_PREFIX_INFO_END]
176 #define nd_opts_rh nd_opt_array[ND_OPT_REDIRECT_HDR]
177 #define nd_opts_mtu nd_opt_array[ND_OPT_MTU]
179 #define NDISC_OPT_SPACE(len) (((len)+2+7)&~7)
182 * Return the padding between the option length and the start of the
183 * link addr. Currently only IP-over-InfiniBand needs this, although
184 * if RFC 3831 IPv6-over-Fibre Channel is ever implemented it may
185 * also need a pad of 2.
187 static int ndisc_addr_option_pad(unsigned short type)
189 switch (type) {
190 case ARPHRD_INFINIBAND: return 2;
191 default: return 0;
195 static inline int ndisc_opt_addr_space(struct net_device *dev)
197 return NDISC_OPT_SPACE(dev->addr_len + ndisc_addr_option_pad(dev->type));
200 static u8 *ndisc_fill_addr_option(u8 *opt, int type, void *data, int data_len,
201 unsigned short addr_type)
203 int space = NDISC_OPT_SPACE(data_len);
204 int pad = ndisc_addr_option_pad(addr_type);
206 opt[0] = type;
207 opt[1] = space>>3;
209 memset(opt + 2, 0, pad);
210 opt += pad;
211 space -= pad;
213 memcpy(opt+2, data, data_len);
214 data_len += 2;
215 opt += data_len;
216 if ((space -= data_len) > 0)
217 memset(opt, 0, space);
218 return opt + space;
221 static struct nd_opt_hdr *ndisc_next_option(struct nd_opt_hdr *cur,
222 struct nd_opt_hdr *end)
224 int type;
225 if (!cur || !end || cur >= end)
226 return NULL;
227 type = cur->nd_opt_type;
228 do {
229 cur = ((void *)cur) + (cur->nd_opt_len << 3);
230 } while(cur < end && cur->nd_opt_type != type);
231 return (cur <= end && cur->nd_opt_type == type ? cur : NULL);
234 static inline int ndisc_is_useropt(struct nd_opt_hdr *opt)
236 return (opt->nd_opt_type == ND_OPT_RDNSS);
239 static struct nd_opt_hdr *ndisc_next_useropt(struct nd_opt_hdr *cur,
240 struct nd_opt_hdr *end)
242 if (!cur || !end || cur >= end)
243 return NULL;
244 do {
245 cur = ((void *)cur) + (cur->nd_opt_len << 3);
246 } while(cur < end && !ndisc_is_useropt(cur));
247 return (cur <= end && ndisc_is_useropt(cur) ? cur : NULL);
250 static struct ndisc_options *ndisc_parse_options(u8 *opt, int opt_len,
251 struct ndisc_options *ndopts)
253 struct nd_opt_hdr *nd_opt = (struct nd_opt_hdr *)opt;
255 if (!nd_opt || opt_len < 0 || !ndopts)
256 return NULL;
257 memset(ndopts, 0, sizeof(*ndopts));
258 while (opt_len) {
259 int l;
260 if (opt_len < sizeof(struct nd_opt_hdr))
261 return NULL;
262 l = nd_opt->nd_opt_len << 3;
263 if (opt_len < l || l == 0)
264 return NULL;
265 switch (nd_opt->nd_opt_type) {
266 case ND_OPT_SOURCE_LL_ADDR:
267 case ND_OPT_TARGET_LL_ADDR:
268 case ND_OPT_MTU:
269 case ND_OPT_REDIRECT_HDR:
270 if (ndopts->nd_opt_array[nd_opt->nd_opt_type]) {
271 ND_PRINTK2(KERN_WARNING
272 "%s(): duplicated ND6 option found: type=%d\n",
273 __FUNCTION__,
274 nd_opt->nd_opt_type);
275 } else {
276 ndopts->nd_opt_array[nd_opt->nd_opt_type] = nd_opt;
278 break;
279 case ND_OPT_PREFIX_INFO:
280 ndopts->nd_opts_pi_end = nd_opt;
281 if (!ndopts->nd_opt_array[nd_opt->nd_opt_type])
282 ndopts->nd_opt_array[nd_opt->nd_opt_type] = nd_opt;
283 break;
284 #ifdef CONFIG_IPV6_ROUTE_INFO
285 case ND_OPT_ROUTE_INFO:
286 ndopts->nd_opts_ri_end = nd_opt;
287 if (!ndopts->nd_opts_ri)
288 ndopts->nd_opts_ri = nd_opt;
289 break;
290 #endif
291 default:
292 if (ndisc_is_useropt(nd_opt)) {
293 ndopts->nd_useropts_end = nd_opt;
294 if (!ndopts->nd_useropts)
295 ndopts->nd_useropts = nd_opt;
296 } else {
298 * Unknown options must be silently ignored,
299 * to accommodate future extension to the
300 * protocol.
302 ND_PRINTK2(KERN_NOTICE
303 "%s(): ignored unsupported option; type=%d, len=%d\n",
304 __FUNCTION__,
305 nd_opt->nd_opt_type, nd_opt->nd_opt_len);
308 opt_len -= l;
309 nd_opt = ((void *)nd_opt) + l;
311 return ndopts;
314 static inline u8 *ndisc_opt_addr_data(struct nd_opt_hdr *p,
315 struct net_device *dev)
317 u8 *lladdr = (u8 *)(p + 1);
318 int lladdrlen = p->nd_opt_len << 3;
319 int prepad = ndisc_addr_option_pad(dev->type);
320 if (lladdrlen != NDISC_OPT_SPACE(dev->addr_len + prepad))
321 return NULL;
322 return (lladdr + prepad);
325 int ndisc_mc_map(struct in6_addr *addr, char *buf, struct net_device *dev, int dir)
327 switch (dev->type) {
328 case ARPHRD_ETHER:
329 case ARPHRD_IEEE802: /* Not sure. Check it later. --ANK */
330 case ARPHRD_FDDI:
331 ipv6_eth_mc_map(addr, buf);
332 return 0;
333 case ARPHRD_IEEE802_TR:
334 ipv6_tr_mc_map(addr,buf);
335 return 0;
336 case ARPHRD_ARCNET:
337 ipv6_arcnet_mc_map(addr, buf);
338 return 0;
339 case ARPHRD_INFINIBAND:
340 ipv6_ib_mc_map(addr, dev->broadcast, buf);
341 return 0;
342 default:
343 if (dir) {
344 memcpy(buf, dev->broadcast, dev->addr_len);
345 return 0;
348 return -EINVAL;
351 EXPORT_SYMBOL(ndisc_mc_map);
353 static u32 ndisc_hash(const void *pkey, const struct net_device *dev)
355 const u32 *p32 = pkey;
356 u32 addr_hash, i;
358 addr_hash = 0;
359 for (i = 0; i < (sizeof(struct in6_addr) / sizeof(u32)); i++)
360 addr_hash ^= *p32++;
362 return jhash_2words(addr_hash, dev->ifindex, nd_tbl.hash_rnd);
365 static int ndisc_constructor(struct neighbour *neigh)
367 struct in6_addr *addr = (struct in6_addr*)&neigh->primary_key;
368 struct net_device *dev = neigh->dev;
369 struct inet6_dev *in6_dev;
370 struct neigh_parms *parms;
371 int is_multicast = ipv6_addr_is_multicast(addr);
373 rcu_read_lock();
374 in6_dev = in6_dev_get(dev);
375 if (in6_dev == NULL) {
376 rcu_read_unlock();
377 return -EINVAL;
380 parms = in6_dev->nd_parms;
381 __neigh_parms_put(neigh->parms);
382 neigh->parms = neigh_parms_clone(parms);
383 rcu_read_unlock();
385 neigh->type = is_multicast ? RTN_MULTICAST : RTN_UNICAST;
386 if (!dev->header_ops) {
387 neigh->nud_state = NUD_NOARP;
388 neigh->ops = &ndisc_direct_ops;
389 neigh->output = neigh->ops->queue_xmit;
390 } else {
391 if (is_multicast) {
392 neigh->nud_state = NUD_NOARP;
393 ndisc_mc_map(addr, neigh->ha, dev, 1);
394 } else if (dev->flags&(IFF_NOARP|IFF_LOOPBACK)) {
395 neigh->nud_state = NUD_NOARP;
396 memcpy(neigh->ha, dev->dev_addr, dev->addr_len);
397 if (dev->flags&IFF_LOOPBACK)
398 neigh->type = RTN_LOCAL;
399 } else if (dev->flags&IFF_POINTOPOINT) {
400 neigh->nud_state = NUD_NOARP;
401 memcpy(neigh->ha, dev->broadcast, dev->addr_len);
403 if (dev->header_ops->cache)
404 neigh->ops = &ndisc_hh_ops;
405 else
406 neigh->ops = &ndisc_generic_ops;
407 if (neigh->nud_state&NUD_VALID)
408 neigh->output = neigh->ops->connected_output;
409 else
410 neigh->output = neigh->ops->output;
412 in6_dev_put(in6_dev);
413 return 0;
416 static int pndisc_constructor(struct pneigh_entry *n)
418 struct in6_addr *addr = (struct in6_addr*)&n->key;
419 struct in6_addr maddr;
420 struct net_device *dev = n->dev;
422 if (dev == NULL || __in6_dev_get(dev) == NULL)
423 return -EINVAL;
424 addrconf_addr_solict_mult(addr, &maddr);
425 ipv6_dev_mc_inc(dev, &maddr);
426 return 0;
429 static void pndisc_destructor(struct pneigh_entry *n)
431 struct in6_addr *addr = (struct in6_addr*)&n->key;
432 struct in6_addr maddr;
433 struct net_device *dev = n->dev;
435 if (dev == NULL || __in6_dev_get(dev) == NULL)
436 return;
437 addrconf_addr_solict_mult(addr, &maddr);
438 ipv6_dev_mc_dec(dev, &maddr);
442 * Send a Neighbour Advertisement
445 static inline void ndisc_flow_init(struct flowi *fl, u8 type,
446 struct in6_addr *saddr, struct in6_addr *daddr,
447 int oif)
449 memset(fl, 0, sizeof(*fl));
450 ipv6_addr_copy(&fl->fl6_src, saddr);
451 ipv6_addr_copy(&fl->fl6_dst, daddr);
452 fl->proto = IPPROTO_ICMPV6;
453 fl->fl_icmp_type = type;
454 fl->fl_icmp_code = 0;
455 fl->oif = oif;
456 security_sk_classify_flow(ndisc_socket->sk, fl);
459 static void __ndisc_send(struct net_device *dev,
460 struct neighbour *neigh,
461 struct in6_addr *daddr, struct in6_addr *saddr,
462 struct icmp6hdr *icmp6h, struct in6_addr *target,
463 int llinfo)
465 struct flowi fl;
466 struct dst_entry *dst;
467 struct sock *sk = ndisc_socket->sk;
468 struct sk_buff *skb;
469 struct icmp6hdr *hdr;
470 struct inet6_dev *idev;
471 int len;
472 int err;
473 u8 *opt, type;
475 type = icmp6h->icmp6_type;
477 ndisc_flow_init(&fl, type, saddr, daddr,
478 dev->ifindex);
480 dst = ndisc_dst_alloc(dev, neigh, daddr, ip6_output);
481 if (!dst)
482 return;
484 err = xfrm_lookup(&dst, &fl, NULL, 0);
485 if (err < 0)
486 return;
488 if (!dev->addr_len)
489 llinfo = 0;
491 len = sizeof(struct icmp6hdr) + (target ? sizeof(*target) : 0);
492 if (llinfo)
493 len += ndisc_opt_addr_space(dev);
495 skb = sock_alloc_send_skb(sk,
496 (MAX_HEADER + sizeof(struct ipv6hdr) +
497 len + LL_RESERVED_SPACE(dev)),
498 1, &err);
499 if (!skb) {
500 ND_PRINTK0(KERN_ERR
501 "ICMPv6 ND: %s() failed to allocate an skb.\n",
502 __FUNCTION__);
503 dst_release(dst);
504 return;
507 skb_reserve(skb, LL_RESERVED_SPACE(dev));
508 ip6_nd_hdr(sk, skb, dev, saddr, daddr, IPPROTO_ICMPV6, len);
510 skb->transport_header = skb->tail;
511 skb_put(skb, len);
513 hdr = (struct icmp6hdr *)skb_transport_header(skb);
514 memcpy(hdr, icmp6h, sizeof(*hdr));
516 opt = skb_transport_header(skb) + sizeof(struct icmp6hdr);
517 if (target) {
518 ipv6_addr_copy((struct in6_addr *)opt, target);
519 opt += sizeof(*target);
522 if (llinfo)
523 ndisc_fill_addr_option(opt, llinfo, dev->dev_addr,
524 dev->addr_len, dev->type);
526 hdr->icmp6_cksum = csum_ipv6_magic(saddr, daddr, len,
527 IPPROTO_ICMPV6,
528 csum_partial((__u8 *) hdr,
529 len, 0));
531 skb->dst = dst;
533 idev = in6_dev_get(dst->dev);
534 IP6_INC_STATS(idev, IPSTATS_MIB_OUTREQUESTS);
536 err = NF_HOOK(PF_INET6, NF_INET_LOCAL_OUT, skb, NULL, dst->dev,
537 dst_output);
538 if (!err) {
539 ICMP6MSGOUT_INC_STATS(idev, type);
540 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTMSGS);
543 if (likely(idev != NULL))
544 in6_dev_put(idev);
547 static void ndisc_send_na(struct net_device *dev, struct neighbour *neigh,
548 struct in6_addr *daddr, struct in6_addr *solicited_addr,
549 int router, int solicited, int override, int inc_opt)
551 struct in6_addr tmpaddr;
552 struct inet6_ifaddr *ifp;
553 struct in6_addr *src_addr;
554 struct icmp6hdr icmp6h = {
555 .icmp6_type = NDISC_NEIGHBOUR_ADVERTISEMENT,
558 /* for anycast or proxy, solicited_addr != src_addr */
559 ifp = ipv6_get_ifaddr(&init_net, solicited_addr, dev, 1);
560 if (ifp) {
561 src_addr = solicited_addr;
562 if (ifp->flags & IFA_F_OPTIMISTIC)
563 override = 0;
564 in6_ifa_put(ifp);
565 } else {
566 if (ipv6_dev_get_saddr(dev, daddr, &tmpaddr))
567 return;
568 src_addr = &tmpaddr;
571 icmp6h.icmp6_router = router;
572 icmp6h.icmp6_solicited = solicited;
573 icmp6h.icmp6_override = override;
575 __ndisc_send(dev, neigh, daddr, src_addr,
576 &icmp6h, solicited_addr,
577 inc_opt ? ND_OPT_TARGET_LL_ADDR : 0);
580 void ndisc_send_ns(struct net_device *dev, struct neighbour *neigh,
581 struct in6_addr *solicit,
582 struct in6_addr *daddr, struct in6_addr *saddr)
584 struct in6_addr addr_buf;
585 struct icmp6hdr icmp6h = {
586 .icmp6_type = NDISC_NEIGHBOUR_SOLICITATION,
589 if (saddr == NULL) {
590 if (ipv6_get_lladdr(dev, &addr_buf,
591 (IFA_F_TENTATIVE|IFA_F_OPTIMISTIC)))
592 return;
593 saddr = &addr_buf;
596 __ndisc_send(dev, neigh, daddr, saddr,
597 &icmp6h, solicit,
598 !ipv6_addr_any(saddr) ? ND_OPT_SOURCE_LL_ADDR : 0);
601 void ndisc_send_rs(struct net_device *dev, struct in6_addr *saddr,
602 struct in6_addr *daddr)
604 struct icmp6hdr icmp6h = {
605 .icmp6_type = NDISC_ROUTER_SOLICITATION,
607 int send_sllao = dev->addr_len;
609 #ifdef CONFIG_IPV6_OPTIMISTIC_DAD
611 * According to section 2.2 of RFC 4429, we must not
612 * send router solicitations with a sllao from
613 * optimistic addresses, but we may send the solicitation
614 * if we don't include the sllao. So here we check
615 * if our address is optimistic, and if so, we
616 * suppress the inclusion of the sllao.
618 if (send_sllao) {
619 struct inet6_ifaddr *ifp = ipv6_get_ifaddr(&init_net, saddr,
620 dev, 1);
621 if (ifp) {
622 if (ifp->flags & IFA_F_OPTIMISTIC) {
623 send_sllao = 0;
625 in6_ifa_put(ifp);
626 } else {
627 send_sllao = 0;
630 #endif
631 __ndisc_send(dev, NULL, daddr, saddr,
632 &icmp6h, NULL,
633 send_sllao ? ND_OPT_SOURCE_LL_ADDR : 0);
637 static void ndisc_error_report(struct neighbour *neigh, struct sk_buff *skb)
640 * "The sender MUST return an ICMP
641 * destination unreachable"
643 dst_link_failure(skb);
644 kfree_skb(skb);
647 /* Called with locked neigh: either read or both */
649 static void ndisc_solicit(struct neighbour *neigh, struct sk_buff *skb)
651 struct in6_addr *saddr = NULL;
652 struct in6_addr mcaddr;
653 struct net_device *dev = neigh->dev;
654 struct in6_addr *target = (struct in6_addr *)&neigh->primary_key;
655 int probes = atomic_read(&neigh->probes);
657 if (skb && ipv6_chk_addr(&init_net, &ipv6_hdr(skb)->saddr, dev, 1))
658 saddr = &ipv6_hdr(skb)->saddr;
660 if ((probes -= neigh->parms->ucast_probes) < 0) {
661 if (!(neigh->nud_state & NUD_VALID)) {
662 ND_PRINTK1(KERN_DEBUG
663 "%s(): trying to ucast probe in NUD_INVALID: "
664 NIP6_FMT "\n",
665 __FUNCTION__,
666 NIP6(*target));
668 ndisc_send_ns(dev, neigh, target, target, saddr);
669 } else if ((probes -= neigh->parms->app_probes) < 0) {
670 #ifdef CONFIG_ARPD
671 neigh_app_ns(neigh);
672 #endif
673 } else {
674 addrconf_addr_solict_mult(target, &mcaddr);
675 ndisc_send_ns(dev, NULL, target, &mcaddr, saddr);
679 static void ndisc_recv_ns(struct sk_buff *skb)
681 struct nd_msg *msg = (struct nd_msg *)skb_transport_header(skb);
682 struct in6_addr *saddr = &ipv6_hdr(skb)->saddr;
683 struct in6_addr *daddr = &ipv6_hdr(skb)->daddr;
684 u8 *lladdr = NULL;
685 u32 ndoptlen = skb->tail - (skb->transport_header +
686 offsetof(struct nd_msg, opt));
687 struct ndisc_options ndopts;
688 struct net_device *dev = skb->dev;
689 struct inet6_ifaddr *ifp;
690 struct inet6_dev *idev = NULL;
691 struct neighbour *neigh;
692 struct pneigh_entry *pneigh = NULL;
693 int dad = ipv6_addr_any(saddr);
694 int inc;
695 int is_router;
697 if (ipv6_addr_is_multicast(&msg->target)) {
698 ND_PRINTK2(KERN_WARNING
699 "ICMPv6 NS: multicast target address");
700 return;
704 * RFC2461 7.1.1:
705 * DAD has to be destined for solicited node multicast address.
707 if (dad &&
708 !(daddr->s6_addr32[0] == htonl(0xff020000) &&
709 daddr->s6_addr32[1] == htonl(0x00000000) &&
710 daddr->s6_addr32[2] == htonl(0x00000001) &&
711 daddr->s6_addr [12] == 0xff )) {
712 ND_PRINTK2(KERN_WARNING
713 "ICMPv6 NS: bad DAD packet (wrong destination)\n");
714 return;
717 if (!ndisc_parse_options(msg->opt, ndoptlen, &ndopts)) {
718 ND_PRINTK2(KERN_WARNING
719 "ICMPv6 NS: invalid ND options\n");
720 return;
723 if (ndopts.nd_opts_src_lladdr) {
724 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_src_lladdr, dev);
725 if (!lladdr) {
726 ND_PRINTK2(KERN_WARNING
727 "ICMPv6 NS: invalid link-layer address length\n");
728 return;
731 /* RFC2461 7.1.1:
732 * If the IP source address is the unspecified address,
733 * there MUST NOT be source link-layer address option
734 * in the message.
736 if (dad) {
737 ND_PRINTK2(KERN_WARNING
738 "ICMPv6 NS: bad DAD packet (link-layer address option)\n");
739 return;
743 inc = ipv6_addr_is_multicast(daddr);
745 if ((ifp = ipv6_get_ifaddr(&init_net, &msg->target, dev, 1)) != NULL) {
747 if (ifp->flags & (IFA_F_TENTATIVE|IFA_F_OPTIMISTIC)) {
748 if (dad) {
749 if (dev->type == ARPHRD_IEEE802_TR) {
750 const unsigned char *sadr;
751 sadr = skb_mac_header(skb);
752 if (((sadr[8] ^ dev->dev_addr[0]) & 0x7f) == 0 &&
753 sadr[9] == dev->dev_addr[1] &&
754 sadr[10] == dev->dev_addr[2] &&
755 sadr[11] == dev->dev_addr[3] &&
756 sadr[12] == dev->dev_addr[4] &&
757 sadr[13] == dev->dev_addr[5]) {
758 /* looped-back to us */
759 goto out;
764 * We are colliding with another node
765 * who is doing DAD
766 * so fail our DAD process
768 addrconf_dad_failure(ifp);
769 return;
770 } else {
772 * This is not a dad solicitation.
773 * If we are an optimistic node,
774 * we should respond.
775 * Otherwise, we should ignore it.
777 if (!(ifp->flags & IFA_F_OPTIMISTIC))
778 goto out;
782 idev = ifp->idev;
783 } else {
784 idev = in6_dev_get(dev);
785 if (!idev) {
786 /* XXX: count this drop? */
787 return;
790 if (ipv6_chk_acast_addr(dev, &msg->target) ||
791 (idev->cnf.forwarding &&
792 (ipv6_devconf.proxy_ndp || idev->cnf.proxy_ndp) &&
793 (pneigh = pneigh_lookup(&nd_tbl, &init_net,
794 &msg->target, dev, 0)) != NULL)) {
795 if (!(NEIGH_CB(skb)->flags & LOCALLY_ENQUEUED) &&
796 skb->pkt_type != PACKET_HOST &&
797 inc != 0 &&
798 idev->nd_parms->proxy_delay != 0) {
800 * for anycast or proxy,
801 * sender should delay its response
802 * by a random time between 0 and
803 * MAX_ANYCAST_DELAY_TIME seconds.
804 * (RFC2461) -- yoshfuji
806 struct sk_buff *n = skb_clone(skb, GFP_ATOMIC);
807 if (n)
808 pneigh_enqueue(&nd_tbl, idev->nd_parms, n);
809 goto out;
811 } else
812 goto out;
815 is_router = !!(pneigh ? pneigh->flags & NTF_ROUTER : idev->cnf.forwarding);
817 if (dad) {
818 struct in6_addr maddr;
820 ipv6_addr_all_nodes(&maddr);
821 ndisc_send_na(dev, NULL, &maddr, &msg->target,
822 is_router, 0, (ifp != NULL), 1);
823 goto out;
826 if (inc)
827 NEIGH_CACHE_STAT_INC(&nd_tbl, rcv_probes_mcast);
828 else
829 NEIGH_CACHE_STAT_INC(&nd_tbl, rcv_probes_ucast);
832 * update / create cache entry
833 * for the source address
835 neigh = __neigh_lookup(&nd_tbl, saddr, dev,
836 !inc || lladdr || !dev->addr_len);
837 if (neigh)
838 neigh_update(neigh, lladdr, NUD_STALE,
839 NEIGH_UPDATE_F_WEAK_OVERRIDE|
840 NEIGH_UPDATE_F_OVERRIDE);
841 if (neigh || !dev->header_ops) {
842 ndisc_send_na(dev, neigh, saddr, &msg->target,
843 is_router,
844 1, (ifp != NULL && inc), inc);
845 if (neigh)
846 neigh_release(neigh);
849 out:
850 if (ifp)
851 in6_ifa_put(ifp);
852 else
853 in6_dev_put(idev);
855 return;
858 static void ndisc_recv_na(struct sk_buff *skb)
860 struct nd_msg *msg = (struct nd_msg *)skb_transport_header(skb);
861 struct in6_addr *saddr = &ipv6_hdr(skb)->saddr;
862 struct in6_addr *daddr = &ipv6_hdr(skb)->daddr;
863 u8 *lladdr = NULL;
864 u32 ndoptlen = skb->tail - (skb->transport_header +
865 offsetof(struct nd_msg, opt));
866 struct ndisc_options ndopts;
867 struct net_device *dev = skb->dev;
868 struct inet6_ifaddr *ifp;
869 struct neighbour *neigh;
871 if (skb->len < sizeof(struct nd_msg)) {
872 ND_PRINTK2(KERN_WARNING
873 "ICMPv6 NA: packet too short\n");
874 return;
877 if (ipv6_addr_is_multicast(&msg->target)) {
878 ND_PRINTK2(KERN_WARNING
879 "ICMPv6 NA: target address is multicast.\n");
880 return;
883 if (ipv6_addr_is_multicast(daddr) &&
884 msg->icmph.icmp6_solicited) {
885 ND_PRINTK2(KERN_WARNING
886 "ICMPv6 NA: solicited NA is multicasted.\n");
887 return;
890 if (!ndisc_parse_options(msg->opt, ndoptlen, &ndopts)) {
891 ND_PRINTK2(KERN_WARNING
892 "ICMPv6 NS: invalid ND option\n");
893 return;
895 if (ndopts.nd_opts_tgt_lladdr) {
896 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_tgt_lladdr, dev);
897 if (!lladdr) {
898 ND_PRINTK2(KERN_WARNING
899 "ICMPv6 NA: invalid link-layer address length\n");
900 return;
903 if ((ifp = ipv6_get_ifaddr(&init_net, &msg->target, dev, 1))) {
904 if (ifp->flags & IFA_F_TENTATIVE) {
905 addrconf_dad_failure(ifp);
906 return;
908 /* What should we make now? The advertisement
909 is invalid, but ndisc specs say nothing
910 about it. It could be misconfiguration, or
911 an smart proxy agent tries to help us :-)
913 ND_PRINTK1(KERN_WARNING
914 "ICMPv6 NA: someone advertises our address on %s!\n",
915 ifp->idev->dev->name);
916 in6_ifa_put(ifp);
917 return;
919 neigh = neigh_lookup(&nd_tbl, &msg->target, dev);
921 if (neigh) {
922 u8 old_flags = neigh->flags;
924 if (neigh->nud_state & NUD_FAILED)
925 goto out;
928 * Don't update the neighbor cache entry on a proxy NA from
929 * ourselves because either the proxied node is off link or it
930 * has already sent a NA to us.
932 if (lladdr && !memcmp(lladdr, dev->dev_addr, dev->addr_len) &&
933 ipv6_devconf.forwarding && ipv6_devconf.proxy_ndp &&
934 pneigh_lookup(&nd_tbl, &init_net, &msg->target, dev, 0)) {
935 /* XXX: idev->cnf.prixy_ndp */
936 goto out;
939 neigh_update(neigh, lladdr,
940 msg->icmph.icmp6_solicited ? NUD_REACHABLE : NUD_STALE,
941 NEIGH_UPDATE_F_WEAK_OVERRIDE|
942 (msg->icmph.icmp6_override ? NEIGH_UPDATE_F_OVERRIDE : 0)|
943 NEIGH_UPDATE_F_OVERRIDE_ISROUTER|
944 (msg->icmph.icmp6_router ? NEIGH_UPDATE_F_ISROUTER : 0));
946 if ((old_flags & ~neigh->flags) & NTF_ROUTER) {
948 * Change: router to host
950 struct rt6_info *rt;
951 rt = rt6_get_dflt_router(saddr, dev);
952 if (rt)
953 ip6_del_rt(rt);
956 out:
957 neigh_release(neigh);
961 static void ndisc_recv_rs(struct sk_buff *skb)
963 struct rs_msg *rs_msg = (struct rs_msg *)skb_transport_header(skb);
964 unsigned long ndoptlen = skb->len - sizeof(*rs_msg);
965 struct neighbour *neigh;
966 struct inet6_dev *idev;
967 struct in6_addr *saddr = &ipv6_hdr(skb)->saddr;
968 struct ndisc_options ndopts;
969 u8 *lladdr = NULL;
971 if (skb->len < sizeof(*rs_msg))
972 return;
974 idev = in6_dev_get(skb->dev);
975 if (!idev) {
976 if (net_ratelimit())
977 ND_PRINTK1("ICMP6 RS: can't find in6 device\n");
978 return;
981 /* Don't accept RS if we're not in router mode */
982 if (!idev->cnf.forwarding)
983 goto out;
986 * Don't update NCE if src = ::;
987 * this implies that the source node has no ip address assigned yet.
989 if (ipv6_addr_any(saddr))
990 goto out;
992 /* Parse ND options */
993 if (!ndisc_parse_options(rs_msg->opt, ndoptlen, &ndopts)) {
994 if (net_ratelimit())
995 ND_PRINTK2("ICMP6 NS: invalid ND option, ignored\n");
996 goto out;
999 if (ndopts.nd_opts_src_lladdr) {
1000 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_src_lladdr,
1001 skb->dev);
1002 if (!lladdr)
1003 goto out;
1006 neigh = __neigh_lookup(&nd_tbl, saddr, skb->dev, 1);
1007 if (neigh) {
1008 neigh_update(neigh, lladdr, NUD_STALE,
1009 NEIGH_UPDATE_F_WEAK_OVERRIDE|
1010 NEIGH_UPDATE_F_OVERRIDE|
1011 NEIGH_UPDATE_F_OVERRIDE_ISROUTER);
1012 neigh_release(neigh);
1014 out:
1015 in6_dev_put(idev);
1018 static void ndisc_ra_useropt(struct sk_buff *ra, struct nd_opt_hdr *opt)
1020 struct icmp6hdr *icmp6h = (struct icmp6hdr *)skb_transport_header(ra);
1021 struct sk_buff *skb;
1022 struct nlmsghdr *nlh;
1023 struct nduseroptmsg *ndmsg;
1024 int err;
1025 int base_size = NLMSG_ALIGN(sizeof(struct nduseroptmsg)
1026 + (opt->nd_opt_len << 3));
1027 size_t msg_size = base_size + nla_total_size(sizeof(struct in6_addr));
1029 skb = nlmsg_new(msg_size, GFP_ATOMIC);
1030 if (skb == NULL) {
1031 err = -ENOBUFS;
1032 goto errout;
1035 nlh = nlmsg_put(skb, 0, 0, RTM_NEWNDUSEROPT, base_size, 0);
1036 if (nlh == NULL) {
1037 goto nla_put_failure;
1040 ndmsg = nlmsg_data(nlh);
1041 ndmsg->nduseropt_family = AF_INET6;
1042 ndmsg->nduseropt_ifindex = ra->dev->ifindex;
1043 ndmsg->nduseropt_icmp_type = icmp6h->icmp6_type;
1044 ndmsg->nduseropt_icmp_code = icmp6h->icmp6_code;
1045 ndmsg->nduseropt_opts_len = opt->nd_opt_len << 3;
1047 memcpy(ndmsg + 1, opt, opt->nd_opt_len << 3);
1049 NLA_PUT(skb, NDUSEROPT_SRCADDR, sizeof(struct in6_addr),
1050 &ipv6_hdr(ra)->saddr);
1051 nlmsg_end(skb, nlh);
1053 err = rtnl_notify(skb, &init_net, 0, RTNLGRP_ND_USEROPT, NULL,
1054 GFP_ATOMIC);
1055 if (err < 0)
1056 goto errout;
1058 return;
1060 nla_put_failure:
1061 nlmsg_free(skb);
1062 err = -EMSGSIZE;
1063 errout:
1064 rtnl_set_sk_err(&init_net, RTNLGRP_ND_USEROPT, err);
1067 static void ndisc_router_discovery(struct sk_buff *skb)
1069 struct ra_msg *ra_msg = (struct ra_msg *)skb_transport_header(skb);
1070 struct neighbour *neigh = NULL;
1071 struct inet6_dev *in6_dev;
1072 struct rt6_info *rt = NULL;
1073 int lifetime;
1074 struct ndisc_options ndopts;
1075 int optlen;
1076 unsigned int pref = 0;
1078 __u8 * opt = (__u8 *)(ra_msg + 1);
1080 optlen = (skb->tail - skb->transport_header) - sizeof(struct ra_msg);
1082 if (!(ipv6_addr_type(&ipv6_hdr(skb)->saddr) & IPV6_ADDR_LINKLOCAL)) {
1083 ND_PRINTK2(KERN_WARNING
1084 "ICMPv6 RA: source address is not link-local.\n");
1085 return;
1087 if (optlen < 0) {
1088 ND_PRINTK2(KERN_WARNING
1089 "ICMPv6 RA: packet too short\n");
1090 return;
1094 * set the RA_RECV flag in the interface
1097 in6_dev = in6_dev_get(skb->dev);
1098 if (in6_dev == NULL) {
1099 ND_PRINTK0(KERN_ERR
1100 "ICMPv6 RA: can't find inet6 device for %s.\n",
1101 skb->dev->name);
1102 return;
1104 if (in6_dev->cnf.forwarding || !in6_dev->cnf.accept_ra) {
1105 in6_dev_put(in6_dev);
1106 return;
1109 if (!ndisc_parse_options(opt, optlen, &ndopts)) {
1110 in6_dev_put(in6_dev);
1111 ND_PRINTK2(KERN_WARNING
1112 "ICMP6 RA: invalid ND options\n");
1113 return;
1116 if (in6_dev->if_flags & IF_RS_SENT) {
1118 * flag that an RA was received after an RS was sent
1119 * out on this interface.
1121 in6_dev->if_flags |= IF_RA_RCVD;
1125 * Remember the managed/otherconf flags from most recently
1126 * received RA message (RFC 2462) -- yoshfuji
1128 in6_dev->if_flags = (in6_dev->if_flags & ~(IF_RA_MANAGED |
1129 IF_RA_OTHERCONF)) |
1130 (ra_msg->icmph.icmp6_addrconf_managed ?
1131 IF_RA_MANAGED : 0) |
1132 (ra_msg->icmph.icmp6_addrconf_other ?
1133 IF_RA_OTHERCONF : 0);
1135 if (!in6_dev->cnf.accept_ra_defrtr)
1136 goto skip_defrtr;
1138 lifetime = ntohs(ra_msg->icmph.icmp6_rt_lifetime);
1140 #ifdef CONFIG_IPV6_ROUTER_PREF
1141 pref = ra_msg->icmph.icmp6_router_pref;
1142 /* 10b is handled as if it were 00b (medium) */
1143 if (pref == ICMPV6_ROUTER_PREF_INVALID ||
1144 !in6_dev->cnf.accept_ra_rtr_pref)
1145 pref = ICMPV6_ROUTER_PREF_MEDIUM;
1146 #endif
1148 rt = rt6_get_dflt_router(&ipv6_hdr(skb)->saddr, skb->dev);
1150 if (rt)
1151 neigh = rt->rt6i_nexthop;
1153 if (rt && lifetime == 0) {
1154 neigh_clone(neigh);
1155 ip6_del_rt(rt);
1156 rt = NULL;
1159 if (rt == NULL && lifetime) {
1160 ND_PRINTK3(KERN_DEBUG
1161 "ICMPv6 RA: adding default router.\n");
1163 rt = rt6_add_dflt_router(&ipv6_hdr(skb)->saddr, skb->dev, pref);
1164 if (rt == NULL) {
1165 ND_PRINTK0(KERN_ERR
1166 "ICMPv6 RA: %s() failed to add default route.\n",
1167 __FUNCTION__);
1168 in6_dev_put(in6_dev);
1169 return;
1172 neigh = rt->rt6i_nexthop;
1173 if (neigh == NULL) {
1174 ND_PRINTK0(KERN_ERR
1175 "ICMPv6 RA: %s() got default router without neighbour.\n",
1176 __FUNCTION__);
1177 dst_release(&rt->u.dst);
1178 in6_dev_put(in6_dev);
1179 return;
1181 neigh->flags |= NTF_ROUTER;
1182 } else if (rt) {
1183 rt->rt6i_flags |= (rt->rt6i_flags & ~RTF_PREF_MASK) | RTF_PREF(pref);
1186 if (rt)
1187 rt->rt6i_expires = jiffies + (HZ * lifetime);
1189 if (ra_msg->icmph.icmp6_hop_limit) {
1190 in6_dev->cnf.hop_limit = ra_msg->icmph.icmp6_hop_limit;
1191 if (rt)
1192 rt->u.dst.metrics[RTAX_HOPLIMIT-1] = ra_msg->icmph.icmp6_hop_limit;
1195 skip_defrtr:
1198 * Update Reachable Time and Retrans Timer
1201 if (in6_dev->nd_parms) {
1202 unsigned long rtime = ntohl(ra_msg->retrans_timer);
1204 if (rtime && rtime/1000 < MAX_SCHEDULE_TIMEOUT/HZ) {
1205 rtime = (rtime*HZ)/1000;
1206 if (rtime < HZ/10)
1207 rtime = HZ/10;
1208 in6_dev->nd_parms->retrans_time = rtime;
1209 in6_dev->tstamp = jiffies;
1210 inet6_ifinfo_notify(RTM_NEWLINK, in6_dev);
1213 rtime = ntohl(ra_msg->reachable_time);
1214 if (rtime && rtime/1000 < MAX_SCHEDULE_TIMEOUT/(3*HZ)) {
1215 rtime = (rtime*HZ)/1000;
1217 if (rtime < HZ/10)
1218 rtime = HZ/10;
1220 if (rtime != in6_dev->nd_parms->base_reachable_time) {
1221 in6_dev->nd_parms->base_reachable_time = rtime;
1222 in6_dev->nd_parms->gc_staletime = 3 * rtime;
1223 in6_dev->nd_parms->reachable_time = neigh_rand_reach_time(rtime);
1224 in6_dev->tstamp = jiffies;
1225 inet6_ifinfo_notify(RTM_NEWLINK, in6_dev);
1231 * Process options.
1234 if (!neigh)
1235 neigh = __neigh_lookup(&nd_tbl, &ipv6_hdr(skb)->saddr,
1236 skb->dev, 1);
1237 if (neigh) {
1238 u8 *lladdr = NULL;
1239 if (ndopts.nd_opts_src_lladdr) {
1240 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_src_lladdr,
1241 skb->dev);
1242 if (!lladdr) {
1243 ND_PRINTK2(KERN_WARNING
1244 "ICMPv6 RA: invalid link-layer address length\n");
1245 goto out;
1248 neigh_update(neigh, lladdr, NUD_STALE,
1249 NEIGH_UPDATE_F_WEAK_OVERRIDE|
1250 NEIGH_UPDATE_F_OVERRIDE|
1251 NEIGH_UPDATE_F_OVERRIDE_ISROUTER|
1252 NEIGH_UPDATE_F_ISROUTER);
1255 #ifdef CONFIG_IPV6_ROUTE_INFO
1256 if (in6_dev->cnf.accept_ra_rtr_pref && ndopts.nd_opts_ri) {
1257 struct nd_opt_hdr *p;
1258 for (p = ndopts.nd_opts_ri;
1260 p = ndisc_next_option(p, ndopts.nd_opts_ri_end)) {
1261 if (((struct route_info *)p)->prefix_len > in6_dev->cnf.accept_ra_rt_info_max_plen)
1262 continue;
1263 rt6_route_rcv(skb->dev, (u8*)p, (p->nd_opt_len) << 3,
1264 &ipv6_hdr(skb)->saddr);
1267 #endif
1269 if (in6_dev->cnf.accept_ra_pinfo && ndopts.nd_opts_pi) {
1270 struct nd_opt_hdr *p;
1271 for (p = ndopts.nd_opts_pi;
1273 p = ndisc_next_option(p, ndopts.nd_opts_pi_end)) {
1274 addrconf_prefix_rcv(skb->dev, (u8*)p, (p->nd_opt_len) << 3);
1278 if (ndopts.nd_opts_mtu) {
1279 __be32 n;
1280 u32 mtu;
1282 memcpy(&n, ((u8*)(ndopts.nd_opts_mtu+1))+2, sizeof(mtu));
1283 mtu = ntohl(n);
1285 if (mtu < IPV6_MIN_MTU || mtu > skb->dev->mtu) {
1286 ND_PRINTK2(KERN_WARNING
1287 "ICMPv6 RA: invalid mtu: %d\n",
1288 mtu);
1289 } else if (in6_dev->cnf.mtu6 != mtu) {
1290 in6_dev->cnf.mtu6 = mtu;
1292 if (rt)
1293 rt->u.dst.metrics[RTAX_MTU-1] = mtu;
1295 rt6_mtu_change(skb->dev, mtu);
1299 if (ndopts.nd_useropts) {
1300 struct nd_opt_hdr *p;
1301 for (p = ndopts.nd_useropts;
1303 p = ndisc_next_useropt(p, ndopts.nd_useropts_end)) {
1304 ndisc_ra_useropt(skb, p);
1308 if (ndopts.nd_opts_tgt_lladdr || ndopts.nd_opts_rh) {
1309 ND_PRINTK2(KERN_WARNING
1310 "ICMPv6 RA: invalid RA options");
1312 out:
1313 if (rt)
1314 dst_release(&rt->u.dst);
1315 else if (neigh)
1316 neigh_release(neigh);
1317 in6_dev_put(in6_dev);
1320 static void ndisc_redirect_rcv(struct sk_buff *skb)
1322 struct inet6_dev *in6_dev;
1323 struct icmp6hdr *icmph;
1324 struct in6_addr *dest;
1325 struct in6_addr *target; /* new first hop to destination */
1326 struct neighbour *neigh;
1327 int on_link = 0;
1328 struct ndisc_options ndopts;
1329 int optlen;
1330 u8 *lladdr = NULL;
1332 if (!(ipv6_addr_type(&ipv6_hdr(skb)->saddr) & IPV6_ADDR_LINKLOCAL)) {
1333 ND_PRINTK2(KERN_WARNING
1334 "ICMPv6 Redirect: source address is not link-local.\n");
1335 return;
1338 optlen = skb->tail - skb->transport_header;
1339 optlen -= sizeof(struct icmp6hdr) + 2 * sizeof(struct in6_addr);
1341 if (optlen < 0) {
1342 ND_PRINTK2(KERN_WARNING
1343 "ICMPv6 Redirect: packet too short\n");
1344 return;
1347 icmph = icmp6_hdr(skb);
1348 target = (struct in6_addr *) (icmph + 1);
1349 dest = target + 1;
1351 if (ipv6_addr_is_multicast(dest)) {
1352 ND_PRINTK2(KERN_WARNING
1353 "ICMPv6 Redirect: destination address is multicast.\n");
1354 return;
1357 if (ipv6_addr_equal(dest, target)) {
1358 on_link = 1;
1359 } else if (ipv6_addr_type(target) !=
1360 (IPV6_ADDR_UNICAST|IPV6_ADDR_LINKLOCAL)) {
1361 ND_PRINTK2(KERN_WARNING
1362 "ICMPv6 Redirect: target address is not link-local unicast.\n");
1363 return;
1366 in6_dev = in6_dev_get(skb->dev);
1367 if (!in6_dev)
1368 return;
1369 if (in6_dev->cnf.forwarding || !in6_dev->cnf.accept_redirects) {
1370 in6_dev_put(in6_dev);
1371 return;
1374 /* RFC2461 8.1:
1375 * The IP source address of the Redirect MUST be the same as the current
1376 * first-hop router for the specified ICMP Destination Address.
1379 if (!ndisc_parse_options((u8*)(dest + 1), optlen, &ndopts)) {
1380 ND_PRINTK2(KERN_WARNING
1381 "ICMPv6 Redirect: invalid ND options\n");
1382 in6_dev_put(in6_dev);
1383 return;
1385 if (ndopts.nd_opts_tgt_lladdr) {
1386 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_tgt_lladdr,
1387 skb->dev);
1388 if (!lladdr) {
1389 ND_PRINTK2(KERN_WARNING
1390 "ICMPv6 Redirect: invalid link-layer address length\n");
1391 in6_dev_put(in6_dev);
1392 return;
1396 neigh = __neigh_lookup(&nd_tbl, target, skb->dev, 1);
1397 if (neigh) {
1398 rt6_redirect(dest, &ipv6_hdr(skb)->daddr,
1399 &ipv6_hdr(skb)->saddr, neigh, lladdr,
1400 on_link);
1401 neigh_release(neigh);
1403 in6_dev_put(in6_dev);
1406 void ndisc_send_redirect(struct sk_buff *skb, struct neighbour *neigh,
1407 struct in6_addr *target)
1409 struct sock *sk = ndisc_socket->sk;
1410 int len = sizeof(struct icmp6hdr) + 2 * sizeof(struct in6_addr);
1411 struct sk_buff *buff;
1412 struct icmp6hdr *icmph;
1413 struct in6_addr saddr_buf;
1414 struct in6_addr *addrp;
1415 struct net_device *dev;
1416 struct rt6_info *rt;
1417 struct dst_entry *dst;
1418 struct inet6_dev *idev;
1419 struct flowi fl;
1420 u8 *opt;
1421 int rd_len;
1422 int err;
1423 int hlen;
1424 u8 ha_buf[MAX_ADDR_LEN], *ha = NULL;
1426 dev = skb->dev;
1428 if (ipv6_get_lladdr(dev, &saddr_buf, IFA_F_TENTATIVE)) {
1429 ND_PRINTK2(KERN_WARNING
1430 "ICMPv6 Redirect: no link-local address on %s\n",
1431 dev->name);
1432 return;
1435 if (!ipv6_addr_equal(&ipv6_hdr(skb)->daddr, target) &&
1436 ipv6_addr_type(target) != (IPV6_ADDR_UNICAST|IPV6_ADDR_LINKLOCAL)) {
1437 ND_PRINTK2(KERN_WARNING
1438 "ICMPv6 Redirect: target address is not link-local unicast.\n");
1439 return;
1442 ndisc_flow_init(&fl, NDISC_REDIRECT, &saddr_buf, &ipv6_hdr(skb)->saddr,
1443 dev->ifindex);
1445 dst = ip6_route_output(NULL, &fl);
1446 if (dst == NULL)
1447 return;
1449 err = xfrm_lookup(&dst, &fl, NULL, 0);
1450 if (err)
1451 return;
1453 rt = (struct rt6_info *) dst;
1455 if (rt->rt6i_flags & RTF_GATEWAY) {
1456 ND_PRINTK2(KERN_WARNING
1457 "ICMPv6 Redirect: destination is not a neighbour.\n");
1458 dst_release(dst);
1459 return;
1461 if (!xrlim_allow(dst, 1*HZ)) {
1462 dst_release(dst);
1463 return;
1466 if (dev->addr_len) {
1467 read_lock_bh(&neigh->lock);
1468 if (neigh->nud_state & NUD_VALID) {
1469 memcpy(ha_buf, neigh->ha, dev->addr_len);
1470 read_unlock_bh(&neigh->lock);
1471 ha = ha_buf;
1472 len += ndisc_opt_addr_space(dev);
1473 } else
1474 read_unlock_bh(&neigh->lock);
1477 rd_len = min_t(unsigned int,
1478 IPV6_MIN_MTU-sizeof(struct ipv6hdr)-len, skb->len + 8);
1479 rd_len &= ~0x7;
1480 len += rd_len;
1482 buff = sock_alloc_send_skb(sk,
1483 (MAX_HEADER + sizeof(struct ipv6hdr) +
1484 len + LL_RESERVED_SPACE(dev)),
1485 1, &err);
1486 if (buff == NULL) {
1487 ND_PRINTK0(KERN_ERR
1488 "ICMPv6 Redirect: %s() failed to allocate an skb.\n",
1489 __FUNCTION__);
1490 dst_release(dst);
1491 return;
1494 hlen = 0;
1496 skb_reserve(buff, LL_RESERVED_SPACE(dev));
1497 ip6_nd_hdr(sk, buff, dev, &saddr_buf, &ipv6_hdr(skb)->saddr,
1498 IPPROTO_ICMPV6, len);
1500 skb_set_transport_header(buff, skb_tail_pointer(buff) - buff->data);
1501 skb_put(buff, len);
1502 icmph = icmp6_hdr(buff);
1504 memset(icmph, 0, sizeof(struct icmp6hdr));
1505 icmph->icmp6_type = NDISC_REDIRECT;
1508 * copy target and destination addresses
1511 addrp = (struct in6_addr *)(icmph + 1);
1512 ipv6_addr_copy(addrp, target);
1513 addrp++;
1514 ipv6_addr_copy(addrp, &ipv6_hdr(skb)->daddr);
1516 opt = (u8*) (addrp + 1);
1519 * include target_address option
1522 if (ha)
1523 opt = ndisc_fill_addr_option(opt, ND_OPT_TARGET_LL_ADDR, ha,
1524 dev->addr_len, dev->type);
1527 * build redirect option and copy skb over to the new packet.
1530 memset(opt, 0, 8);
1531 *(opt++) = ND_OPT_REDIRECT_HDR;
1532 *(opt++) = (rd_len >> 3);
1533 opt += 6;
1535 memcpy(opt, ipv6_hdr(skb), rd_len - 8);
1537 icmph->icmp6_cksum = csum_ipv6_magic(&saddr_buf, &ipv6_hdr(skb)->saddr,
1538 len, IPPROTO_ICMPV6,
1539 csum_partial((u8 *) icmph, len, 0));
1541 buff->dst = dst;
1542 idev = in6_dev_get(dst->dev);
1543 IP6_INC_STATS(idev, IPSTATS_MIB_OUTREQUESTS);
1544 err = NF_HOOK(PF_INET6, NF_INET_LOCAL_OUT, buff, NULL, dst->dev,
1545 dst_output);
1546 if (!err) {
1547 ICMP6MSGOUT_INC_STATS(idev, NDISC_REDIRECT);
1548 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTMSGS);
1551 if (likely(idev != NULL))
1552 in6_dev_put(idev);
1555 static void pndisc_redo(struct sk_buff *skb)
1557 ndisc_recv_ns(skb);
1558 kfree_skb(skb);
1561 int ndisc_rcv(struct sk_buff *skb)
1563 struct nd_msg *msg;
1565 if (!pskb_may_pull(skb, skb->len))
1566 return 0;
1568 msg = (struct nd_msg *)skb_transport_header(skb);
1570 __skb_push(skb, skb->data - skb_transport_header(skb));
1572 if (ipv6_hdr(skb)->hop_limit != 255) {
1573 ND_PRINTK2(KERN_WARNING
1574 "ICMPv6 NDISC: invalid hop-limit: %d\n",
1575 ipv6_hdr(skb)->hop_limit);
1576 return 0;
1579 if (msg->icmph.icmp6_code != 0) {
1580 ND_PRINTK2(KERN_WARNING
1581 "ICMPv6 NDISC: invalid ICMPv6 code: %d\n",
1582 msg->icmph.icmp6_code);
1583 return 0;
1586 memset(NEIGH_CB(skb), 0, sizeof(struct neighbour_cb));
1588 switch (msg->icmph.icmp6_type) {
1589 case NDISC_NEIGHBOUR_SOLICITATION:
1590 ndisc_recv_ns(skb);
1591 break;
1593 case NDISC_NEIGHBOUR_ADVERTISEMENT:
1594 ndisc_recv_na(skb);
1595 break;
1597 case NDISC_ROUTER_SOLICITATION:
1598 ndisc_recv_rs(skb);
1599 break;
1601 case NDISC_ROUTER_ADVERTISEMENT:
1602 ndisc_router_discovery(skb);
1603 break;
1605 case NDISC_REDIRECT:
1606 ndisc_redirect_rcv(skb);
1607 break;
1610 return 0;
1613 static int ndisc_netdev_event(struct notifier_block *this, unsigned long event, void *ptr)
1615 struct net_device *dev = ptr;
1617 if (dev->nd_net != &init_net)
1618 return NOTIFY_DONE;
1620 switch (event) {
1621 case NETDEV_CHANGEADDR:
1622 neigh_changeaddr(&nd_tbl, dev);
1623 fib6_run_gc(~0UL);
1624 break;
1625 case NETDEV_DOWN:
1626 neigh_ifdown(&nd_tbl, dev);
1627 fib6_run_gc(~0UL);
1628 break;
1629 default:
1630 break;
1633 return NOTIFY_DONE;
1636 static struct notifier_block ndisc_netdev_notifier = {
1637 .notifier_call = ndisc_netdev_event,
1640 #ifdef CONFIG_SYSCTL
1641 static void ndisc_warn_deprecated_sysctl(struct ctl_table *ctl,
1642 const char *func, const char *dev_name)
1644 static char warncomm[TASK_COMM_LEN];
1645 static int warned;
1646 if (strcmp(warncomm, current->comm) && warned < 5) {
1647 strcpy(warncomm, current->comm);
1648 printk(KERN_WARNING
1649 "process `%s' is using deprecated sysctl (%s) "
1650 "net.ipv6.neigh.%s.%s; "
1651 "Use net.ipv6.neigh.%s.%s_ms "
1652 "instead.\n",
1653 warncomm, func,
1654 dev_name, ctl->procname,
1655 dev_name, ctl->procname);
1656 warned++;
1660 int ndisc_ifinfo_sysctl_change(struct ctl_table *ctl, int write, struct file * filp, void __user *buffer, size_t *lenp, loff_t *ppos)
1662 struct net_device *dev = ctl->extra1;
1663 struct inet6_dev *idev;
1664 int ret;
1666 if ((strcmp(ctl->procname, "retrans_time") == 0) ||
1667 (strcmp(ctl->procname, "base_reachable_time") == 0))
1668 ndisc_warn_deprecated_sysctl(ctl, "syscall", dev ? dev->name : "default");
1670 if (strcmp(ctl->procname, "retrans_time") == 0)
1671 ret = proc_dointvec(ctl, write, filp, buffer, lenp, ppos);
1673 else if (strcmp(ctl->procname, "base_reachable_time") == 0)
1674 ret = proc_dointvec_jiffies(ctl, write,
1675 filp, buffer, lenp, ppos);
1677 else if ((strcmp(ctl->procname, "retrans_time_ms") == 0) ||
1678 (strcmp(ctl->procname, "base_reachable_time_ms") == 0))
1679 ret = proc_dointvec_ms_jiffies(ctl, write,
1680 filp, buffer, lenp, ppos);
1681 else
1682 ret = -1;
1684 if (write && ret == 0 && dev && (idev = in6_dev_get(dev)) != NULL) {
1685 if (ctl->data == &idev->nd_parms->base_reachable_time)
1686 idev->nd_parms->reachable_time = neigh_rand_reach_time(idev->nd_parms->base_reachable_time);
1687 idev->tstamp = jiffies;
1688 inet6_ifinfo_notify(RTM_NEWLINK, idev);
1689 in6_dev_put(idev);
1691 return ret;
1694 static int ndisc_ifinfo_sysctl_strategy(ctl_table *ctl, int __user *name,
1695 int nlen, void __user *oldval,
1696 size_t __user *oldlenp,
1697 void __user *newval, size_t newlen)
1699 struct net_device *dev = ctl->extra1;
1700 struct inet6_dev *idev;
1701 int ret;
1703 if (ctl->ctl_name == NET_NEIGH_RETRANS_TIME ||
1704 ctl->ctl_name == NET_NEIGH_REACHABLE_TIME)
1705 ndisc_warn_deprecated_sysctl(ctl, "procfs", dev ? dev->name : "default");
1707 switch (ctl->ctl_name) {
1708 case NET_NEIGH_REACHABLE_TIME:
1709 ret = sysctl_jiffies(ctl, name, nlen,
1710 oldval, oldlenp, newval, newlen);
1711 break;
1712 case NET_NEIGH_RETRANS_TIME_MS:
1713 case NET_NEIGH_REACHABLE_TIME_MS:
1714 ret = sysctl_ms_jiffies(ctl, name, nlen,
1715 oldval, oldlenp, newval, newlen);
1716 break;
1717 default:
1718 ret = 0;
1721 if (newval && newlen && ret > 0 &&
1722 dev && (idev = in6_dev_get(dev)) != NULL) {
1723 if (ctl->ctl_name == NET_NEIGH_REACHABLE_TIME ||
1724 ctl->ctl_name == NET_NEIGH_REACHABLE_TIME_MS)
1725 idev->nd_parms->reachable_time = neigh_rand_reach_time(idev->nd_parms->base_reachable_time);
1726 idev->tstamp = jiffies;
1727 inet6_ifinfo_notify(RTM_NEWLINK, idev);
1728 in6_dev_put(idev);
1731 return ret;
1734 #endif
1736 int __init ndisc_init(struct net_proto_family *ops)
1738 struct ipv6_pinfo *np;
1739 struct sock *sk;
1740 int err;
1742 err = sock_create_kern(PF_INET6, SOCK_RAW, IPPROTO_ICMPV6, &ndisc_socket);
1743 if (err < 0) {
1744 ND_PRINTK0(KERN_ERR
1745 "ICMPv6 NDISC: Failed to initialize the control socket (err %d).\n",
1746 err);
1747 ndisc_socket = NULL; /* For safety. */
1748 return err;
1751 sk = ndisc_socket->sk;
1752 np = inet6_sk(sk);
1753 sk->sk_allocation = GFP_ATOMIC;
1754 np->hop_limit = 255;
1755 /* Do not loopback ndisc messages */
1756 np->mc_loop = 0;
1757 sk->sk_prot->unhash(sk);
1760 * Initialize the neighbour table
1763 neigh_table_init(&nd_tbl);
1765 #ifdef CONFIG_SYSCTL
1766 neigh_sysctl_register(NULL, &nd_tbl.parms, NET_IPV6, NET_IPV6_NEIGH,
1767 "ipv6",
1768 &ndisc_ifinfo_sysctl_change,
1769 &ndisc_ifinfo_sysctl_strategy);
1770 #endif
1772 register_netdevice_notifier(&ndisc_netdev_notifier);
1773 return 0;
1776 void ndisc_cleanup(void)
1778 unregister_netdevice_notifier(&ndisc_netdev_notifier);
1779 #ifdef CONFIG_SYSCTL
1780 neigh_sysctl_unregister(&nd_tbl.parms);
1781 #endif
1782 neigh_table_clear(&nd_tbl);
1783 sock_release(ndisc_socket);
1784 ndisc_socket = NULL; /* For safety. */