addrconf.c 114 KB
Newer Older
Linus Torvalds's avatar
Linus Torvalds committed
1
2
3
4
5
/*
 *	IPv6 Address [auto]configuration
 *	Linux INET6 implementation
 *
 *	Authors:
6
 *	Pedro Roque		<roque@di.fc.ul.pt>
Linus Torvalds's avatar
Linus Torvalds committed
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
 *	Alexey Kuznetsov	<kuznet@ms2.inr.ac.ru>
 *
 *	This program is free software; you can redistribute it and/or
 *      modify it under the terms of the GNU General Public License
 *      as published by the Free Software Foundation; either version
 *      2 of the License, or (at your option) any later version.
 */

/*
 *	Changes:
 *
 *	Janos Farkas			:	delete timer on ifdown
 *	<chexum@bankinf.banki.hu>
 *	Andi Kleen			:	kill double kfree on module
 *						unload.
 *	Maciej W. Rozycki		:	FDDI support
 *	sekiya@USAGI			:	Don't send too many RS
 *						packets.
 *	yoshfuji@USAGI			:       Fixed interval between DAD
 *						packets.
 *	YOSHIFUJI Hideaki @USAGI	:	improved accuracy of
 *						address validation timer.
 *	YOSHIFUJI Hideaki @USAGI	:	Privacy Extensions (RFC3041)
 *						support.
 *	Yuji SEKIYA @USAGI		:	Don't assign a same IPv6
 *						address on a same interface.
 *	YOSHIFUJI Hideaki @USAGI	:	ARCnet support
 *	YOSHIFUJI Hideaki @USAGI	:	convert /proc/net/if_inet6 to
 *						seq_file.
36
37
38
 *	YOSHIFUJI Hideaki @USAGI	:	improved source address
 *						selection; consider scope,
 *						status etc.
Linus Torvalds's avatar
Linus Torvalds committed
39
40
41
42
 */

#include <linux/errno.h>
#include <linux/types.h>
43
#include <linux/kernel.h>
Linus Torvalds's avatar
Linus Torvalds committed
44
45
46
47
48
#include <linux/socket.h>
#include <linux/sockios.h>
#include <linux/net.h>
#include <linux/in6.h>
#include <linux/netdevice.h>
49
#include <linux/if_addr.h>
Linus Torvalds's avatar
Linus Torvalds committed
50
51
52
53
54
55
#include <linux/if_arp.h>
#include <linux/if_arcnet.h>
#include <linux/if_infiniband.h>
#include <linux/route.h>
#include <linux/inetdevice.h>
#include <linux/init.h>
56
#include <linux/slab.h>
Linus Torvalds's avatar
Linus Torvalds committed
57
58
59
#ifdef CONFIG_SYSCTL
#include <linux/sysctl.h>
#endif
60
#include <linux/capability.h>
Linus Torvalds's avatar
Linus Torvalds committed
61
62
#include <linux/delay.h>
#include <linux/notifier.h>
63
#include <linux/string.h>
Linus Torvalds's avatar
Linus Torvalds committed
64

65
#include <net/net_namespace.h>
Linus Torvalds's avatar
Linus Torvalds committed
66
67
68
69
70
71
72
73
74
75
#include <net/sock.h>
#include <net/snmp.h>

#include <net/ipv6.h>
#include <net/protocol.h>
#include <net/ndisc.h>
#include <net/ip6_route.h>
#include <net/addrconf.h>
#include <net/tcp.h>
#include <net/ip.h>
76
#include <net/netlink.h>
77
#include <net/pkt_sched.h>
Linus Torvalds's avatar
Linus Torvalds committed
78
79
80
81
82
83
84
#include <linux/if_tunnel.h>
#include <linux/rtnetlink.h>

#ifdef CONFIG_IPV6_PRIVACY
#include <linux/random.h>
#endif

Stephen Hemminger's avatar
Stephen Hemminger committed
85
#include <linux/uaccess.h>
86
#include <asm/unaligned.h>
Linus Torvalds's avatar
Linus Torvalds committed
87
88
89
90
91
92
93
94
95
96
97
98
99
100

#include <linux/proc_fs.h>
#include <linux/seq_file.h>

/* Set to 3 to get tracing... */
#define ACONF_DEBUG 2

#if ACONF_DEBUG >= 3
#define ADBG(x) printk x
#else
#define ADBG(x)
#endif

#define	INFINITY_LIFE_TIME	0xFFFFFFFF
101
102
103
104
105

static inline u32 cstamp_delta(unsigned long cstamp)
{
	return (cstamp - INITIAL_JIFFIES) * 100UL / HZ;
}
Linus Torvalds's avatar
Linus Torvalds committed
106

107
108
109
110
#define ADDRCONF_TIMER_FUZZ_MINUS	(HZ > 50 ? HZ/50 : 1)
#define ADDRCONF_TIMER_FUZZ		(HZ / 4)
#define ADDRCONF_TIMER_FUZZ_MAX		(HZ)

Linus Torvalds's avatar
Linus Torvalds committed
111
#ifdef CONFIG_SYSCTL
112
static void addrconf_sysctl_register(struct inet6_dev *idev);
113
114
115
116
117
118
119
120
121
static void addrconf_sysctl_unregister(struct inet6_dev *idev);
#else
static inline void addrconf_sysctl_register(struct inet6_dev *idev)
{
}

static inline void addrconf_sysctl_unregister(struct inet6_dev *idev)
{
}
Linus Torvalds's avatar
Linus Torvalds committed
122
123
124
125
#endif

#ifdef CONFIG_IPV6_PRIVACY
static int __ipv6_regen_rndid(struct inet6_dev *idev);
126
static int __ipv6_try_regen_rndid(struct inet6_dev *idev, struct in6_addr *tmpaddr);
Linus Torvalds's avatar
Linus Torvalds committed
127
128
129
static void ipv6_regen_rndid(unsigned long data);
#endif

130
static int ipv6_generate_eui64(u8 *eui, struct net_device *dev);
Linus Torvalds's avatar
Linus Torvalds committed
131
132
133
134
135
static int ipv6_count_addresses(struct inet6_dev *idev);

/*
 *	Configured unicast address hash table
 */
136
static struct hlist_head inet6_addr_lst[IN6_ADDR_HSIZE];
137
static DEFINE_SPINLOCK(addrconf_hash_lock);
Linus Torvalds's avatar
Linus Torvalds committed
138
139
140

static void addrconf_verify(unsigned long);

141
static DEFINE_TIMER(addr_chk_timer, addrconf_verify, 0, 0);
Linus Torvalds's avatar
Linus Torvalds committed
142
143
144
145
146
static DEFINE_SPINLOCK(addrconf_verify_lock);

static void addrconf_join_anycast(struct inet6_ifaddr *ifp);
static void addrconf_leave_anycast(struct inet6_ifaddr *ifp);

147
148
static void addrconf_type_change(struct net_device *dev,
				 unsigned long event);
Linus Torvalds's avatar
Linus Torvalds committed
149
150
static int addrconf_ifdown(struct net_device *dev, int how);

Jamal Hadi Salim's avatar
Jamal Hadi Salim committed
151
static void addrconf_dad_start(struct inet6_ifaddr *ifp, u32 flags);
Linus Torvalds's avatar
Linus Torvalds committed
152
153
static void addrconf_dad_timer(unsigned long data);
static void addrconf_dad_completed(struct inet6_ifaddr *ifp);
154
static void addrconf_dad_run(struct inet6_dev *idev);
Linus Torvalds's avatar
Linus Torvalds committed
155
156
157
158
static void addrconf_rs_timer(unsigned long data);
static void __ipv6_ifa_notify(int event, struct inet6_ifaddr *ifa);
static void ipv6_ifa_notify(int event, struct inet6_ifaddr *ifa);

159
static void inet6_prefix_notify(int event, struct inet6_dev *idev,
Linus Torvalds's avatar
Linus Torvalds committed
160
				struct prefix_info *pinfo);
161
162
static bool ipv6_chk_same_addr(struct net *net, const struct in6_addr *addr,
			       struct net_device *dev);
Linus Torvalds's avatar
Linus Torvalds committed
163

164
static ATOMIC_NOTIFIER_HEAD(inet6addr_chain);
Linus Torvalds's avatar
Linus Torvalds committed
165

166
static struct ipv6_devconf ipv6_devconf __read_mostly = {
Linus Torvalds's avatar
Linus Torvalds committed
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
	.forwarding		= 0,
	.hop_limit		= IPV6_DEFAULT_HOPLIMIT,
	.mtu6			= IPV6_MIN_MTU,
	.accept_ra		= 1,
	.accept_redirects	= 1,
	.autoconf		= 1,
	.force_mld_version	= 0,
	.dad_transmits		= 1,
	.rtr_solicits		= MAX_RTR_SOLICITATIONS,
	.rtr_solicit_interval	= RTR_SOLICITATION_INTERVAL,
	.rtr_solicit_delay	= MAX_RTR_SOLICITATION_DELAY,
#ifdef CONFIG_IPV6_PRIVACY
	.use_tempaddr 		= 0,
	.temp_valid_lft		= TEMP_VALID_LIFETIME,
	.temp_prefered_lft	= TEMP_PREFERRED_LIFETIME,
	.regen_max_retry	= REGEN_MAX_RETRY,
	.max_desync_factor	= MAX_DESYNC_FACTOR,
#endif
	.max_addresses		= IPV6_MAX_ADDRESSES,
186
	.accept_ra_defrtr	= 1,
187
	.accept_ra_pinfo	= 1,
188
189
#ifdef CONFIG_IPV6_ROUTER_PREF
	.accept_ra_rtr_pref	= 1,
190
	.rtr_probe_interval	= 60 * HZ,
191
192
193
#ifdef CONFIG_IPV6_ROUTE_INFO
	.accept_ra_rt_info_max_plen = 0,
#endif
194
#endif
195
	.proxy_ndp		= 0,
196
	.accept_source_route	= 0,	/* we do not accept RH0 by default. */
197
	.disable_ipv6		= 0,
198
	.accept_dad		= 1,
Linus Torvalds's avatar
Linus Torvalds committed
199
200
};

201
static struct ipv6_devconf ipv6_devconf_dflt __read_mostly = {
Linus Torvalds's avatar
Linus Torvalds committed
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
	.forwarding		= 0,
	.hop_limit		= IPV6_DEFAULT_HOPLIMIT,
	.mtu6			= IPV6_MIN_MTU,
	.accept_ra		= 1,
	.accept_redirects	= 1,
	.autoconf		= 1,
	.dad_transmits		= 1,
	.rtr_solicits		= MAX_RTR_SOLICITATIONS,
	.rtr_solicit_interval	= RTR_SOLICITATION_INTERVAL,
	.rtr_solicit_delay	= MAX_RTR_SOLICITATION_DELAY,
#ifdef CONFIG_IPV6_PRIVACY
	.use_tempaddr		= 0,
	.temp_valid_lft		= TEMP_VALID_LIFETIME,
	.temp_prefered_lft	= TEMP_PREFERRED_LIFETIME,
	.regen_max_retry	= REGEN_MAX_RETRY,
	.max_desync_factor	= MAX_DESYNC_FACTOR,
#endif
	.max_addresses		= IPV6_MAX_ADDRESSES,
220
	.accept_ra_defrtr	= 1,
221
	.accept_ra_pinfo	= 1,
222
223
#ifdef CONFIG_IPV6_ROUTER_PREF
	.accept_ra_rtr_pref	= 1,
224
	.rtr_probe_interval	= 60 * HZ,
225
226
227
#ifdef CONFIG_IPV6_ROUTE_INFO
	.accept_ra_rt_info_max_plen = 0,
#endif
228
#endif
229
	.proxy_ndp		= 0,
230
	.accept_source_route	= 0,	/* we do not accept RH0 by default. */
231
	.disable_ipv6		= 0,
232
	.accept_dad		= 1,
Linus Torvalds's avatar
Linus Torvalds committed
233
234
235
236
237
};

/* IPv6 Wildcard Address and Loopback Address defined by RFC2553 */
const struct in6_addr in6addr_any = IN6ADDR_ANY_INIT;
const struct in6_addr in6addr_loopback = IN6ADDR_LOOPBACK_INIT;
238
239
const struct in6_addr in6addr_linklocal_allnodes = IN6ADDR_LINKLOCAL_ALLNODES_INIT;
const struct in6_addr in6addr_linklocal_allrouters = IN6ADDR_LINKLOCAL_ALLROUTERS_INIT;
Linus Torvalds's avatar
Linus Torvalds committed
240

241
/* Check if a valid qdisc is available */
242
static inline bool addrconf_qdisc_ok(const struct net_device *dev)
243
{
244
	return !qdisc_tx_is_noop(dev);
245
246
}

247
248
249
/* Check if a route is valid prefix route */
static inline int addrconf_is_prefix_route(const struct rt6_info *rt)
{
Eric Dumazet's avatar
Eric Dumazet committed
250
	return (rt->rt6i_flags & (RTF_GATEWAY | RTF_DEFAULT)) == 0;
251
252
}

Linus Torvalds's avatar
Linus Torvalds committed
253
254
255
256
257
258
static void addrconf_del_timer(struct inet6_ifaddr *ifp)
{
	if (del_timer(&ifp->timer))
		__in6_ifa_put(ifp);
}

Stephen Hemminger's avatar
Stephen Hemminger committed
259
enum addrconf_timer_t {
Linus Torvalds's avatar
Linus Torvalds committed
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
	AC_NONE,
	AC_DAD,
	AC_RS,
};

static void addrconf_mod_timer(struct inet6_ifaddr *ifp,
			       enum addrconf_timer_t what,
			       unsigned long when)
{
	if (!del_timer(&ifp->timer))
		in6_ifa_hold(ifp);

	switch (what) {
	case AC_DAD:
		ifp->timer.function = addrconf_dad_timer;
		break;
	case AC_RS:
		ifp->timer.function = addrconf_rs_timer;
		break;
Stephen Hemminger's avatar
Stephen Hemminger committed
279
280
	default:
		break;
Linus Torvalds's avatar
Linus Torvalds committed
281
282
283
284
285
	}
	ifp->timer.expires = jiffies + when;
	add_timer(&ifp->timer);
}

286
287
static int snmp6_alloc_dev(struct inet6_dev *idev)
{
288
	if (snmp_mib_init((void __percpu **)idev->stats.ipv6,
289
290
			  sizeof(struct ipstats_mib),
			  __alignof__(struct ipstats_mib)) < 0)
291
		goto err_ip;
292
	if (snmp_mib_init((void __percpu **)idev->stats.icmpv6,
293
294
			  sizeof(struct icmpv6_mib),
			  __alignof__(struct icmpv6_mib)) < 0)
295
		goto err_icmp;
296
	if (snmp_mib_init((void __percpu **)idev->stats.icmpv6msg,
297
298
			  sizeof(struct icmpv6msg_mib),
			  __alignof__(struct icmpv6msg_mib)) < 0)
299
		goto err_icmpmsg;
300
301
302

	return 0;

303
err_icmpmsg:
304
	snmp_mib_free((void __percpu **)idev->stats.icmpv6);
305
err_icmp:
306
	snmp_mib_free((void __percpu **)idev->stats.ipv6);
307
err_ip:
308
	return -ENOMEM;
309
310
}

311
static void snmp6_free_dev(struct inet6_dev *idev)
312
{
313
314
315
	snmp_mib_free((void __percpu **)idev->stats.icmpv6msg);
	snmp_mib_free((void __percpu **)idev->stats.icmpv6);
	snmp_mib_free((void __percpu **)idev->stats.ipv6);
316
317
}

Linus Torvalds's avatar
Linus Torvalds committed
318
319
/* Nobody refers to this device, we may destroy it. */

320
321
322
323
324
325
static void in6_dev_finish_destroy_rcu(struct rcu_head *head)
{
	struct inet6_dev *idev = container_of(head, struct inet6_dev, rcu);
	kfree(idev);
}

Linus Torvalds's avatar
Linus Torvalds committed
326
327
328
void in6_dev_finish_destroy(struct inet6_dev *idev)
{
	struct net_device *dev = idev->dev;
329

330
	WARN_ON(!list_empty(&idev->addr_list));
331
332
	WARN_ON(idev->mc_list != NULL);

Linus Torvalds's avatar
Linus Torvalds committed
333
334
335
336
337
#ifdef NET_REFCNT_DEBUG
	printk(KERN_DEBUG "in6_dev_finish_destroy: %s\n", dev ? dev->name : "NIL");
#endif
	dev_put(dev);
	if (!idev->dead) {
Stephen Hemminger's avatar
Stephen Hemminger committed
338
		pr_warning("Freeing alive inet6 device %p\n", idev);
Linus Torvalds's avatar
Linus Torvalds committed
339
340
341
		return;
	}
	snmp6_free_dev(idev);
342
	call_rcu(&idev->rcu, in6_dev_finish_destroy_rcu);
Linus Torvalds's avatar
Linus Torvalds committed
343
344
}

345
346
EXPORT_SYMBOL(in6_dev_finish_destroy);

Linus Torvalds's avatar
Linus Torvalds committed
347
348
349
350
351
352
353
354
355
static struct inet6_dev * ipv6_add_dev(struct net_device *dev)
{
	struct inet6_dev *ndev;

	ASSERT_RTNL();

	if (dev->mtu < IPV6_MIN_MTU)
		return NULL;

356
	ndev = kzalloc(sizeof(struct inet6_dev), GFP_KERNEL);
357

358
359
	if (ndev == NULL)
		return NULL;
360
361
362

	rwlock_init(&ndev->lock);
	ndev->dev = dev;
363
364
	INIT_LIST_HEAD(&ndev->addr_list);

365
	memcpy(&ndev->cnf, dev_net(dev)->ipv6.devconf_dflt, sizeof(ndev->cnf));
366
367
368
369
370
371
372
	ndev->cnf.mtu6 = dev->mtu;
	ndev->cnf.sysctl = NULL;
	ndev->nd_parms = neigh_parms_alloc(dev, &nd_tbl);
	if (ndev->nd_parms == NULL) {
		kfree(ndev);
		return NULL;
	}
373
374
	if (ndev->cnf.forwarding)
		dev_disable_lro(dev);
375
376
	/* We refer to the device */
	dev_hold(dev);
Linus Torvalds's avatar
Linus Torvalds committed
377

378
379
380
	if (snmp6_alloc_dev(ndev) < 0) {
		ADBG((KERN_WARNING
			"%s(): cannot allocate memory for statistics; dev=%s.\n",
381
			__func__, dev->name));
382
383
384
385
386
		neigh_parms_release(&nd_tbl, ndev->nd_parms);
		ndev->dead = 1;
		in6_dev_finish_destroy(ndev);
		return NULL;
	}
Linus Torvalds's avatar
Linus Torvalds committed
387

388
389
390
	if (snmp6_register_dev(ndev) < 0) {
		ADBG((KERN_WARNING
			"%s(): cannot create /proc/net/dev_snmp6/%s\n",
391
			__func__, dev->name));
392
393
394
395
396
397
398
399
400
401
		neigh_parms_release(&nd_tbl, ndev->nd_parms);
		ndev->dead = 1;
		in6_dev_finish_destroy(ndev);
		return NULL;
	}

	/* One reference from device.  We must do this before
	 * we invoke __ipv6_regen_rndid().
	 */
	in6_dev_hold(ndev);
Linus Torvalds's avatar
Linus Torvalds committed
402

403
404
405
	if (dev->flags & (IFF_NOARP | IFF_LOOPBACK))
		ndev->cnf.accept_dad = -1;

406
407
408
409
410
411
412
413
414
#if defined(CONFIG_IPV6_SIT) || defined(CONFIG_IPV6_SIT_MODULE)
	if (dev->type == ARPHRD_SIT && (dev->priv_flags & IFF_ISATAP)) {
		printk(KERN_INFO
		       "%s: Disabled Multicast RS\n",
		       dev->name);
		ndev->cnf.rtr_solicits = 0;
	}
#endif

Linus Torvalds's avatar
Linus Torvalds committed
415
#ifdef CONFIG_IPV6_PRIVACY
416
	INIT_LIST_HEAD(&ndev->tempaddr_list);
417
	setup_timer(&ndev->regen_timer, ipv6_regen_rndid, (unsigned long)ndev);
418
419
	if ((dev->flags&IFF_LOOPBACK) ||
	    dev->type == ARPHRD_TUNNEL ||
420
	    dev->type == ARPHRD_TUNNEL6 ||
421
422
	    dev->type == ARPHRD_SIT ||
	    dev->type == ARPHRD_NONE) {
423
424
425
426
427
		ndev->cnf.use_tempaddr = -1;
	} else {
		in6_dev_hold(ndev);
		ipv6_regen_rndid((unsigned long) ndev);
	}
Linus Torvalds's avatar
Linus Torvalds committed
428
429
#endif

430
	if (netif_running(dev) && addrconf_qdisc_ok(dev))
431
432
		ndev->if_flags |= IF_READY;

433
434
	ipv6_mc_init_dev(ndev);
	ndev->tstamp = jiffies;
435
	addrconf_sysctl_register(ndev);
436
437
	/* protected by rtnl_lock */
	rcu_assign_pointer(dev->ip6_ptr, ndev);
438
439

	/* Join all-node multicast group */
440
	ipv6_dev_mc_inc(dev, &in6addr_linklocal_allnodes);
441

Linus Torvalds's avatar
Linus Torvalds committed
442
443
444
	return ndev;
}

445
static struct inet6_dev * ipv6_find_idev(struct net_device *dev)
Linus Torvalds's avatar
Linus Torvalds committed
446
447
448
449
450
{
	struct inet6_dev *idev;

	ASSERT_RTNL();

Stephen Hemminger's avatar
Stephen Hemminger committed
451
452
453
454
	idev = __in6_dev_get(dev);
	if (!idev) {
		idev = ipv6_add_dev(dev);
		if (!idev)
Linus Torvalds's avatar
Linus Torvalds committed
455
456
			return NULL;
	}
457

Linus Torvalds's avatar
Linus Torvalds committed
458
459
460
461
462
463
464
465
466
467
468
469
470
471
	if (dev->flags&IFF_UP)
		ipv6_mc_up(idev);
	return idev;
}

#ifdef CONFIG_SYSCTL
static void dev_forward_change(struct inet6_dev *idev)
{
	struct net_device *dev;
	struct inet6_ifaddr *ifa;

	if (!idev)
		return;
	dev = idev->dev;
472
473
	if (idev->cnf.forwarding)
		dev_disable_lro(dev);
Linus Torvalds's avatar
Linus Torvalds committed
474
475
	if (dev && (dev->flags & IFF_MULTICAST)) {
		if (idev->cnf.forwarding)
476
			ipv6_dev_mc_inc(dev, &in6addr_linklocal_allrouters);
Linus Torvalds's avatar
Linus Torvalds committed
477
		else
478
			ipv6_dev_mc_dec(dev, &in6addr_linklocal_allrouters);
Linus Torvalds's avatar
Linus Torvalds committed
479
	}
480
481

	list_for_each_entry(ifa, &idev->addr_list, if_list) {
Michal Wrobel's avatar
Michal Wrobel committed
482
483
		if (ifa->flags&IFA_F_TENTATIVE)
			continue;
Linus Torvalds's avatar
Linus Torvalds committed
484
485
486
487
488
489
490
491
		if (idev->cnf.forwarding)
			addrconf_join_anycast(ifa);
		else
			addrconf_leave_anycast(ifa);
	}
}


492
static void addrconf_forward_change(struct net *net, __s32 newf)
Linus Torvalds's avatar
Linus Torvalds committed
493
494
495
496
{
	struct net_device *dev;
	struct inet6_dev *idev;

497
498
	rcu_read_lock();
	for_each_netdev_rcu(net, dev) {
Linus Torvalds's avatar
Linus Torvalds committed
499
500
		idev = __in6_dev_get(dev);
		if (idev) {
501
502
			int changed = (!idev->cnf.forwarding) ^ (!newf);
			idev->cnf.forwarding = newf;
Linus Torvalds's avatar
Linus Torvalds committed
503
504
505
506
			if (changed)
				dev_forward_change(idev);
		}
	}
507
	rcu_read_unlock();
Linus Torvalds's avatar
Linus Torvalds committed
508
}
509

510
static int addrconf_fixup_forwarding(struct ctl_table *table, int *p, int old)
511
{
512
513
514
	struct net *net;

	net = (struct net *)table->extra2;
515
	if (p == &net->ipv6.devconf_dflt->forwarding)
516
517
		return 0;

518
519
520
	if (!rtnl_trylock()) {
		/* Restore the original values before restarting */
		*p = old;
521
		return restart_syscall();
522
	}
523

524
525
526
527
	if (p == &net->ipv6.devconf_all->forwarding) {
		__s32 newf = net->ipv6.devconf_all->forwarding;
		net->ipv6.devconf_dflt->forwarding = newf;
		addrconf_forward_change(net, newf);
528
529
	} else if ((!*p) ^ (!old))
		dev_forward_change((struct inet6_dev *)table->extra1);
530
	rtnl_unlock();
531
532

	if (*p)
533
		rt6_purge_dflt_routers(net);
534
	return 1;
535
}
Linus Torvalds's avatar
Linus Torvalds committed
536
537
#endif

538
539
540
541
542
static void inet6_ifa_finish_destroy_rcu(struct rcu_head *head)
{
	struct inet6_ifaddr *ifp = container_of(head, struct inet6_ifaddr, rcu);
	kfree(ifp);
}
Linus Torvalds's avatar
Linus Torvalds committed
543

544
/* Nobody refers to this ifaddr, destroy it */
Linus Torvalds's avatar
Linus Torvalds committed
545
546
void inet6_ifa_finish_destroy(struct inet6_ifaddr *ifp)
{
547
	WARN_ON(!hlist_unhashed(&ifp->addr_lst));
548

Linus Torvalds's avatar
Linus Torvalds committed
549
550
551
552
553
554
555
#ifdef NET_REFCNT_DEBUG
	printk(KERN_DEBUG "inet6_ifa_finish_destroy\n");
#endif

	in6_dev_put(ifp->idev);

	if (del_timer(&ifp->timer))
Stephen Hemminger's avatar
Stephen Hemminger committed
556
		pr_notice("Timer is still running, when freeing ifa=%p\n", ifp);
Linus Torvalds's avatar
Linus Torvalds committed
557

558
	if (ifp->state != INET6_IFADDR_STATE_DEAD) {
Stephen Hemminger's avatar
Stephen Hemminger committed
559
		pr_warning("Freeing alive inet6 address %p\n", ifp);
Linus Torvalds's avatar
Linus Torvalds committed
560
561
		return;
	}
562
	dst_release(&ifp->rt->dst);
Linus Torvalds's avatar
Linus Torvalds committed
563

564
	call_rcu(&ifp->rcu, inet6_ifa_finish_destroy_rcu);
Linus Torvalds's avatar
Linus Torvalds committed
565
566
}

Brian Haley's avatar
Brian Haley committed
567
568
569
static void
ipv6_link_dev_addr(struct inet6_dev *idev, struct inet6_ifaddr *ifp)
{
570
	struct list_head *p;
571
	int ifp_scope = ipv6_addr_src_scope(&ifp->addr);
Brian Haley's avatar
Brian Haley committed
572
573
574
575
576

	/*
	 * Each device address list is sorted in order of scope -
	 * global before linklocal.
	 */
577
578
579
	list_for_each(p, &idev->addr_list) {
		struct inet6_ifaddr *ifa
			= list_entry(p, struct inet6_ifaddr, if_list);
580
		if (ifp_scope >= ipv6_addr_src_scope(&ifa->addr))
Brian Haley's avatar
Brian Haley committed
581
582
583
			break;
	}

584
	list_add_tail(&ifp->if_list, p);
Brian Haley's avatar
Brian Haley committed
585
586
}

587
static u32 ipv6_addr_hash(const struct in6_addr *addr)
588
589
590
591
592
{
	/*
	 * We perform the hash function over the last 64 bits of the address
	 * This will include the IEEE address token on links that support it.
	 */
593
594
	return jhash_2words((__force u32)addr->s6_addr32[2],
			    (__force u32)addr->s6_addr32[3], 0)
595
		& (IN6_ADDR_HSIZE - 1);
596
597
}

Linus Torvalds's avatar
Linus Torvalds committed
598
599
600
601
/* On success it returns ifp with increased reference count */

static struct inet6_ifaddr *
ipv6_add_addr(struct inet6_dev *idev, const struct in6_addr *addr, int pfxlen,
Jamal Hadi Salim's avatar
Jamal Hadi Salim committed
602
	      int scope, u32 flags)
Linus Torvalds's avatar
Linus Torvalds committed
603
604
605
{
	struct inet6_ifaddr *ifa = NULL;
	struct rt6_info *rt;
606
	unsigned int hash;
Linus Torvalds's avatar
Linus Torvalds committed
607
	int err = 0;
608
609
610
611
612
613
614
	int addr_type = ipv6_addr_type(addr);

	if (addr_type == IPV6_ADDR_ANY ||
	    addr_type & IPV6_ADDR_MULTICAST ||
	    (!(idev->dev->flags & IFF_LOOPBACK) &&
	     addr_type & IPV6_ADDR_LOOPBACK))
		return ERR_PTR(-EADDRNOTAVAIL);
Linus Torvalds's avatar
Linus Torvalds committed
615

616
	rcu_read_lock_bh();
Linus Torvalds's avatar
Linus Torvalds committed
617
618
619
620
621
	if (idev->dead) {
		err = -ENODEV;			/*XXX*/
		goto out2;
	}

622
	if (idev->cnf.disable_ipv6) {
623
624
625
626
		err = -EACCES;
		goto out2;
	}

627
	spin_lock(&addrconf_hash_lock);
Linus Torvalds's avatar
Linus Torvalds committed
628
629

	/* Ignore adding duplicate addresses on an interface */
630
	if (ipv6_chk_same_addr(dev_net(idev->dev), addr, idev->dev)) {
Linus Torvalds's avatar
Linus Torvalds committed
631
632
633
634
635
		ADBG(("ipv6_add_addr: already assigned\n"));
		err = -EEXIST;
		goto out;
	}

636
	ifa = kzalloc(sizeof(struct inet6_ifaddr), GFP_ATOMIC);
Linus Torvalds's avatar
Linus Torvalds committed
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652

	if (ifa == NULL) {
		ADBG(("ipv6_add_addr: malloc failed\n"));
		err = -ENOBUFS;
		goto out;
	}

	rt = addrconf_dst_alloc(idev, addr, 0);
	if (IS_ERR(rt)) {
		err = PTR_ERR(rt);
		goto out;
	}

	ipv6_addr_copy(&ifa->addr, addr);

	spin_lock_init(&ifa->lock);
653
	spin_lock_init(&ifa->state_lock);
Linus Torvalds's avatar
Linus Torvalds committed
654
	init_timer(&ifa->timer);
655
	INIT_HLIST_NODE(&ifa->addr_lst);
Linus Torvalds's avatar
Linus Torvalds committed
656
657
658
659
660
661
	ifa->timer.data = (unsigned long) ifa;
	ifa->scope = scope;
	ifa->prefix_len = pfxlen;
	ifa->flags = flags | IFA_F_TENTATIVE;
	ifa->cstamp = ifa->tstamp = jiffies;

662
663
	ifa->rt = rt;

664
665
666
667
668
669
670
671
672
673
	/*
	 * part one of RFC 4429, section 3.3
	 * We should not configure an address as
	 * optimistic if we do not yet know the link
	 * layer address of our nexhop router
	 */

	if (rt->rt6i_nexthop == NULL)
		ifa->flags &= ~IFA_F_OPTIMISTIC;

Linus Torvalds's avatar
Linus Torvalds committed
674
675
676
677
678
679
680
681
	ifa->idev = idev;
	in6_dev_hold(idev);
	/* For caller */
	in6_ifa_hold(ifa);

	/* Add to big hash table */
	hash = ipv6_addr_hash(addr);

682
683
	hlist_add_head_rcu(&ifa->addr_lst, &inet6_addr_lst[hash]);
	spin_unlock(&addrconf_hash_lock);
Linus Torvalds's avatar
Linus Torvalds committed
684
685
686

	write_lock(&idev->lock);
	/* Add to inet6_dev unicast addr list. */
Brian Haley's avatar
Brian Haley committed
687
	ipv6_link_dev_addr(idev, ifa);
Linus Torvalds's avatar
Linus Torvalds committed
688
689
690

#ifdef CONFIG_IPV6_PRIVACY
	if (ifa->flags&IFA_F_TEMPORARY) {
691
		list_add(&ifa->tmp_list, &idev->tempaddr_list);
Linus Torvalds's avatar
Linus Torvalds committed
692
693
694
695
696
697
698
		in6_ifa_hold(ifa);
	}
#endif

	in6_ifa_hold(ifa);
	write_unlock(&idev->lock);
out2:
699
	rcu_read_unlock_bh();
Linus Torvalds's avatar
Linus Torvalds committed
700

701
	if (likely(err == 0))
702
		atomic_notifier_call_chain(&inet6addr_chain, NETDEV_UP, ifa);
Linus Torvalds's avatar
Linus Torvalds committed
703
704
705
706
707
708
709
	else {
		kfree(ifa);
		ifa = ERR_PTR(err);
	}

	return ifa;
out:
710
	spin_unlock(&addrconf_hash_lock);
Linus Torvalds's avatar
Linus Torvalds committed
711
712
713
714
715
716
717
	goto out2;
}

/* This function wants to get referenced ifp and releases it before return */

static void ipv6_del_addr(struct inet6_ifaddr *ifp)
{
718
	struct inet6_ifaddr *ifa, *ifn;
Linus Torvalds's avatar
Linus Torvalds committed
719
	struct inet6_dev *idev = ifp->idev;
720
	int state;
Linus Torvalds's avatar
Linus Torvalds committed
721
722
723
724
725
726
	int hash;
	int deleted = 0, onlink = 0;
	unsigned long expires = jiffies;

	hash = ipv6_addr_hash(&ifp->addr);

727
728
	spin_lock_bh(&ifp->state_lock);
	state = ifp->state;
729
	ifp->state = INET6_IFADDR_STATE_DEAD;
730
731
732
733
	spin_unlock_bh(&ifp->state_lock);

	if (state == INET6_IFADDR_STATE_DEAD)
		goto out;
Linus Torvalds's avatar
Linus Torvalds committed
734

735
736
737
	spin_lock_bh(&addrconf_hash_lock);
	hlist_del_init_rcu(&ifp->addr_lst);
	spin_unlock_bh(&addrconf_hash_lock);
Linus Torvalds's avatar
Linus Torvalds committed
738
739
740
741

	write_lock_bh(&idev->lock);
#ifdef CONFIG_IPV6_PRIVACY
	if (ifp->flags&IFA_F_TEMPORARY) {
742
743
744
745
		list_del(&ifp->tmp_list);
		if (ifp->ifpub) {
			in6_ifa_put(ifp->ifpub);
			ifp->ifpub = NULL;
Linus Torvalds's avatar
Linus Torvalds committed
746
		}
747
		__in6_ifa_put(ifp);
Linus Torvalds's avatar
Linus Torvalds committed
748
749
750
	}
#endif

751
	list_for_each_entry_safe(ifa, ifn, &idev->addr_list, if_list) {
Linus Torvalds's avatar
Linus Torvalds committed
752
		if (ifa == ifp) {
753
			list_del_init(&ifp->if_list);
Linus Torvalds's avatar
Linus Torvalds committed
754
			__in6_ifa_put(ifp);
755

Linus Torvalds's avatar
Linus Torvalds committed
756
757
758
			if (!(ifp->flags & IFA_F_PERMANENT) || onlink > 0)
				break;
			deleted = 1;
Kristian Slavov's avatar
Kristian Slavov committed
759
			continue;
Linus Torvalds's avatar
Linus Torvalds committed
760
761
762
763
764
765
766
767
768
769
770
771
772
773
		} else if (ifp->flags & IFA_F_PERMANENT) {
			if (ipv6_prefix_equal(&ifa->addr, &ifp->addr,
					      ifp->prefix_len)) {
				if (ifa->flags & IFA_F_PERMANENT) {
					onlink = 1;
					if (deleted)
						break;
				} else {
					unsigned long lifetime;

					if (!onlink)
						onlink = -1;

					spin_lock(&ifa->lock);
774
775
776
777
778
779
780

					lifetime = addrconf_timeout_fixup(ifa->valid_lft, HZ);
					/*
					 * Note: Because this address is
					 * not permanent, lifetime <
					 * LONG_MAX / HZ here.
					 */
Linus Torvalds's avatar
Linus Torvalds committed
781
782
783
784
785
786
787
788
789
790
					if (time_before(expires,
							ifa->tstamp + lifetime * HZ))
						expires = ifa->tstamp + lifetime * HZ;
					spin_unlock(&ifa->lock);
				}
			}
		}
	}
	write_unlock_bh(&idev->lock);

791
792
	addrconf_del_timer(ifp);

Linus Torvalds's avatar
Linus Torvalds committed
793
794
	ipv6_ifa_notify(RTM_DELADDR, ifp);

795
	atomic_notifier_call_chain(&inet6addr_chain, NETDEV_DOWN, ifp);
Linus Torvalds's avatar
Linus Torvalds committed
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814

	/*
	 * Purge or update corresponding prefix
	 *
	 * 1) we don't purge prefix here if address was not permanent.
	 *    prefix is managed by its own lifetime.
	 * 2) if there're no addresses, delete prefix.
	 * 3) if there're still other permanent address(es),
	 *    corresponding prefix is still permanent.
	 * 4) otherwise, update prefix lifetime to the
	 *    longest valid lifetime among the corresponding
	 *    addresses on the device.
	 *    Note: subsequent RA will update lifetime.
	 *
	 * --yoshfuji
	 */
	if ((ifp->flags & IFA_F_PERMANENT) && onlink < 1) {
		struct in6_addr prefix;
		struct rt6_info *rt;
815
		struct net *net = dev_net(ifp->idev->dev);
Linus Torvalds's avatar
Linus Torvalds committed
816
		ipv6_addr_prefix(&prefix, &ifp->addr, ifp->prefix_len);
817
		rt = rt6_lookup(net, &prefix, NULL, ifp->idev->dev->ifindex, 1);
Linus Torvalds's avatar
Linus Torvalds committed
818

819
		if (rt && addrconf_is_prefix_route(rt)) {
Linus Torvalds's avatar
Linus Torvalds committed
820
			if (onlink == 0) {
821
				ip6_del_rt(rt);
Linus Torvalds's avatar
Linus Torvalds committed
822
823
824
825
826
827
				rt = NULL;
			} else if (!(rt->rt6i_flags & RTF_EXPIRES)) {
				rt->rt6i_expires = expires;
				rt->rt6i_flags |= RTF_EXPIRES;
			}
		}
828
		dst_release(&rt->dst);
Linus Torvalds's avatar
Linus Torvalds committed
829
830
	}

831
out:
Linus Torvalds's avatar
Linus Torvalds committed
832
833
834
835
836
837
838
839
	in6_ifa_put(ifp);
}

#ifdef CONFIG_IPV6_PRIVACY
static int ipv6_create_tempaddr(struct inet6_ifaddr *ifp, struct inet6_ifaddr *ift)
{
	struct inet6_dev *idev = ifp->idev;
	struct in6_addr addr, *tmpaddr;
840
	unsigned long tmp_prefered_lft, tmp_valid_lft, tmp_cstamp, tmp_tstamp, age;
841
	unsigned long regen_advance;
Linus Torvalds's avatar
Linus Torvalds committed
842
843
844
	int tmp_plen;
	int ret = 0;
	int max_addresses;
845
	u32 addr_flags;
Linus Torvalds's avatar
Linus Torvalds committed
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889

	write_lock(&idev->lock);
	if (ift) {
		spin_lock_bh(&ift->lock);
		memcpy(&addr.s6_addr[8], &ift->addr.s6_addr[8], 8);
		spin_unlock_bh(&ift->lock);
		tmpaddr = &addr;
	} else {
		tmpaddr = NULL;
	}
retry:
	in6_dev_hold(idev);
	if (idev->cnf.use_tempaddr <= 0) {
		write_unlock(&idev->lock);
		printk(KERN_INFO
			"ipv6_create_tempaddr(): use_tempaddr is disabled.\n");
		in6_dev_put(idev);
		ret = -1;
		goto out;
	}
	spin_lock_bh(&ifp->lock);
	if (ifp->regen_count++ >= idev->cnf.regen_max_retry) {
		idev->cnf.use_tempaddr = -1;	/*XXX*/
		spin_unlock_bh(&ifp->lock);
		write_unlock(&idev->lock);
		printk(KERN_WARNING
			"ipv6_create_tempaddr(): regeneration time exceeded. disabled temporary address support.\n");
		in6_dev_put(idev);
		ret = -1;
		goto out;
	}
	in6_ifa_hold(ifp);
	memcpy(addr.s6_addr, ifp->addr.s6_addr, 8);
	if (__ipv6_try_regen_rndid(idev, tmpaddr) < 0) {
		spin_unlock_bh(&ifp->lock);
		write_unlock(&idev->lock);
		printk(KERN_WARNING
			"ipv6_create_tempaddr(): regeneration of randomized interface id failed.\n");
		in6_ifa_put(ifp);
		in6_dev_put(idev);
		ret = -1;
		goto out;
	}
	memcpy(&addr.s6_addr[8], idev->rndid, 8);
890
	age = (jiffies - ifp->tstamp) / HZ;
Linus Torvalds's avatar
Linus Torvalds committed
891
892
	tmp_valid_lft = min_t(__u32,
			      ifp->valid_lft,
893
			      idev->cnf.temp_valid_lft + age);
894
895
	tmp_prefered_lft = min_t(__u32,
				 ifp->prefered_lft,
896
				 idev->cnf.temp_prefered_lft + age -
897
				 idev->cnf.max_desync_factor);
Linus Torvalds's avatar
Linus Torvalds committed
898
899
900
901
902
903
	tmp_plen = ifp->prefix_len;
	max_addresses = idev->cnf.max_addresses;
	tmp_cstamp = ifp->cstamp;
	tmp_tstamp = ifp->tstamp;
	spin_unlock_bh(&ifp->lock);

904
905
906
	regen_advance = idev->cnf.regen_max_retry *
	                idev->cnf.dad_transmits *
	                idev->nd_parms->retrans_time / HZ;
Linus Torvalds's avatar
Linus Torvalds committed
907
	write_unlock(&idev->lock);
908

909
910
911
912
913
914
915
916
917
918
919
920
	/* A temporary address is created only if this calculated Preferred
	 * Lifetime is greater than REGEN_ADVANCE time units.  In particular,
	 * an implementation must not create a temporary address with a zero
	 * Preferred Lifetime.
	 */
	if (tmp_prefered_lft <= regen_advance) {
		in6_ifa_put(ifp);
		in6_dev_put(idev);
		ret = -1;
		goto out;
	}

921
922
923
924
925
	addr_flags = IFA_F_TEMPORARY;
	/* set in addrconf_prefix_rcv() */
	if (ifp->flags & IFA_F_OPTIMISTIC)
		addr_flags |= IFA_F_OPTIMISTIC;

Linus Torvalds's avatar
Linus Torvalds committed
926
	ift = !max_addresses ||
927
	      ipv6_count_addresses(idev) < max_addresses ?
Linus Torvalds's avatar
Linus Torvalds committed
928
		ipv6_add_addr(idev, &addr, tmp_plen,
929
930
			      ipv6_addr_type(&addr)&IPV6_ADDR_SCOPE_MASK,
			      addr_flags) : NULL;
Linus Torvalds's avatar
Linus Torvalds committed
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
	if (!ift || IS_ERR(ift)) {
		in6_ifa_put(ifp);
		in6_dev_put(idev);
		printk(KERN_INFO
			"ipv6_create_tempaddr(): retry temporary address regeneration.\n");
		tmpaddr = &addr;
		write_lock(&idev->lock);
		goto retry;
	}

	spin_lock_bh(&ift->lock);
	ift->ifpub = ifp;
	ift->valid_lft = tmp_valid_lft;
	ift->prefered_lft = tmp_prefered_lft;
	ift->cstamp = tmp_cstamp;
	ift->tstamp = tmp_tstamp;
	spin_unlock_bh(&ift->lock);

	addrconf_dad_start(ift, 0);
	in6_ifa_put(ift);
	in6_dev_put(idev);
out:
	return ret;
}
#endif

/*
958
 *	Choose an appropriate source address (RFC3484)
Linus Torvalds's avatar
Linus Torvalds committed
959
 */
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
enum {
	IPV6_SADDR_RULE_INIT = 0,
	IPV6_SADDR_RULE_LOCAL,
	IPV6_SADDR_RULE_SCOPE,
	IPV6_SADDR_RULE_PREFERRED,
#ifdef CONFIG_IPV6_MIP6
	IPV6_SADDR_RULE_HOA,
#endif
	IPV6_SADDR_RULE_OIF,
	IPV6_SADDR_RULE_LABEL,
#ifdef CONFIG_IPV6_PRIVACY
	IPV6_SADDR_RULE_PRIVACY,
#endif
	IPV6_SADDR_RULE_ORCHID,
	IPV6_SADDR_RULE_PREFIX,
	IPV6_SADDR_RULE_MAX
};

978
struct ipv6_saddr_score {
979
980
981
982
983
984
	int			rule;
	int			addr_type;
	struct inet6_ifaddr	*ifa;
	DECLARE_BITMAP(scorebits, IPV6_SADDR_RULE_MAX);
	int			scopedist;
	int			matchlen;
985
986
};

987
struct ipv6_saddr_dst {
988
	const struct in6_addr *addr;
989
990
991
	int ifindex;
	int scope;
	int label;
992
	unsigned int prefs;
993
};
994

Dave Jones's avatar
Dave Jones committed
995
static inline int ipv6_saddr_preferred(int type)
Linus Torvalds's avatar
Linus Torvalds committed
996
{
Ulrich Weber's avatar
Ulrich Weber committed
997
	if (type & (IPV6_ADDR_MAPPED|IPV6_ADDR_COMPATv4|IPV6_ADDR_LOOPBACK))
998
999
		return 1;
	return 0;
Linus Torvalds's avatar
Linus Torvalds committed
1000
1001
}

1002
1003
static int ipv6_get_saddr_eval(struct net *net,
			       struct ipv6_saddr_score *score,
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
1042
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
			       struct ipv6_saddr_dst *dst,
			       int i)
{
	int ret;

	if (i <= score->rule) {
		switch (i) {
		case IPV6_SADDR_RULE_SCOPE:
			ret = score->scopedist;
			break;
		case IPV6_SADDR_RULE_PREFIX:
			ret = score->matchlen;
			break;
		default:
			ret = !!test_bit(i, score->scorebits);
		}
		goto out;
	}

	switch (i) {
	case IPV6_SADDR_RULE_INIT:
		/* Rule 0: remember if hiscore is not ready yet */
		ret = !!score->ifa;
		break;
	case IPV6_SADDR_RULE_LOCAL:
		/* Rule 1: Prefer same address */
		ret = ipv6_addr_equal(&score->ifa->addr, dst->addr);
		break;
	case IPV6_SADDR_RULE_SCOPE:
		/* Rule 2: Prefer appropriate scope
		 *
		 *      ret
		 *       ^
		 *    -1 |  d 15
		 *    ---+--+-+---> scope
		 *       |
		 *       |             d is scope of the destination.
		 *  B-d  |  \
		 *       |   \      <- smaller scope is better if
		 *  B-15 |    \        if scope is enough for destinaion.
		 *       |             ret = B - scope (-1 <= scope >= d <= 15).
		 * d-C-1 | /
		 *       |/         <- greater is better
		 *   -C  /             if scope is not enough for destination.
		 *      /|             ret = scope - C (-1 <= d < scope <= 15).
		 *
		 * d - C - 1 < B -15 (for all -1 <= d <= 15).
		 * C > d + 14 - B >= 15 + 14 - B = 29 - B.
		 * Assume B = 0 and we get C > 29.
		 */
		ret = __ipv6_addr_src_scope(score->addr_type);
		if (ret >= dst->scope)
			ret = -ret;
		else
			ret -= 128;	/* 30 is enough */
		score->scopedist = ret;
		break;
	case IPV6_SADDR_RULE_PREFERRED:
		/* Rule 3: Avoid deprecated and optimistic addresses */
		ret = ipv6_saddr_preferred(score->addr_type) ||
		      !(score->ifa->flags & (IFA_F_DEPRECATED|IFA_F_OPTIMISTIC));
		break;
#ifdef CONFIG_IPV6_MIP6
	case IPV6_SADDR_RULE_HOA:
1068
	    {
1069
		/* Rule 4: Prefer home address */
1070
1071
		int prefhome = !(dst->prefs & IPV6_PREFER_SRC_COA);
		ret = !(score->ifa->flags & IFA_F_HOMEADDRESS) ^ prefhome;
1072
		break;
1073
	    }
1074
1075
1076
1077
1078
1079
1080
1081
#endif
	case IPV6_SADDR_RULE_OIF:
		/* Rule 5: Prefer outgoing interface */
		ret = (!dst->ifindex ||
		       dst->ifindex == score->ifa->idev->dev->ifindex);
		break;
	case IPV6_SADDR_RULE_LABEL:
		/* Rule 6: Prefer matching label */
1082
1083
		ret = ipv6_addr_label(net,
				      &score->ifa->addr, score->addr_type,
1084
1085
1086
1087
				      score->ifa->idev->dev->ifindex) == dst->label;
		break;
#ifdef CONFIG_IPV6_PRIVACY
	case IPV6_SADDR_RULE_PRIVACY:
1088
	    {
1089
1090
1091
		/* Rule 7: Prefer public address
		 * Note: prefer temprary address if use_tempaddr >= 2
		 */
1092
1093
1094
1095
		int preftmp = dst->prefs & (IPV6_PREFER_SRC_PUBLIC|IPV6_PREFER_SRC_TMP) ?
				!!(dst->prefs & IPV6_PREFER_SRC_TMP) :
				score->ifa->idev->cnf.use_tempaddr >= 2;
		ret = (!(score->ifa->flags & IFA_F_TEMPORARY)) ^ preftmp;
1096
		break;
1097
	    }
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
#endif
	case IPV6_SADDR_RULE_ORCHID:
		/* Rule 8-: Prefer ORCHID vs ORCHID or
		 *	    non-ORCHID vs non-ORCHID
		 */
		ret = !(ipv6_addr_orchid(&score->ifa->addr) ^
			ipv6_addr_orchid(dst->addr));
		break;
	case IPV6_SADDR_RULE_PREFIX:
		/* Rule 8: Use longest matching prefix */
		score->matchlen = ret = ipv6_addr_diff(&score->ifa->addr,
						       dst->addr);
		break;
	default:
		ret = 0;
	}

	if (ret)
		__set_bit(i, score->scorebits);
	score->rule = i;
out:
	return ret;
}

1122
int ipv6_dev_get_saddr(struct net *net, struct net_device *dst_dev,
1123
		       const struct in6_addr *daddr, unsigned int prefs,
1124
		       struct in6_addr *saddr)
Linus Torvalds's avatar
Linus Torvalds committed
1125
{
1126
1127
1128
	struct ipv6_saddr_score scores[2],
				*score = &scores[0], *hiscore = &scores[1];
	struct ipv6_saddr_dst dst;
1129
	struct net_device *dev;
1130
	int dst_type;
Linus Torvalds's avatar
Linus Torvalds committed
1131

1132
1133
1134
1135
	dst_type = __ipv6_addr_type(daddr);
	dst.addr = daddr;
	dst.ifindex = dst_dev ? dst_dev->ifindex : 0;
	dst.scope = __ipv6_addr_src_scope(dst_type);
1136
	dst.label = ipv6_addr_label(net, daddr, dst_type, dst.ifindex);
1137
	dst.prefs = prefs;
1138
1139
1140

	hiscore->rule = -1;
	hiscore->ifa = NULL;
Linus Torvalds's avatar
Linus Torvalds committed
1141

1142
	rcu_read_lock();
Linus Torvalds's avatar
Linus Torvalds committed
1143

1144
	for_each_netdev_rcu(net, dev) {
1145
1146
		struct inet6_dev *idev;

1147
		/* Candidate Source Address (section 4)
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
		 *  - multicast and link-local destination address,
		 *    the set of candidate source address MUST only
		 *    include addresses assigned to interfaces
		 *    belonging to the same link as the outgoing
		 *    interface.
		 * (- For site-local destination addresses, the
		 *    set of candidate source addresses MUST only
		 *    include addresses assigned to interfaces
		 *    belonging to the same site as the outgoing
		 *    interface.)
		 */
1159
1160
1161
		if (((dst_type & IPV6_ADDR_MULTICAST) ||
		     dst.scope <= IPV6_ADDR_SCOPE_LINKLOCAL) &&
		    dst.ifindex && dev->ifindex != dst.ifindex)
1162
			continue;
Linus Torvalds's avatar
Linus Torvalds committed
1163
1164

		idev = __in6_dev_get(dev);
1165
1166
1167
1168
		if (!idev)
			continue;

		read_lock_bh(&idev->lock);
1169
		list_for_each_entry(score->ifa, &idev->addr_list, if_list) {
1170
			int i;
1171

1172
			/*
1173
1174
1175
			 * - Tentative Address (RFC2462 section 5.4)
			 *  - A tentative address is not considered
			 *    "assigned to an interface" in the traditional
1176
			 *    sense, unless it is also flagged as optimistic.
1177
			 * - Candidate Source Address (section 4)
1178
1179
1180
1181
			 *  - In any case, anycast addresses, multicast
			 *    addresses, and the unspecified address MUST
			 *    NOT be included in a candidate set.
			 */
1182
1183
			if ((score->ifa->flags & IFA_F_TENTATIVE) &&
			    (!(score->ifa->flags & IFA_F_OPTIMISTIC)))
1184
				continue;
1185
1186
1187
1188
1189

			score->addr_type = __ipv6_addr_type(&score->ifa->addr);

			if (unlikely(score->addr_type == IPV6_ADDR_ANY ||
				     score->addr_type & IPV6_ADDR_MULTICAST)) {
1190
				LIMIT_NETDEBUG(KERN_DEBUG
Joe Perches's avatar
Joe Perches committed
1191
					       "ADDRCONF: unspecified / multicast address "
1192
1193
1194
1195
1196
					       "assigned as unicast address on %s",
					       dev->name);
				continue;
			}

1197
1198
1199
1200
1201
1202
			score->rule = -1;
			bitmap_zero(score->scorebits, IPV6_SADDR_RULE_MAX);

			for (i = 0; i < IPV6_SADDR_RULE_MAX; i++) {
				int minihiscore, miniscore;

1203
1204
				minihiscore = ipv6_get_saddr_eval(net, hiscore, &dst, i);
				miniscore = ipv6_get_saddr_eval(net, score, &dst, i);
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222
1223
1224
1225

				if (minihiscore > miniscore) {
					if (i == IPV6_SADDR_RULE_SCOPE &&
					    score->scopedist > 0) {
						/*
						 * special case:
						 * each remaining entry
						 * has too small (not enough)
						 * scope, because ifa entries
						 * are sorted by their scope
						 * values.
						 */
						goto try_nextdev;
					}
					break;
				} else if (minihiscore < miniscore) {
					if (hiscore->ifa)
						in6_ifa_put(hiscore->ifa);

					in6_ifa_hold(score->ifa);

1226
					swap(hiscore, score);
1227
1228
1229
1230
1231

					/* restore our iterator */
					score->ifa = hiscore->ifa;

					break;
Linus Torvalds's avatar
Linus Torvalds committed
1232
				}
1233
			}
Linus Torvalds's avatar
Linus Torvalds committed
1234
		}
1235
try_nextdev:
1236
		read_unlock_bh(&idev->lock);
Linus Torvalds's avatar
Linus Torvalds committed
1237
	}
1238
	rcu_read_unlock();
Linus Torvalds's avatar
Linus Torvalds committed
1239

1240
	if (!hiscore->ifa)
1241
		return -EADDRNOTAVAIL;
1242

1243
1244
	ipv6_addr_copy(saddr, &hiscore->ifa->addr);
	in6_ifa_put(hiscore->ifa);