From: Lukasz Stelmach <stlman@poczta.fm>
To: linux-kernel@vger.kernel.org
Cc: David Miller <davem@davemloft.net>,
yoshfuji@linux-ipv6.org, netdev@vger.kernel.org
Subject: Re: [PATCH] Temporary IPv6 address asignment
Date: Mon, 04 May 2009 00:20:51 +0200 [thread overview]
Message-ID: <49FE18C3.7040702@poczta.fm> (raw)
In-Reply-To: <20090503.144758.222061423.davem@davemloft.net>
[-- Attachment #1: Type: text/plain, Size: 12600 bytes --]
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
David Miller pisze:
> From: Lukasz Stelmach <stlman@poczta.fm>
> Date: Sun, 03 May 2009 23:45:30 +0200
>
>> -----BEGIN PGP SIGNED MESSAGE-----
>> Hash: SHA1
>>
>> Greetings.
>>
>> I discovered recently and fixed some problems with IPv6 temporary
>> address asignment. I have described the problem at
>> http://bugzilla.kernel.org as bugs #13208 and #13221.
>>
>> http://bugzilla.kernel.org/show_bug.cgi?id=13208
>> http://bugzilla.kernel.org/show_bug.cgi?id=13221
>>
>> The patch is available at:
>>
>> http://bugzilla.kernel.org/attachment.cgi?id=21201
>
> Nobody is going to look at this unless you post the patch
> with description and proper signoffs with netdev@vger.kernel.org
> CC:'d
The description is in the patch, and a sign-off too. But all righ.
- -----CUT HERE-----
A fixed mechanism to create and recreate temporary addresses,
even for very short preferred lifetimes.
A new RFC-compliant DESYNC_FACTOR implemented as a sysctl
variable desync_factor which is assigned a random value
each time max_desync_factor is written to. Each interface
has its own desync_factor and max_desync_factor. Writes to
default/max_desync_factor influence only default values. Writes
to all/max_desync_factor influence "all" and default values but
not values of running interfaces.
The patch fixes issues described in bugs #13208 and #13221 at
http://bugzilla.kernel.org.
Signed-off-by: Łukasz Stelmach <stlman@poczta.fm>
diff --git a/include/linux/ipv6.h b/include/linux/ipv6.h
index 476d946..fa45ad2 100644
- --- a/include/linux/ipv6.h
+++ b/include/linux/ipv6.h
@@ -146,6 +146,7 @@ struct ipv6_devconf {
__s32 temp_prefered_lft;
__s32 regen_max_retry;
__s32 max_desync_factor;
+ __s32 desync_factor;
#endif
__s32 max_addresses;
__s32 accept_ra_defrtr;
@@ -188,6 +189,7 @@ enum {
DEVCONF_TEMP_PREFERED_LFT,
DEVCONF_REGEN_MAX_RETRY,
DEVCONF_MAX_DESYNC_FACTOR,
+ DEVCONF_DESYNC_FACTOR,
DEVCONF_MAX_ADDRESSES,
DEVCONF_FORCE_MLD_VERSION,
DEVCONF_ACCEPT_RA_DEFRTR,
diff --git a/include/linux/sysctl.h b/include/linux/sysctl.h
index e76d3b2..951ba2c 100644
- --- a/include/linux/sysctl.h
+++ b/include/linux/sysctl.h
@@ -570,15 +570,16 @@ enum {
NET_IPV6_TEMP_PREFERED_LFT=13,
NET_IPV6_REGEN_MAX_RETRY=14,
NET_IPV6_MAX_DESYNC_FACTOR=15,
- - NET_IPV6_MAX_ADDRESSES=16,
- - NET_IPV6_FORCE_MLD_VERSION=17,
- - NET_IPV6_ACCEPT_RA_DEFRTR=18,
- - NET_IPV6_ACCEPT_RA_PINFO=19,
- - NET_IPV6_ACCEPT_RA_RTR_PREF=20,
- - NET_IPV6_RTR_PROBE_INTERVAL=21,
- - NET_IPV6_ACCEPT_RA_RT_INFO_MAX_PLEN=22,
- - NET_IPV6_PROXY_NDP=23,
- - NET_IPV6_ACCEPT_SOURCE_ROUTE=25,
+ NET_IPV6_DESYNC_FACTOR=16,
+ NET_IPV6_MAX_ADDRESSES=17,
+ NET_IPV6_FORCE_MLD_VERSION=18,
+ NET_IPV6_ACCEPT_RA_DEFRTR=19,
+ NET_IPV6_ACCEPT_RA_PINFO=20,
+ NET_IPV6_ACCEPT_RA_RTR_PREF=21,
+ NET_IPV6_RTR_PROBE_INTERVAL=22,
+ NET_IPV6_ACCEPT_RA_RT_INFO_MAX_PLEN=23,
+ NET_IPV6_PROXY_NDP=24,
+ NET_IPV6_ACCEPT_SOURCE_ROUTE=26,
__NET_IPV6_MAX
};
diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c
index a8218bc..1b746ee 100644
- --- a/net/ipv6/addrconf.c
+++ b/net/ipv6/addrconf.c
@@ -116,8 +116,6 @@ static inline void addrconf_sysctl_unregister(struct inet6_dev *idev)
static int __ipv6_regen_rndid(struct inet6_dev *idev);
static int __ipv6_try_regen_rndid(struct inet6_dev *idev, struct in6_addr *tmpaddr);
static void ipv6_regen_rndid(unsigned long data);
- -
- -static int desync_factor = MAX_DESYNC_FACTOR * HZ;
#endif
static int ipv6_generate_eui64(u8 *eui, struct net_device *dev);
@@ -172,6 +170,7 @@ static struct ipv6_devconf ipv6_devconf __read_mostly = {
.temp_prefered_lft = TEMP_PREFERRED_LIFETIME,
.regen_max_retry = REGEN_MAX_RETRY,
.max_desync_factor = MAX_DESYNC_FACTOR,
+ .desync_factor = MAX_DESYNC_FACTOR / 2,
#endif
.max_addresses = IPV6_MAX_ADDRESSES,
.accept_ra_defrtr = 1,
@@ -206,6 +205,7 @@ static struct ipv6_devconf ipv6_devconf_dflt __read_mostly = {
.temp_prefered_lft = TEMP_PREFERRED_LIFETIME,
.regen_max_retry = REGEN_MAX_RETRY,
.max_desync_factor = MAX_DESYNC_FACTOR,
+ .desync_factor = MAX_DESYNC_FACTOR / 2,
#endif
.max_addresses = IPV6_MAX_ADDRESSES,
.accept_ra_defrtr = 1,
@@ -831,11 +831,13 @@ static void ipv6_del_addr(struct inet6_ifaddr *ifp)
}
#ifdef CONFIG_IPV6_PRIVACY
- -static int ipv6_create_tempaddr(struct inet6_ifaddr *ifp, struct inet6_ifaddr *ift)
+static int ipv6_create_tempaddr(struct inet6_ifaddr *ifp,
+ struct inet6_ifaddr *ift,
+ unsigned long now)
{
struct inet6_dev *idev = ifp->idev;
struct in6_addr addr, *tmpaddr;
- - unsigned long tmp_prefered_lft, tmp_valid_lft, tmp_cstamp, tmp_tstamp;
+ unsigned long tmp_prefered_lft, tmp_valid_lft;
unsigned long regen_advance;
int tmp_plen;
int ret = 0;
@@ -890,11 +892,9 @@ retry:
idev->cnf.temp_valid_lft);
tmp_prefered_lft = min_t(__u32,
ifp->prefered_lft,
- - idev->cnf.temp_prefered_lft - desync_factor / HZ);
+ idev->cnf.temp_prefered_lft - idev->cnf.desync_factor);
tmp_plen = ifp->prefix_len;
max_addresses = idev->cnf.max_addresses;
- - tmp_cstamp = ifp->cstamp;
- - tmp_tstamp = ifp->tstamp;
spin_unlock_bh(&ifp->lock);
regen_advance = idev->cnf.regen_max_retry *
@@ -938,8 +938,7 @@ retry:
ift->ifpub = ifp;
ift->valid_lft = tmp_valid_lft;
ift->prefered_lft = tmp_prefered_lft;
- - ift->cstamp = tmp_cstamp;
- - ift->tstamp = tmp_tstamp;
+ ift->cstamp = ift->tstamp = now;
spin_unlock_bh(&ift->lock);
addrconf_dad_start(ift, 0);
@@ -1388,7 +1387,7 @@ static void addrconf_dad_stop(struct inet6_ifaddr *ifp)
if (ifpub) {
in6_ifa_hold(ifpub);
spin_unlock_bh(&ifp->lock);
- - ipv6_create_tempaddr(ifpub, ifp);
+ ipv6_create_tempaddr(ifpub, ifp, jiffies);
in6_ifa_put(ifpub);
} else {
spin_unlock_bh(&ifp->lock);
@@ -1624,7 +1623,8 @@ static void ipv6_regen_rndid(unsigned long data)
expires = jiffies +
idev->cnf.temp_prefered_lft * HZ -
- - idev->cnf.regen_max_retry * idev->cnf.dad_transmits * idev->nd_parms->retrans_time - desync_factor;
+ idev->cnf.regen_max_retry * idev->cnf.dad_transmits * idev->nd_parms->retrans_time -
+ idev->cnf.desync_factor * HZ;
if (time_before(expires, jiffies)) {
printk(KERN_WARNING
"ipv6_regen_rndid(): too short regeneration interval; timer disabled for %s.\n",
@@ -1971,7 +1971,7 @@ ok:
* also create a new temporary address.
*/
read_unlock_bh(&in6_dev->lock);
- - ipv6_create_tempaddr(ifp, NULL);
+ ipv6_create_tempaddr(ifp, NULL, jiffies);
} else {
read_unlock_bh(&in6_dev->lock);
}
@@ -2809,6 +2809,11 @@ static void addrconf_dad_timer(unsigned long data)
read_unlock_bh(&idev->lock);
addrconf_dad_completed(ifp);
+ /*
+ * Required to expire properly temporary addresses
+ * with preferred lifetimes < ADDR_CHECK_FREQUENCY
+ */
+ addrconf_verify(0);
goto out;
}
@@ -3121,7 +3126,7 @@ restart:
spin_lock(&ifpub->lock);
ifpub->regen_count = 0;
spin_unlock(&ifpub->lock);
- - ipv6_create_tempaddr(ifpub, ifp);
+ ipv6_create_tempaddr(ifpub, ifp, now);
in6_ifa_put(ifpub);
in6_ifa_put(ifp);
goto restart;
@@ -3638,6 +3643,7 @@ static inline void ipv6_store_devconf(struct ipv6_devconf *cnf,
array[DEVCONF_TEMP_PREFERED_LFT] = cnf->temp_prefered_lft;
array[DEVCONF_REGEN_MAX_RETRY] = cnf->regen_max_retry;
array[DEVCONF_MAX_DESYNC_FACTOR] = cnf->max_desync_factor;
+ array[DEVCONF_DESYNC_FACTOR] = cnf->desync_factor;
#endif
array[DEVCONF_MAX_ADDRESSES] = cnf->max_addresses;
array[DEVCONF_ACCEPT_RA_DEFRTR] = cnf->accept_ra_defrtr;
@@ -3935,6 +3941,43 @@ static void ipv6_ifa_notify(int event, struct inet6_ifaddr *ifp)
}
#ifdef CONFIG_SYSCTL
+#ifdef CONFIG_IPV6_PRIVACY
+static int addrconf_sysctl_desync(ctl_table *ctl, int write,
+ struct file *filp, void __user *buffer,
+ size_t *lenp, loff_t *ppos)
+{
+ int ret;
+
+ ret = proc_dointvec(ctl, write, filp, buffer, lenp, ppos);
+
+ if (write) {
+ __s32 df;
+ int *valp = ctl->data;
+ struct ipv6_devconf *all, *dflt;
+ struct inet6_dev *idev = ctl->extra1;
+ struct net *net = ctl->extra2;
+ all = net->ipv6.devconf_all;
+ dflt = net->ipv6.devconf_dflt;
+
+ get_random_bytes(&df, sizeof(df));
+ /* The global abs() casts to int. */;
+ df = ((df) < 0 ? -(df) : df) % (*valp)
+
+ /* XXX How about some locking? */
+ if(idev)
+ idev->cnf.desync_factor = df;
+ else if (valp == &dflt->max_desync_factor)
+ dflt->desync_factor = df;
+ else if (valp == &all->max_desync_factor) {
+ all->desync_factor = df;
+ dflt->max_desync_factor = all->max_desync_factor;
+ dflt->desync_factor = df;
+ }
+
+ }
+ return ret;
+}
+#endif
static
int addrconf_sysctl_forward(ctl_table *ctl, int write, struct file * filp,
@@ -4124,6 +4167,14 @@ static struct addrconf_sysctl_table
.data = &ipv6_devconf.max_desync_factor,
.maxlen = sizeof(int),
.mode = 0644,
+ .proc_handler = addrconf_sysctl_desync,
+ },
+ {
+ .ctl_name = NET_IPV6_DESYNC_FACTOR,
+ .procname = "desync_factor",
+ .data = &ipv6_devconf.desync_factor,
+ .maxlen = sizeof(int),
+ .mode = 0444,
.proc_handler = proc_dointvec,
},
#endif
@@ -4449,6 +4500,11 @@ int __init addrconf_init(void)
rtnl_unlock();
if (err)
goto errlo;
+#ifdef CONFIG_IPV6_PRIVACY
+ get_random_bytes(&ipv6_devconf.desync_factor, sizeof(ipv6_devconf.desync_factor));
+ ipv6_devconf.desync_factor = abs(ipv6_devconf.desync_factor) % ipv6_devconf.max_desync_factor;
+ ipv6_devconf_dflt.desync_factor = ipv6_devconf.desync_factor;
+#endif
register_netdevice_notifier(&ipv6_dev_notf);
- -----CUT HERE-----
- --
Było mi bardzo miło. Czwarta pospolita klęska, [...]
>Łukasz< Już nie katolicka lecz złodziejska. (c)PP
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v2.0.11 (GNU/Linux)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org
iEYEARECAAYFAkn+GMMACgkQNdzY8sm9K9zimACcC6NfOGMzd0vqB9J/QXrc6q0P
h6oAmgKP7sG+/h0JkdjVEeLbbyDgHH/s
=CryG
-----END PGP SIGNATURE-----
----------------------------------------------------------------------
Gotowka na koncie. Otworz konto direct i wez podwojny limit.
http://link.interia.pl/f2145
[-- Attachment #2: stlman.vcf --]
[-- Type: text/x-vcard, Size: 177 bytes --]
begin:vcard
fn;quoted-printable:=C5=81ukasz Stelmach
n;quoted-printable:Stelmach;=C5=81ukasz
email;internet:stlman@poczta.fm
x-mozilla-html:FALSE
version:2.1
end:vcard
next prev parent reply other threads:[~2009-05-03 22:21 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2009-05-03 21:45 [PATCH] Temporary IPv6 address asignment Lukasz Stelmach
2009-05-03 21:47 ` David Miller
2009-05-03 22:20 ` Lukasz Stelmach [this message]
2009-05-03 22:34 ` David Miller
2009-05-03 22:45 ` Lukasz Stelmach
2009-05-03 23:58 ` Eric W. Biederman
2009-05-04 0:21 ` David Miller
2009-05-04 10:57 ` YOSHIFUJI Hideaki / 吉藤英明
2009-05-04 13:30 ` [PATCH] Temporary IPv6 address asignment (v.1.1) Lukasz Stelmach
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=49FE18C3.7040702@poczta.fm \
--to=stlman@poczta.fm \
--cc=davem@davemloft.net \
--cc=linux-kernel@vger.kernel.org \
--cc=netdev@vger.kernel.org \
--cc=yoshfuji@linux-ipv6.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.