2 * Neighbour Discovery for IPv6
3 * Linux INET6 implementation
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.
18 * Lars Fenneberg : fixed MTU setting on receipt
21 * Janos Farkas : kmalloc failure checks
22 * Alexey Kuznetsov : state machine reworked
23 * and moved to net/core.
24 * Pekka Savola : RFC2461 validation
25 * YOSHIFUJI Hideaki @USAGI : Verify ND options properly
28 /* Set to 3 to get tracing... */
31 #define ND_PRINTK(fmt, args...) do { if (net_ratelimit()) { printk(fmt, ## args); } } while(0)
32 #define ND_NOPRINTK(x...) do { ; } while(0)
33 #define ND_PRINTK0 ND_PRINTK
34 #define ND_PRINTK1 ND_NOPRINTK
35 #define ND_PRINTK2 ND_NOPRINTK
36 #define ND_PRINTK3 ND_NOPRINTK
39 #define ND_PRINTK1 ND_PRINTK
43 #define ND_PRINTK2 ND_PRINTK
47 #define ND_PRINTK3 ND_PRINTK
50 #include <linux/module.h>
51 #include <linux/errno.h>
52 #include <linux/types.h>
53 #include <linux/socket.h>
54 #include <linux/sockios.h>
55 #include <linux/sched.h>
56 #include <linux/net.h>
57 #include <linux/in6.h>
58 #include <linux/route.h>
59 #include <linux/init.h>
60 #include <linux/rcupdate.h>
62 #include <linux/sysctl.h>
65 #include <linux/if_addr.h>
66 #include <linux/if_arp.h>
67 #include <linux/ipv6.h>
68 #include <linux/icmpv6.h>
69 #include <linux/jhash.h>
75 #include <net/protocol.h>
76 #include <net/ndisc.h>
77 #include <net/ip6_route.h>
78 #include <net/addrconf.h>
82 #include <net/ip6_checksum.h>
83 #include <linux/proc_fs.h>
85 #include <linux/netfilter.h>
86 #include <linux/netfilter_ipv6.h>
88 static struct socket *ndisc_socket;
90 static u32 ndisc_hash(const void *pkey, const struct net_device *dev);
91 static int ndisc_constructor(struct neighbour *neigh);
92 static void ndisc_solicit(struct neighbour *neigh, struct sk_buff *skb);
93 static void ndisc_error_report(struct neighbour *neigh, struct sk_buff *skb);
94 static int pndisc_constructor(struct pneigh_entry *n);
95 static void pndisc_destructor(struct pneigh_entry *n);
96 static void pndisc_redo(struct sk_buff *skb);
98 static struct neigh_ops ndisc_generic_ops = {
100 .solicit = ndisc_solicit,
101 .error_report = ndisc_error_report,
102 .output = neigh_resolve_output,
103 .connected_output = neigh_connected_output,
104 .hh_output = dev_queue_xmit,
105 .queue_xmit = dev_queue_xmit,
108 static struct neigh_ops ndisc_hh_ops = {
110 .solicit = ndisc_solicit,
111 .error_report = ndisc_error_report,
112 .output = neigh_resolve_output,
113 .connected_output = neigh_resolve_output,
114 .hh_output = dev_queue_xmit,
115 .queue_xmit = dev_queue_xmit,
119 static struct neigh_ops ndisc_direct_ops = {
121 .output = dev_queue_xmit,
122 .connected_output = dev_queue_xmit,
123 .hh_output = dev_queue_xmit,
124 .queue_xmit = dev_queue_xmit,
127 struct neigh_table nd_tbl = {
129 .entry_size = sizeof(struct neighbour) + sizeof(struct in6_addr),
130 .key_len = sizeof(struct in6_addr),
132 .constructor = ndisc_constructor,
133 .pconstructor = pndisc_constructor,
134 .pdestructor = pndisc_destructor,
135 .proxy_redo = pndisc_redo,
139 .base_reachable_time = 30 * HZ,
140 .retrans_time = 1 * HZ,
141 .gc_staletime = 60 * HZ,
142 .reachable_time = 30 * HZ,
143 .delay_probe_time = 5 * HZ,
147 .anycast_delay = 1 * HZ,
148 .proxy_delay = (8 * HZ) / 10,
151 .gc_interval = 30 * HZ,
158 struct ndisc_options {
159 struct nd_opt_hdr *nd_opt_array[__ND_OPT_ARRAY_MAX];
160 #ifdef CONFIG_IPV6_ROUTE_INFO
161 struct nd_opt_hdr *nd_opts_ri;
162 struct nd_opt_hdr *nd_opts_ri_end;
166 #define nd_opts_src_lladdr nd_opt_array[ND_OPT_SOURCE_LL_ADDR]
167 #define nd_opts_tgt_lladdr nd_opt_array[ND_OPT_TARGET_LL_ADDR]
168 #define nd_opts_pi nd_opt_array[ND_OPT_PREFIX_INFO]
169 #define nd_opts_pi_end nd_opt_array[__ND_OPT_PREFIX_INFO_END]
170 #define nd_opts_rh nd_opt_array[ND_OPT_REDIRECT_HDR]
171 #define nd_opts_mtu nd_opt_array[ND_OPT_MTU]
173 #define NDISC_OPT_SPACE(len) (((len)+2+7)&~7)
176 * Return the padding between the option length and the start of the
177 * link addr. Currently only IP-over-InfiniBand needs this, although
178 * if RFC 3831 IPv6-over-Fibre Channel is ever implemented it may
179 * also need a pad of 2.
181 static int ndisc_addr_option_pad(unsigned short type)
184 case ARPHRD_INFINIBAND: return 2;
189 static inline int ndisc_opt_addr_space(struct net_device *dev)
191 return NDISC_OPT_SPACE(dev->addr_len + ndisc_addr_option_pad(dev->type));
194 static u8 *ndisc_fill_addr_option(u8 *opt, int type, void *data, int data_len,
195 unsigned short addr_type)
197 int space = NDISC_OPT_SPACE(data_len);
198 int pad = ndisc_addr_option_pad(addr_type);
203 memset(opt + 2, 0, pad);
207 memcpy(opt+2, data, data_len);
210 if ((space -= data_len) > 0)
211 memset(opt, 0, space);
215 static struct nd_opt_hdr *ndisc_next_option(struct nd_opt_hdr *cur,
216 struct nd_opt_hdr *end)
219 if (!cur || !end || cur >= end)
221 type = cur->nd_opt_type;
223 cur = ((void *)cur) + (cur->nd_opt_len << 3);
224 } while(cur < end && cur->nd_opt_type != type);
225 return (cur <= end && cur->nd_opt_type == type ? cur : NULL);
228 static struct ndisc_options *ndisc_parse_options(u8 *opt, int opt_len,
229 struct ndisc_options *ndopts)
231 struct nd_opt_hdr *nd_opt = (struct nd_opt_hdr *)opt;
233 if (!nd_opt || opt_len < 0 || !ndopts)
235 memset(ndopts, 0, sizeof(*ndopts));
238 if (opt_len < sizeof(struct nd_opt_hdr))
240 l = nd_opt->nd_opt_len << 3;
241 if (opt_len < l || l == 0)
243 switch (nd_opt->nd_opt_type) {
244 case ND_OPT_SOURCE_LL_ADDR:
245 case ND_OPT_TARGET_LL_ADDR:
247 case ND_OPT_REDIRECT_HDR:
248 if (ndopts->nd_opt_array[nd_opt->nd_opt_type]) {
249 ND_PRINTK2(KERN_WARNING
250 "%s(): duplicated ND6 option found: type=%d\n",
252 nd_opt->nd_opt_type);
254 ndopts->nd_opt_array[nd_opt->nd_opt_type] = nd_opt;
257 case ND_OPT_PREFIX_INFO:
258 ndopts->nd_opts_pi_end = nd_opt;
259 if (ndopts->nd_opt_array[nd_opt->nd_opt_type] == 0)
260 ndopts->nd_opt_array[nd_opt->nd_opt_type] = nd_opt;
262 #ifdef CONFIG_IPV6_ROUTE_INFO
263 case ND_OPT_ROUTE_INFO:
264 ndopts->nd_opts_ri_end = nd_opt;
265 if (!ndopts->nd_opts_ri)
266 ndopts->nd_opts_ri = nd_opt;
271 * Unknown options must be silently ignored,
272 * to accommodate future extension to the protocol.
274 ND_PRINTK2(KERN_NOTICE
275 "%s(): ignored unsupported option; type=%d, len=%d\n",
277 nd_opt->nd_opt_type, nd_opt->nd_opt_len);
280 nd_opt = ((void *)nd_opt) + l;
285 static inline u8 *ndisc_opt_addr_data(struct nd_opt_hdr *p,
286 struct net_device *dev)
288 u8 *lladdr = (u8 *)(p + 1);
289 int lladdrlen = p->nd_opt_len << 3;
290 int prepad = ndisc_addr_option_pad(dev->type);
291 if (lladdrlen != NDISC_OPT_SPACE(dev->addr_len + prepad))
293 return (lladdr + prepad);
296 int ndisc_mc_map(struct in6_addr *addr, char *buf, struct net_device *dev, int dir)
300 case ARPHRD_IEEE802: /* Not sure. Check it later. --ANK */
302 ipv6_eth_mc_map(addr, buf);
304 case ARPHRD_IEEE802_TR:
305 ipv6_tr_mc_map(addr,buf);
308 ipv6_arcnet_mc_map(addr, buf);
310 case ARPHRD_INFINIBAND:
311 ipv6_ib_mc_map(addr, buf);
315 memcpy(buf, dev->broadcast, dev->addr_len);
322 static u32 ndisc_hash(const void *pkey, const struct net_device *dev)
324 const u32 *p32 = pkey;
328 for (i = 0; i < (sizeof(struct in6_addr) / sizeof(u32)); i++)
331 return jhash_2words(addr_hash, dev->ifindex, nd_tbl.hash_rnd);
334 static int ndisc_constructor(struct neighbour *neigh)
336 struct in6_addr *addr = (struct in6_addr*)&neigh->primary_key;
337 struct net_device *dev = neigh->dev;
338 struct inet6_dev *in6_dev;
339 struct neigh_parms *parms;
340 int is_multicast = ipv6_addr_is_multicast(addr);
343 in6_dev = in6_dev_get(dev);
344 if (in6_dev == NULL) {
349 parms = in6_dev->nd_parms;
350 __neigh_parms_put(neigh->parms);
351 neigh->parms = neigh_parms_clone(parms);
354 neigh->type = is_multicast ? RTN_MULTICAST : RTN_UNICAST;
355 if (dev->hard_header == NULL) {
356 neigh->nud_state = NUD_NOARP;
357 neigh->ops = &ndisc_direct_ops;
358 neigh->output = neigh->ops->queue_xmit;
361 neigh->nud_state = NUD_NOARP;
362 ndisc_mc_map(addr, neigh->ha, dev, 1);
363 } else if (dev->flags&(IFF_NOARP|IFF_LOOPBACK)) {
364 neigh->nud_state = NUD_NOARP;
365 memcpy(neigh->ha, dev->dev_addr, dev->addr_len);
366 if (dev->flags&IFF_LOOPBACK)
367 neigh->type = RTN_LOCAL;
368 } else if (dev->flags&IFF_POINTOPOINT) {
369 neigh->nud_state = NUD_NOARP;
370 memcpy(neigh->ha, dev->broadcast, dev->addr_len);
372 if (dev->hard_header_cache)
373 neigh->ops = &ndisc_hh_ops;
375 neigh->ops = &ndisc_generic_ops;
376 if (neigh->nud_state&NUD_VALID)
377 neigh->output = neigh->ops->connected_output;
379 neigh->output = neigh->ops->output;
381 in6_dev_put(in6_dev);
385 static int pndisc_constructor(struct pneigh_entry *n)
387 struct in6_addr *addr = (struct in6_addr*)&n->key;
388 struct in6_addr maddr;
389 struct net_device *dev = n->dev;
391 if (dev == NULL || __in6_dev_get(dev) == NULL)
393 addrconf_addr_solict_mult(addr, &maddr);
394 ipv6_dev_mc_inc(dev, &maddr);
398 static void pndisc_destructor(struct pneigh_entry *n)
400 struct in6_addr *addr = (struct in6_addr*)&n->key;
401 struct in6_addr maddr;
402 struct net_device *dev = n->dev;
404 if (dev == NULL || __in6_dev_get(dev) == NULL)
406 addrconf_addr_solict_mult(addr, &maddr);
407 ipv6_dev_mc_dec(dev, &maddr);
411 * Send a Neighbour Advertisement
414 static inline void ndisc_flow_init(struct flowi *fl, u8 type,
415 struct in6_addr *saddr, struct in6_addr *daddr)
417 memset(fl, 0, sizeof(*fl));
418 ipv6_addr_copy(&fl->fl6_src, saddr);
419 ipv6_addr_copy(&fl->fl6_dst, daddr);
420 fl->proto = IPPROTO_ICMPV6;
421 fl->fl_icmp_type = type;
422 fl->fl_icmp_code = 0;
423 security_sk_classify_flow(ndisc_socket->sk, fl);
426 static void ndisc_send_na(struct net_device *dev, struct neighbour *neigh,
427 struct in6_addr *daddr, struct in6_addr *solicited_addr,
428 int router, int solicited, int override, int inc_opt)
430 struct in6_addr tmpaddr;
431 struct inet6_ifaddr *ifp;
432 struct inet6_dev *idev;
434 struct dst_entry* dst;
435 struct sock *sk = ndisc_socket->sk;
436 struct in6_addr *src_addr;
442 len = sizeof(struct icmp6hdr) + sizeof(struct in6_addr);
444 /* for anycast or proxy, solicited_addr != src_addr */
445 ifp = ipv6_get_ifaddr(solicited_addr, dev, 1);
447 src_addr = solicited_addr;
450 if (ipv6_dev_get_saddr(dev, daddr, &tmpaddr))
455 ndisc_flow_init(&fl, NDISC_NEIGHBOUR_ADVERTISEMENT, src_addr, daddr);
457 dst = ndisc_dst_alloc(dev, neigh, daddr, ip6_output);
461 err = xfrm_lookup(&dst, &fl, NULL, 0);
467 len += ndisc_opt_addr_space(dev);
472 skb = sock_alloc_send_skb(sk, MAX_HEADER + len + LL_RESERVED_SPACE(dev),
477 "ICMPv6 NA: %s() failed to allocate an skb.\n",
483 skb_reserve(skb, LL_RESERVED_SPACE(dev));
484 ip6_nd_hdr(sk, skb, dev, src_addr, daddr, IPPROTO_ICMPV6, len);
486 msg = (struct nd_msg *)skb_put(skb, len);
487 skb->h.raw = (unsigned char*)msg;
489 msg->icmph.icmp6_type = NDISC_NEIGHBOUR_ADVERTISEMENT;
490 msg->icmph.icmp6_code = 0;
491 msg->icmph.icmp6_cksum = 0;
493 msg->icmph.icmp6_unused = 0;
494 msg->icmph.icmp6_router = router;
495 msg->icmph.icmp6_solicited = solicited;
496 msg->icmph.icmp6_override = !!override;
498 /* Set the target address. */
499 ipv6_addr_copy(&msg->target, solicited_addr);
502 ndisc_fill_addr_option(msg->opt, ND_OPT_TARGET_LL_ADDR, dev->dev_addr,
503 dev->addr_len, dev->type);
506 msg->icmph.icmp6_cksum = csum_ipv6_magic(src_addr, daddr, len,
508 csum_partial((__u8 *) msg,
512 idev = in6_dev_get(dst->dev);
513 IP6_INC_STATS(IPSTATS_MIB_OUTREQUESTS);
514 err = NF_HOOK(PF_INET6, NF_IP6_LOCAL_OUT, skb, NULL, dst->dev, dst_output);
516 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTNEIGHBORADVERTISEMENTS);
517 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTMSGS);
520 if (likely(idev != NULL))
524 void ndisc_send_ns(struct net_device *dev, struct neighbour *neigh,
525 struct in6_addr *solicit,
526 struct in6_addr *daddr, struct in6_addr *saddr)
529 struct dst_entry* dst;
530 struct inet6_dev *idev;
531 struct sock *sk = ndisc_socket->sk;
534 struct in6_addr addr_buf;
540 if (ipv6_get_lladdr(dev, &addr_buf))
545 ndisc_flow_init(&fl, NDISC_NEIGHBOUR_SOLICITATION, saddr, daddr);
547 dst = ndisc_dst_alloc(dev, neigh, daddr, ip6_output);
551 err = xfrm_lookup(&dst, &fl, NULL, 0);
555 len = sizeof(struct icmp6hdr) + sizeof(struct in6_addr);
556 send_llinfo = dev->addr_len && !ipv6_addr_any(saddr);
558 len += ndisc_opt_addr_space(dev);
560 skb = sock_alloc_send_skb(sk, MAX_HEADER + len + LL_RESERVED_SPACE(dev),
564 "ICMPv6 NA: %s() failed to allocate an skb.\n",
570 skb_reserve(skb, LL_RESERVED_SPACE(dev));
571 ip6_nd_hdr(sk, skb, dev, saddr, daddr, IPPROTO_ICMPV6, len);
573 msg = (struct nd_msg *)skb_put(skb, len);
574 skb->h.raw = (unsigned char*)msg;
575 msg->icmph.icmp6_type = NDISC_NEIGHBOUR_SOLICITATION;
576 msg->icmph.icmp6_code = 0;
577 msg->icmph.icmp6_cksum = 0;
578 msg->icmph.icmp6_unused = 0;
580 /* Set the target address. */
581 ipv6_addr_copy(&msg->target, solicit);
584 ndisc_fill_addr_option(msg->opt, ND_OPT_SOURCE_LL_ADDR, dev->dev_addr,
585 dev->addr_len, dev->type);
588 msg->icmph.icmp6_cksum = csum_ipv6_magic(&skb->nh.ipv6h->saddr,
591 csum_partial((__u8 *) msg,
595 idev = in6_dev_get(dst->dev);
596 IP6_INC_STATS(IPSTATS_MIB_OUTREQUESTS);
597 err = NF_HOOK(PF_INET6, NF_IP6_LOCAL_OUT, skb, NULL, dst->dev, dst_output);
599 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTNEIGHBORSOLICITS);
600 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTMSGS);
603 if (likely(idev != NULL))
607 void ndisc_send_rs(struct net_device *dev, struct in6_addr *saddr,
608 struct in6_addr *daddr)
611 struct dst_entry* dst;
612 struct inet6_dev *idev;
613 struct sock *sk = ndisc_socket->sk;
615 struct icmp6hdr *hdr;
620 ndisc_flow_init(&fl, NDISC_ROUTER_SOLICITATION, saddr, daddr);
622 dst = ndisc_dst_alloc(dev, NULL, daddr, ip6_output);
626 err = xfrm_lookup(&dst, &fl, NULL, 0);
630 len = sizeof(struct icmp6hdr);
632 len += ndisc_opt_addr_space(dev);
634 skb = sock_alloc_send_skb(sk, MAX_HEADER + len + LL_RESERVED_SPACE(dev),
638 "ICMPv6 RS: %s() failed to allocate an skb.\n",
644 skb_reserve(skb, LL_RESERVED_SPACE(dev));
645 ip6_nd_hdr(sk, skb, dev, saddr, daddr, IPPROTO_ICMPV6, len);
647 hdr = (struct icmp6hdr *)skb_put(skb, len);
648 skb->h.raw = (unsigned char*)hdr;
649 hdr->icmp6_type = NDISC_ROUTER_SOLICITATION;
651 hdr->icmp6_cksum = 0;
652 hdr->icmp6_unused = 0;
654 opt = (u8*) (hdr + 1);
657 ndisc_fill_addr_option(opt, ND_OPT_SOURCE_LL_ADDR, dev->dev_addr,
658 dev->addr_len, dev->type);
661 hdr->icmp6_cksum = csum_ipv6_magic(&skb->nh.ipv6h->saddr, daddr, len,
663 csum_partial((__u8 *) hdr, len, 0));
667 idev = in6_dev_get(dst->dev);
668 IP6_INC_STATS(IPSTATS_MIB_OUTREQUESTS);
669 err = NF_HOOK(PF_INET6, NF_IP6_LOCAL_OUT, skb, NULL, dst->dev, dst_output);
671 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTROUTERSOLICITS);
672 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTMSGS);
675 if (likely(idev != NULL))
680 static void ndisc_error_report(struct neighbour *neigh, struct sk_buff *skb)
683 * "The sender MUST return an ICMP
684 * destination unreachable"
686 dst_link_failure(skb);
690 /* Called with locked neigh: either read or both */
692 static void ndisc_solicit(struct neighbour *neigh, struct sk_buff *skb)
694 struct in6_addr *saddr = NULL;
695 struct in6_addr mcaddr;
696 struct net_device *dev = neigh->dev;
697 struct in6_addr *target = (struct in6_addr *)&neigh->primary_key;
698 int probes = atomic_read(&neigh->probes);
700 if (skb && ipv6_chk_addr(&skb->nh.ipv6h->saddr, dev, 1))
701 saddr = &skb->nh.ipv6h->saddr;
703 if ((probes -= neigh->parms->ucast_probes) < 0) {
704 if (!(neigh->nud_state & NUD_VALID)) {
705 ND_PRINTK1(KERN_DEBUG
706 "%s(): trying to ucast probe in NUD_INVALID: "
711 ndisc_send_ns(dev, neigh, target, target, saddr);
712 } else if ((probes -= neigh->parms->app_probes) < 0) {
717 addrconf_addr_solict_mult(target, &mcaddr);
718 ndisc_send_ns(dev, NULL, target, &mcaddr, saddr);
722 static void ndisc_recv_ns(struct sk_buff *skb)
724 struct nd_msg *msg = (struct nd_msg *)skb->h.raw;
725 struct in6_addr *saddr = &skb->nh.ipv6h->saddr;
726 struct in6_addr *daddr = &skb->nh.ipv6h->daddr;
728 u32 ndoptlen = skb->tail - msg->opt;
729 struct ndisc_options ndopts;
730 struct net_device *dev = skb->dev;
731 struct inet6_ifaddr *ifp;
732 struct inet6_dev *idev = NULL;
733 struct neighbour *neigh;
734 int dad = ipv6_addr_any(saddr);
737 if (ipv6_addr_is_multicast(&msg->target)) {
738 ND_PRINTK2(KERN_WARNING
739 "ICMPv6 NS: multicast target address");
745 * DAD has to be destined for solicited node multicast address.
748 !(daddr->s6_addr32[0] == htonl(0xff020000) &&
749 daddr->s6_addr32[1] == htonl(0x00000000) &&
750 daddr->s6_addr32[2] == htonl(0x00000001) &&
751 daddr->s6_addr [12] == 0xff )) {
752 ND_PRINTK2(KERN_WARNING
753 "ICMPv6 NS: bad DAD packet (wrong destination)\n");
757 if (!ndisc_parse_options(msg->opt, ndoptlen, &ndopts)) {
758 ND_PRINTK2(KERN_WARNING
759 "ICMPv6 NS: invalid ND options\n");
763 if (ndopts.nd_opts_src_lladdr) {
764 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_src_lladdr, dev);
766 ND_PRINTK2(KERN_WARNING
767 "ICMPv6 NS: invalid link-layer address length\n");
772 * If the IP source address is the unspecified address,
773 * there MUST NOT be source link-layer address option
777 ND_PRINTK2(KERN_WARNING
778 "ICMPv6 NS: bad DAD packet (link-layer address option)\n");
783 inc = ipv6_addr_is_multicast(daddr);
785 if ((ifp = ipv6_get_ifaddr(&msg->target, dev, 1)) != NULL) {
786 if (ifp->flags & IFA_F_TENTATIVE) {
787 /* Address is tentative. If the source
788 is unspecified address, it is someone
789 does DAD, otherwise we ignore solicitations
790 until DAD timer expires.
794 if (dev->type == ARPHRD_IEEE802_TR) {
795 unsigned char *sadr = skb->mac.raw;
796 if (((sadr[8] ^ dev->dev_addr[0]) & 0x7f) == 0 &&
797 sadr[9] == dev->dev_addr[1] &&
798 sadr[10] == dev->dev_addr[2] &&
799 sadr[11] == dev->dev_addr[3] &&
800 sadr[12] == dev->dev_addr[4] &&
801 sadr[13] == dev->dev_addr[5]) {
802 /* looped-back to us */
806 addrconf_dad_failure(ifp);
812 idev = in6_dev_get(dev);
814 /* XXX: count this drop? */
818 if (ipv6_chk_acast_addr(dev, &msg->target) ||
819 (idev->cnf.forwarding &&
820 pneigh_lookup(&nd_tbl, &msg->target, dev, 0))) {
821 if (!(NEIGH_CB(skb)->flags & LOCALLY_ENQUEUED) &&
822 skb->pkt_type != PACKET_HOST &&
824 idev->nd_parms->proxy_delay != 0) {
826 * for anycast or proxy,
827 * sender should delay its response
828 * by a random time between 0 and
829 * MAX_ANYCAST_DELAY_TIME seconds.
830 * (RFC2461) -- yoshfuji
832 struct sk_buff *n = skb_clone(skb, GFP_ATOMIC);
834 pneigh_enqueue(&nd_tbl, idev->nd_parms, n);
842 struct in6_addr maddr;
844 ipv6_addr_all_nodes(&maddr);
845 ndisc_send_na(dev, NULL, &maddr, &msg->target,
846 idev->cnf.forwarding, 0, (ifp != NULL), 1);
851 NEIGH_CACHE_STAT_INC(&nd_tbl, rcv_probes_mcast);
853 NEIGH_CACHE_STAT_INC(&nd_tbl, rcv_probes_ucast);
856 * update / create cache entry
857 * for the source address
859 neigh = __neigh_lookup(&nd_tbl, saddr, dev,
860 !inc || lladdr || !dev->addr_len);
862 neigh_update(neigh, lladdr, NUD_STALE,
863 NEIGH_UPDATE_F_WEAK_OVERRIDE|
864 NEIGH_UPDATE_F_OVERRIDE);
865 if (neigh || !dev->hard_header) {
866 ndisc_send_na(dev, neigh, saddr, &msg->target,
867 idev->cnf.forwarding,
868 1, (ifp != NULL && inc), inc);
870 neigh_release(neigh);
882 static void ndisc_recv_na(struct sk_buff *skb)
884 struct nd_msg *msg = (struct nd_msg *)skb->h.raw;
885 struct in6_addr *saddr = &skb->nh.ipv6h->saddr;
886 struct in6_addr *daddr = &skb->nh.ipv6h->daddr;
888 u32 ndoptlen = skb->tail - msg->opt;
889 struct ndisc_options ndopts;
890 struct net_device *dev = skb->dev;
891 struct inet6_ifaddr *ifp;
892 struct neighbour *neigh;
894 if (skb->len < sizeof(struct nd_msg)) {
895 ND_PRINTK2(KERN_WARNING
896 "ICMPv6 NA: packet too short\n");
900 if (ipv6_addr_is_multicast(&msg->target)) {
901 ND_PRINTK2(KERN_WARNING
902 "ICMPv6 NA: target address is multicast.\n");
906 if (ipv6_addr_is_multicast(daddr) &&
907 msg->icmph.icmp6_solicited) {
908 ND_PRINTK2(KERN_WARNING
909 "ICMPv6 NA: solicited NA is multicasted.\n");
913 if (!ndisc_parse_options(msg->opt, ndoptlen, &ndopts)) {
914 ND_PRINTK2(KERN_WARNING
915 "ICMPv6 NS: invalid ND option\n");
918 if (ndopts.nd_opts_tgt_lladdr) {
919 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_tgt_lladdr, dev);
921 ND_PRINTK2(KERN_WARNING
922 "ICMPv6 NA: invalid link-layer address length\n");
926 if ((ifp = ipv6_get_ifaddr(&msg->target, dev, 1))) {
927 if (ifp->flags & IFA_F_TENTATIVE) {
928 addrconf_dad_failure(ifp);
931 /* What should we make now? The advertisement
932 is invalid, but ndisc specs say nothing
933 about it. It could be misconfiguration, or
934 an smart proxy agent tries to help us :-)
936 ND_PRINTK1(KERN_WARNING
937 "ICMPv6 NA: someone advertises our address on %s!\n",
938 ifp->idev->dev->name);
942 neigh = neigh_lookup(&nd_tbl, &msg->target, dev);
945 u8 old_flags = neigh->flags;
947 if (neigh->nud_state & NUD_FAILED)
950 neigh_update(neigh, lladdr,
951 msg->icmph.icmp6_solicited ? NUD_REACHABLE : NUD_STALE,
952 NEIGH_UPDATE_F_WEAK_OVERRIDE|
953 (msg->icmph.icmp6_override ? NEIGH_UPDATE_F_OVERRIDE : 0)|
954 NEIGH_UPDATE_F_OVERRIDE_ISROUTER|
955 (msg->icmph.icmp6_router ? NEIGH_UPDATE_F_ISROUTER : 0));
957 if ((old_flags & ~neigh->flags) & NTF_ROUTER) {
959 * Change: router to host
962 rt = rt6_get_dflt_router(saddr, dev);
968 neigh_release(neigh);
972 static void ndisc_recv_rs(struct sk_buff *skb)
974 struct rs_msg *rs_msg = (struct rs_msg *) skb->h.raw;
975 unsigned long ndoptlen = skb->len - sizeof(*rs_msg);
976 struct neighbour *neigh;
977 struct inet6_dev *idev;
978 struct in6_addr *saddr = &skb->nh.ipv6h->saddr;
979 struct ndisc_options ndopts;
982 if (skb->len < sizeof(*rs_msg))
985 idev = in6_dev_get(skb->dev);
988 ND_PRINTK1("ICMP6 RS: can't find in6 device\n");
992 /* Don't accept RS if we're not in router mode */
993 if (!idev->cnf.forwarding)
997 * Don't update NCE if src = ::;
998 * this implies that the source node has no ip address assigned yet.
1000 if (ipv6_addr_any(saddr))
1003 /* Parse ND options */
1004 if (!ndisc_parse_options(rs_msg->opt, ndoptlen, &ndopts)) {
1005 if (net_ratelimit())
1006 ND_PRINTK2("ICMP6 NS: invalid ND option, ignored\n");
1010 if (ndopts.nd_opts_src_lladdr) {
1011 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_src_lladdr,
1017 neigh = __neigh_lookup(&nd_tbl, saddr, skb->dev, 1);
1019 neigh_update(neigh, lladdr, NUD_STALE,
1020 NEIGH_UPDATE_F_WEAK_OVERRIDE|
1021 NEIGH_UPDATE_F_OVERRIDE|
1022 NEIGH_UPDATE_F_OVERRIDE_ISROUTER);
1023 neigh_release(neigh);
1029 static void ndisc_router_discovery(struct sk_buff *skb)
1031 struct ra_msg *ra_msg = (struct ra_msg *) skb->h.raw;
1032 struct neighbour *neigh = NULL;
1033 struct inet6_dev *in6_dev;
1034 struct rt6_info *rt = NULL;
1036 struct ndisc_options ndopts;
1038 unsigned int pref = 0;
1040 __u8 * opt = (__u8 *)(ra_msg + 1);
1042 optlen = (skb->tail - skb->h.raw) - sizeof(struct ra_msg);
1044 if (!(ipv6_addr_type(&skb->nh.ipv6h->saddr) & IPV6_ADDR_LINKLOCAL)) {
1045 ND_PRINTK2(KERN_WARNING
1046 "ICMPv6 RA: source address is not link-local.\n");
1050 ND_PRINTK2(KERN_WARNING
1051 "ICMPv6 RA: packet too short\n");
1056 * set the RA_RECV flag in the interface
1059 in6_dev = in6_dev_get(skb->dev);
1060 if (in6_dev == NULL) {
1062 "ICMPv6 RA: can't find inet6 device for %s.\n",
1066 if (in6_dev->cnf.forwarding || !in6_dev->cnf.accept_ra) {
1067 in6_dev_put(in6_dev);
1071 if (!ndisc_parse_options(opt, optlen, &ndopts)) {
1072 in6_dev_put(in6_dev);
1073 ND_PRINTK2(KERN_WARNING
1074 "ICMP6 RA: invalid ND options\n");
1078 if (in6_dev->if_flags & IF_RS_SENT) {
1080 * flag that an RA was received after an RS was sent
1081 * out on this interface.
1083 in6_dev->if_flags |= IF_RA_RCVD;
1087 * Remember the managed/otherconf flags from most recently
1088 * received RA message (RFC 2462) -- yoshfuji
1090 in6_dev->if_flags = (in6_dev->if_flags & ~(IF_RA_MANAGED |
1092 (ra_msg->icmph.icmp6_addrconf_managed ?
1093 IF_RA_MANAGED : 0) |
1094 (ra_msg->icmph.icmp6_addrconf_other ?
1095 IF_RA_OTHERCONF : 0);
1097 if (!in6_dev->cnf.accept_ra_defrtr)
1100 lifetime = ntohs(ra_msg->icmph.icmp6_rt_lifetime);
1102 #ifdef CONFIG_IPV6_ROUTER_PREF
1103 pref = ra_msg->icmph.icmp6_router_pref;
1104 /* 10b is handled as if it were 00b (medium) */
1105 if (pref == ICMPV6_ROUTER_PREF_INVALID ||
1106 in6_dev->cnf.accept_ra_rtr_pref)
1107 pref = ICMPV6_ROUTER_PREF_MEDIUM;
1110 rt = rt6_get_dflt_router(&skb->nh.ipv6h->saddr, skb->dev);
1113 neigh = rt->rt6i_nexthop;
1115 if (rt && lifetime == 0) {
1121 if (rt == NULL && lifetime) {
1122 ND_PRINTK3(KERN_DEBUG
1123 "ICMPv6 RA: adding default router.\n");
1125 rt = rt6_add_dflt_router(&skb->nh.ipv6h->saddr, skb->dev, pref);
1128 "ICMPv6 RA: %s() failed to add default route.\n",
1130 in6_dev_put(in6_dev);
1134 neigh = rt->rt6i_nexthop;
1135 if (neigh == NULL) {
1137 "ICMPv6 RA: %s() got default router without neighbour.\n",
1139 dst_release(&rt->u.dst);
1140 in6_dev_put(in6_dev);
1143 neigh->flags |= NTF_ROUTER;
1145 rt->rt6i_flags |= (rt->rt6i_flags & ~RTF_PREF_MASK) | RTF_PREF(pref);
1149 rt->rt6i_expires = jiffies + (HZ * lifetime);
1151 if (ra_msg->icmph.icmp6_hop_limit) {
1152 in6_dev->cnf.hop_limit = ra_msg->icmph.icmp6_hop_limit;
1154 rt->u.dst.metrics[RTAX_HOPLIMIT-1] = ra_msg->icmph.icmp6_hop_limit;
1160 * Update Reachable Time and Retrans Timer
1163 if (in6_dev->nd_parms) {
1164 unsigned long rtime = ntohl(ra_msg->retrans_timer);
1166 if (rtime && rtime/1000 < MAX_SCHEDULE_TIMEOUT/HZ) {
1167 rtime = (rtime*HZ)/1000;
1170 in6_dev->nd_parms->retrans_time = rtime;
1171 in6_dev->tstamp = jiffies;
1172 inet6_ifinfo_notify(RTM_NEWLINK, in6_dev);
1175 rtime = ntohl(ra_msg->reachable_time);
1176 if (rtime && rtime/1000 < MAX_SCHEDULE_TIMEOUT/(3*HZ)) {
1177 rtime = (rtime*HZ)/1000;
1182 if (rtime != in6_dev->nd_parms->base_reachable_time) {
1183 in6_dev->nd_parms->base_reachable_time = rtime;
1184 in6_dev->nd_parms->gc_staletime = 3 * rtime;
1185 in6_dev->nd_parms->reachable_time = neigh_rand_reach_time(rtime);
1186 in6_dev->tstamp = jiffies;
1187 inet6_ifinfo_notify(RTM_NEWLINK, in6_dev);
1197 neigh = __neigh_lookup(&nd_tbl, &skb->nh.ipv6h->saddr,
1201 if (ndopts.nd_opts_src_lladdr) {
1202 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_src_lladdr,
1205 ND_PRINTK2(KERN_WARNING
1206 "ICMPv6 RA: invalid link-layer address length\n");
1210 neigh_update(neigh, lladdr, NUD_STALE,
1211 NEIGH_UPDATE_F_WEAK_OVERRIDE|
1212 NEIGH_UPDATE_F_OVERRIDE|
1213 NEIGH_UPDATE_F_OVERRIDE_ISROUTER|
1214 NEIGH_UPDATE_F_ISROUTER);
1217 #ifdef CONFIG_IPV6_ROUTE_INFO
1218 if (in6_dev->cnf.accept_ra_rtr_pref && ndopts.nd_opts_ri) {
1219 struct nd_opt_hdr *p;
1220 for (p = ndopts.nd_opts_ri;
1222 p = ndisc_next_option(p, ndopts.nd_opts_ri_end)) {
1223 if (((struct route_info *)p)->prefix_len > in6_dev->cnf.accept_ra_rt_info_max_plen)
1225 rt6_route_rcv(skb->dev, (u8*)p, (p->nd_opt_len) << 3,
1226 &skb->nh.ipv6h->saddr);
1231 if (in6_dev->cnf.accept_ra_pinfo && ndopts.nd_opts_pi) {
1232 struct nd_opt_hdr *p;
1233 for (p = ndopts.nd_opts_pi;
1235 p = ndisc_next_option(p, ndopts.nd_opts_pi_end)) {
1236 addrconf_prefix_rcv(skb->dev, (u8*)p, (p->nd_opt_len) << 3);
1240 if (ndopts.nd_opts_mtu) {
1243 memcpy(&mtu, ((u8*)(ndopts.nd_opts_mtu+1))+2, sizeof(mtu));
1246 if (mtu < IPV6_MIN_MTU || mtu > skb->dev->mtu) {
1247 ND_PRINTK2(KERN_WARNING
1248 "ICMPv6 RA: invalid mtu: %d\n",
1250 } else if (in6_dev->cnf.mtu6 != mtu) {
1251 in6_dev->cnf.mtu6 = mtu;
1254 rt->u.dst.metrics[RTAX_MTU-1] = mtu;
1256 rt6_mtu_change(skb->dev, mtu);
1260 if (ndopts.nd_opts_tgt_lladdr || ndopts.nd_opts_rh) {
1261 ND_PRINTK2(KERN_WARNING
1262 "ICMPv6 RA: invalid RA options");
1266 dst_release(&rt->u.dst);
1268 neigh_release(neigh);
1269 in6_dev_put(in6_dev);
1272 static void ndisc_redirect_rcv(struct sk_buff *skb)
1274 struct inet6_dev *in6_dev;
1275 struct icmp6hdr *icmph;
1276 struct in6_addr *dest;
1277 struct in6_addr *target; /* new first hop to destination */
1278 struct neighbour *neigh;
1280 struct ndisc_options ndopts;
1284 if (!(ipv6_addr_type(&skb->nh.ipv6h->saddr) & IPV6_ADDR_LINKLOCAL)) {
1285 ND_PRINTK2(KERN_WARNING
1286 "ICMPv6 Redirect: source address is not link-local.\n");
1290 optlen = skb->tail - skb->h.raw;
1291 optlen -= sizeof(struct icmp6hdr) + 2 * sizeof(struct in6_addr);
1294 ND_PRINTK2(KERN_WARNING
1295 "ICMPv6 Redirect: packet too short\n");
1299 icmph = (struct icmp6hdr *) skb->h.raw;
1300 target = (struct in6_addr *) (icmph + 1);
1303 if (ipv6_addr_is_multicast(dest)) {
1304 ND_PRINTK2(KERN_WARNING
1305 "ICMPv6 Redirect: destination address is multicast.\n");
1309 if (ipv6_addr_equal(dest, target)) {
1311 } else if (!(ipv6_addr_type(target) & IPV6_ADDR_LINKLOCAL)) {
1312 ND_PRINTK2(KERN_WARNING
1313 "ICMPv6 Redirect: target address is not link-local.\n");
1317 in6_dev = in6_dev_get(skb->dev);
1320 if (in6_dev->cnf.forwarding || !in6_dev->cnf.accept_redirects) {
1321 in6_dev_put(in6_dev);
1326 * The IP source address of the Redirect MUST be the same as the current
1327 * first-hop router for the specified ICMP Destination Address.
1330 if (!ndisc_parse_options((u8*)(dest + 1), optlen, &ndopts)) {
1331 ND_PRINTK2(KERN_WARNING
1332 "ICMPv6 Redirect: invalid ND options\n");
1333 in6_dev_put(in6_dev);
1336 if (ndopts.nd_opts_tgt_lladdr) {
1337 lladdr = ndisc_opt_addr_data(ndopts.nd_opts_tgt_lladdr,
1340 ND_PRINTK2(KERN_WARNING
1341 "ICMPv6 Redirect: invalid link-layer address length\n");
1342 in6_dev_put(in6_dev);
1347 neigh = __neigh_lookup(&nd_tbl, target, skb->dev, 1);
1349 rt6_redirect(dest, &skb->nh.ipv6h->saddr, neigh, lladdr,
1351 neigh_release(neigh);
1353 in6_dev_put(in6_dev);
1356 void ndisc_send_redirect(struct sk_buff *skb, struct neighbour *neigh,
1357 struct in6_addr *target)
1359 struct sock *sk = ndisc_socket->sk;
1360 int len = sizeof(struct icmp6hdr) + 2 * sizeof(struct in6_addr);
1361 struct sk_buff *buff;
1362 struct icmp6hdr *icmph;
1363 struct in6_addr saddr_buf;
1364 struct in6_addr *addrp;
1365 struct net_device *dev;
1366 struct rt6_info *rt;
1367 struct dst_entry *dst;
1368 struct inet6_dev *idev;
1374 u8 ha_buf[MAX_ADDR_LEN], *ha = NULL;
1378 if (ipv6_get_lladdr(dev, &saddr_buf)) {
1379 ND_PRINTK2(KERN_WARNING
1380 "ICMPv6 Redirect: no link-local address on %s\n",
1385 ndisc_flow_init(&fl, NDISC_REDIRECT, &saddr_buf, &skb->nh.ipv6h->saddr);
1387 dst = ip6_route_output(NULL, &fl);
1391 err = xfrm_lookup(&dst, &fl, NULL, 0);
1395 rt = (struct rt6_info *) dst;
1397 if (rt->rt6i_flags & RTF_GATEWAY) {
1398 ND_PRINTK2(KERN_WARNING
1399 "ICMPv6 Redirect: destination is not a neighbour.\n");
1403 if (!xrlim_allow(dst, 1*HZ)) {
1408 if (dev->addr_len) {
1409 read_lock_bh(&neigh->lock);
1410 if (neigh->nud_state & NUD_VALID) {
1411 memcpy(ha_buf, neigh->ha, dev->addr_len);
1412 read_unlock_bh(&neigh->lock);
1414 len += ndisc_opt_addr_space(dev);
1416 read_unlock_bh(&neigh->lock);
1419 rd_len = min_t(unsigned int,
1420 IPV6_MIN_MTU-sizeof(struct ipv6hdr)-len, skb->len + 8);
1424 buff = sock_alloc_send_skb(sk, MAX_HEADER + len + LL_RESERVED_SPACE(dev),
1428 "ICMPv6 Redirect: %s() failed to allocate an skb.\n",
1436 skb_reserve(buff, LL_RESERVED_SPACE(dev));
1437 ip6_nd_hdr(sk, buff, dev, &saddr_buf, &skb->nh.ipv6h->saddr,
1438 IPPROTO_ICMPV6, len);
1440 icmph = (struct icmp6hdr *)skb_put(buff, len);
1441 buff->h.raw = (unsigned char*)icmph;
1443 memset(icmph, 0, sizeof(struct icmp6hdr));
1444 icmph->icmp6_type = NDISC_REDIRECT;
1447 * copy target and destination addresses
1450 addrp = (struct in6_addr *)(icmph + 1);
1451 ipv6_addr_copy(addrp, target);
1453 ipv6_addr_copy(addrp, &skb->nh.ipv6h->daddr);
1455 opt = (u8*) (addrp + 1);
1458 * include target_address option
1462 opt = ndisc_fill_addr_option(opt, ND_OPT_TARGET_LL_ADDR, ha,
1463 dev->addr_len, dev->type);
1466 * build redirect option and copy skb over to the new packet.
1470 *(opt++) = ND_OPT_REDIRECT_HDR;
1471 *(opt++) = (rd_len >> 3);
1474 memcpy(opt, skb->nh.ipv6h, rd_len - 8);
1476 icmph->icmp6_cksum = csum_ipv6_magic(&saddr_buf, &skb->nh.ipv6h->saddr,
1477 len, IPPROTO_ICMPV6,
1478 csum_partial((u8 *) icmph, len, 0));
1481 idev = in6_dev_get(dst->dev);
1482 IP6_INC_STATS(IPSTATS_MIB_OUTREQUESTS);
1483 err = NF_HOOK(PF_INET6, NF_IP6_LOCAL_OUT, buff, NULL, dst->dev, dst_output);
1485 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTREDIRECTS);
1486 ICMP6_INC_STATS(idev, ICMP6_MIB_OUTMSGS);
1489 if (likely(idev != NULL))
1493 static void pndisc_redo(struct sk_buff *skb)
1499 int ndisc_rcv(struct sk_buff *skb)
1503 if (!pskb_may_pull(skb, skb->len))
1506 msg = (struct nd_msg *) skb->h.raw;
1508 __skb_push(skb, skb->data-skb->h.raw);
1510 if (skb->nh.ipv6h->hop_limit != 255) {
1511 ND_PRINTK2(KERN_WARNING
1512 "ICMPv6 NDISC: invalid hop-limit: %d\n",
1513 skb->nh.ipv6h->hop_limit);
1517 if (msg->icmph.icmp6_code != 0) {
1518 ND_PRINTK2(KERN_WARNING
1519 "ICMPv6 NDISC: invalid ICMPv6 code: %d\n",
1520 msg->icmph.icmp6_code);
1524 memset(NEIGH_CB(skb), 0, sizeof(struct neighbour_cb));
1526 switch (msg->icmph.icmp6_type) {
1527 case NDISC_NEIGHBOUR_SOLICITATION:
1531 case NDISC_NEIGHBOUR_ADVERTISEMENT:
1535 case NDISC_ROUTER_SOLICITATION:
1539 case NDISC_ROUTER_ADVERTISEMENT:
1540 ndisc_router_discovery(skb);
1543 case NDISC_REDIRECT:
1544 ndisc_redirect_rcv(skb);
1551 static int ndisc_netdev_event(struct notifier_block *this, unsigned long event, void *ptr)
1553 struct net_device *dev = ptr;
1556 case NETDEV_CHANGEADDR:
1557 neigh_changeaddr(&nd_tbl, dev);
1561 neigh_ifdown(&nd_tbl, dev);
1571 static struct notifier_block ndisc_netdev_notifier = {
1572 .notifier_call = ndisc_netdev_event,
1575 #ifdef CONFIG_SYSCTL
1576 static void ndisc_warn_deprecated_sysctl(struct ctl_table *ctl,
1577 const char *func, const char *dev_name)
1579 static char warncomm[TASK_COMM_LEN];
1581 if (strcmp(warncomm, current->comm) && warned < 5) {
1582 strcpy(warncomm, current->comm);
1584 "process `%s' is using deprecated sysctl (%s) "
1585 "net.ipv6.neigh.%s.%s; "
1586 "Use net.ipv6.neigh.%s.%s_ms "
1589 dev_name, ctl->procname,
1590 dev_name, ctl->procname);
1595 int ndisc_ifinfo_sysctl_change(struct ctl_table *ctl, int write, struct file * filp, void __user *buffer, size_t *lenp, loff_t *ppos)
1597 struct net_device *dev = ctl->extra1;
1598 struct inet6_dev *idev;
1601 if (ctl->ctl_name == NET_NEIGH_RETRANS_TIME ||
1602 ctl->ctl_name == NET_NEIGH_REACHABLE_TIME)
1603 ndisc_warn_deprecated_sysctl(ctl, "syscall", dev ? dev->name : "default");
1605 switch (ctl->ctl_name) {
1606 case NET_NEIGH_RETRANS_TIME:
1607 ret = proc_dointvec(ctl, write, filp, buffer, lenp, ppos);
1609 case NET_NEIGH_REACHABLE_TIME:
1610 ret = proc_dointvec_jiffies(ctl, write,
1611 filp, buffer, lenp, ppos);
1613 case NET_NEIGH_RETRANS_TIME_MS:
1614 case NET_NEIGH_REACHABLE_TIME_MS:
1615 ret = proc_dointvec_ms_jiffies(ctl, write,
1616 filp, buffer, lenp, ppos);
1622 if (write && ret == 0 && dev && (idev = in6_dev_get(dev)) != NULL) {
1623 if (ctl->ctl_name == NET_NEIGH_REACHABLE_TIME ||
1624 ctl->ctl_name == NET_NEIGH_REACHABLE_TIME_MS)
1625 idev->nd_parms->reachable_time = neigh_rand_reach_time(idev->nd_parms->base_reachable_time);
1626 idev->tstamp = jiffies;
1627 inet6_ifinfo_notify(RTM_NEWLINK, idev);
1633 static int ndisc_ifinfo_sysctl_strategy(ctl_table *ctl, int __user *name,
1634 int nlen, void __user *oldval,
1635 size_t __user *oldlenp,
1636 void __user *newval, size_t newlen,
1639 struct net_device *dev = ctl->extra1;
1640 struct inet6_dev *idev;
1643 if (ctl->ctl_name == NET_NEIGH_RETRANS_TIME ||
1644 ctl->ctl_name == NET_NEIGH_REACHABLE_TIME)
1645 ndisc_warn_deprecated_sysctl(ctl, "procfs", dev ? dev->name : "default");
1647 switch (ctl->ctl_name) {
1648 case NET_NEIGH_REACHABLE_TIME:
1649 ret = sysctl_jiffies(ctl, name, nlen,
1650 oldval, oldlenp, newval, newlen,
1653 case NET_NEIGH_RETRANS_TIME_MS:
1654 case NET_NEIGH_REACHABLE_TIME_MS:
1655 ret = sysctl_ms_jiffies(ctl, name, nlen,
1656 oldval, oldlenp, newval, newlen,
1663 if (newval && newlen && ret > 0 &&
1664 dev && (idev = in6_dev_get(dev)) != NULL) {
1665 if (ctl->ctl_name == NET_NEIGH_REACHABLE_TIME ||
1666 ctl->ctl_name == NET_NEIGH_REACHABLE_TIME_MS)
1667 idev->nd_parms->reachable_time = neigh_rand_reach_time(idev->nd_parms->base_reachable_time);
1668 idev->tstamp = jiffies;
1669 inet6_ifinfo_notify(RTM_NEWLINK, idev);
1678 int __init ndisc_init(struct net_proto_family *ops)
1680 struct ipv6_pinfo *np;
1684 err = sock_create_kern(PF_INET6, SOCK_RAW, IPPROTO_ICMPV6, &ndisc_socket);
1687 "ICMPv6 NDISC: Failed to initialize the control socket (err %d).\n",
1689 ndisc_socket = NULL; /* For safety. */
1693 sk = ndisc_socket->sk;
1695 sk->sk_allocation = GFP_ATOMIC;
1696 np->hop_limit = 255;
1697 /* Do not loopback ndisc messages */
1699 sk->sk_prot->unhash(sk);
1702 * Initialize the neighbour table
1705 neigh_table_init(&nd_tbl);
1707 #ifdef CONFIG_SYSCTL
1708 neigh_sysctl_register(NULL, &nd_tbl.parms, NET_IPV6, NET_IPV6_NEIGH,
1710 &ndisc_ifinfo_sysctl_change,
1711 &ndisc_ifinfo_sysctl_strategy);
1714 register_netdevice_notifier(&ndisc_netdev_notifier);
1718 void ndisc_cleanup(void)
1720 #ifdef CONFIG_SYSCTL
1721 neigh_sysctl_unregister(&nd_tbl.parms);
1723 neigh_table_clear(&nd_tbl);
1724 sock_release(ndisc_socket);
1725 ndisc_socket = NULL; /* For safety. */