Subject: Re: dhcpd
To: Christos Zoulas <christos@astron.com>
From: Greg Troxel <gdt@ir.bbn.com>
List: tech-net
Date: 09/14/2007 19:29:52
christos@astron.com (Christos Zoulas) writes:
[dropping current-users; we're polishing now]
> In article <rmify1i2zcn.fsf@fnord.ir.bbn.com>,
> Greg Troxel <gdt@ir.bbn.com> wrote:
>>I looked at the ifconf() code and now think that the kernel wasn't
>>copying the whole sockaddr. I have compile tested but not run the
>>following patch, which I think will fix the 'missing two bytes' of the
>>mac address problem, as well as unbreak v6 addresses.
>>
>>Index: sys/net/if.c
>>===================================================================
>>RCS file: /cvsroot/src/sys/net/if.c,v
>>retrieving revision 1.200
>>diff -u -p -r1.200 if.c
>>--- sys/net/if.c 11 Sep 2007 19:31:22 -0000 1.200
>>+++ sys/net/if.c 13 Sep 2007 18:28:48 -0000
>>@@ -1669,7 +1669,7 @@ ifconf(u_long cmd, void *data)
>>
>> if (ifrp != NULL)
>> {
>>- ifr.ifr_addr = *sa;
>>+ memcpy(&ifr.ifr_space, sa, sa->sa_len);
>
> I think that this should be MIN(sa->sa_len, sizeof(ifr.ifr_space)) just
> to be paranoid... Or even better:
>
> _KASSERT(sa->sa_len < sizeof(ifr.ifr_space));
>
> before the memcpy...
>
> christos
I think so too, but the whole loop has:
TAILQ_FOREACH(ifa, &ifp->if_addrlist, ifa_list) {
struct sockaddr *sa = ifa->ifa_addr;
/* all sockaddrs must fit in sockaddr_storage */
KASSERT(sa->sa_len <= sizeof(ifr.ifr_ifru));
if (ifrp != NULL)
{
memcpy(&ifr.ifr_space, sa, sa->sa_len);
if (space >= sz) {
error = copyout(&ifr, ifrp, sz);
if (error != 0)
return (error);
ifrp++; space -= sz;
}
}
else
space += sz;
}
So perhaps you could argue that the KASSERT only belongs in the if branch.
I used the union, not space, because that's the real destination of the
copy. But they should be the same.
Why < vs <= ?
Is _KASSERT just a typeo for KASSERT?