Fix couple of bugs from r257692 related to scan of address list on

an interface:
- in in_control() skip over not AF_INET addresses.
- in in_aifaddr_ioctl() and in_difaddr_ioctl() do correct check
  of address family, w/o accessing memory beyond struct ifaddr.

Sponsored by:	Nginx, Inc.
This commit is contained in:
Gleb Smirnoff 2013-12-29 22:20:06 +00:00
parent 56dc4e726b
commit 9706c950a2

View File

@ -247,6 +247,8 @@ in_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
*/
IF_ADDR_RLOCK(ifp);
TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) {
if (ifa->ifa_addr->sa_family != AF_INET)
continue;
ia = (struct in_ifaddr *)ifa;
if (cmd == SIOCGIFADDR || addr->sin_addr.s_addr == INADDR_ANY)
break;
@ -338,11 +340,12 @@ in_aifaddr_ioctl(u_long cmd, caddr_t data, struct ifnet *ifp, struct thread *td)
ia = NULL;
IF_ADDR_RLOCK(ifp);
TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) {
struct in_ifaddr *it = ifatoia(ifa);
struct in_ifaddr *it;
if (it->ia_addr.sin_family != AF_INET)
if (ifa->ifa_addr->sa_family != AF_INET)
continue;
it = (struct in_ifaddr *)ifa;
iaIsFirst = false;
if (it->ia_addr.sin_addr.s_addr == addr->sin_addr.s_addr &&
prison_check_ip4(td->td_ucred, &addr->sin_addr) == 0)
@ -530,11 +533,12 @@ in_difaddr_ioctl(caddr_t data, struct ifnet *ifp, struct thread *td)
ia = NULL;
IF_ADDR_WLOCK(ifp);
TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) {
struct in_ifaddr *it = ifatoia(ifa);
struct in_ifaddr *it;
if (it->ia_addr.sin_family != AF_INET)
if (ifa->ifa_addr->sa_family != AF_INET)
continue;
it = (struct in_ifaddr *)ifa;
if (deleteAny && ia == NULL && (td == NULL ||
prison_check_ip4(td->td_ucred, &it->ia_addr.sin_addr) == 0))
ia = it;