I have a look at this. The ppp code is a total nightmare.

On Sun, Jun 28, 2009 at 02:17:13PM +0200, Oliver Klima wrote:
> Hi,
> 
> after the latest change in ppp(8)/iface.c ppp(8) will loop endlessly if
> there's an interface with ifm_version != RTM_VERSION. The pointer to the
> if_msghdr structure doesn't point to the next element when continue is
> executed.
> 
> In addition the inner loop checks the ifm_version a second time,
> although that loop iterates over ifa_msghdr structures. That doesn't
> make sense to me.
> 
> I attached a patch that solved the problem for me (amd64/GENERIC.MP).
> 
> Regards,
> 
> Oliver Klima
> --- usr.sbin/ppp/ppp/iface.c.orig     Sat Jun 27 20:41:25 2009
> +++ usr.sbin/ppp/ppp/iface.c  Sun Jun 28 13:46:54 2009
> @@ -140,23 +140,23 @@
>  
>    while (ptr < end && iface == NULL) {
>      ifm = (struct if_msghdr *)ptr;                   /* On if_msghdr */
> -    if (ifm->ifm_version != RTM_VERSION)
> -      continue;
> -    if (ifm->ifm_type != RTM_IFINFO)
> -      break;
> -    dl = (struct sockaddr_dl *)(ifm + 1);            /* Single _dl at end */
> -    if (dl->sdl_nlen == namelen && !strncmp(name, dl->sdl_data, namelen)) {
> -      iface = (struct iface *)malloc(sizeof *iface);
> -      if (iface == NULL) {
> -        fprintf(stderr, "iface_Create: malloc: %s\n", strerror(errno));
> -        return NULL;
> -      }
> -      iface->name = strdup(name);
> -      iface->index = ifm->ifm_index;
> -      iface->flags = ifm->ifm_flags;
> -      iface->mtu = 0;
> -      iface->addrs = 0;
> -      iface->addr = NULL;
> +    if (ifm->ifm_version == RTM_VERSION) {
> +         if (ifm->ifm_type != RTM_IFINFO)
> +           break;
> +         dl = (struct sockaddr_dl *)(ifm + 1);               /* Single _dl 
> at end */
> +         if (dl->sdl_nlen == namelen && !strncmp(name, dl->sdl_data, 
> namelen)) {
> +           iface = (struct iface *)malloc(sizeof *iface);
> +           if (iface == NULL) {
> +             fprintf(stderr, "iface_Create: malloc: %s\n", strerror(errno));
> +             return NULL;
> +           }
> +           iface->name = strdup(name);
> +           iface->index = ifm->ifm_index;
> +           iface->flags = ifm->ifm_flags;
> +           iface->mtu = 0;
> +           iface->addrs = 0;
> +           iface->addr = NULL;
> +         }
>      }
>      ptr += ifm->ifm_msglen;                          /* First ifa_msghdr */
>      for (; ptr < end; ptr += ifam->ifam_msglen) {
> @@ -164,7 +164,7 @@
>  
>        if (ifam->ifam_type != RTM_NEWADDR)            /* finished this if */
>          break;
> -      if (ifm->ifm_version != RTM_VERSION)
> +      if (ifam->ifam_version != RTM_VERSION)
>          continue;
>  
>        if (iface != NULL && ifam->ifam_addrs & RTA_IFA) {
> 

-- 
:wq Claudio

Reply via email to