On Sun, Apr 03, 2016 at 10:17:49PM +0200, Vincent Gross wrote:
> in_pcbpickport() need the local address, so I extend the prototype and
> keep a void * to the sin(6)_addr or zeroin46_addr. And while at it, I set
> the INPLOOKUP_IPV6 flag which will be needed in in_pcbpickport().
> 
> Ok ?

OK bluhm@

> 
> Index: netinet/in_pcb.c
> ===================================================================
> RCS file: /cvs/src/sys/netinet/in_pcb.c,v
> retrieving revision 1.198
> diff -u -p -r1.198 in_pcb.c
> --- netinet/in_pcb.c  26 Mar 2016 21:56:04 -0000      1.198
> +++ netinet/in_pcb.c  3 Apr 2016 19:16:37 -0000
> @@ -286,6 +286,7 @@ in_pcbbind(struct inpcb *inp, struct mbu
>       struct socket *so = inp->inp_socket;
>       u_int16_t lport = 0;
>       int wild = 0;
> +     void *laddr = &zeroin46_addr;
>       int error;
>  
>       if (inp->inp_lport)
> @@ -312,9 +313,10 @@ in_pcbbind(struct inpcb *inp, struct mbu
>                       if (sin6->sin6_family != AF_INET6)
>                               return (EAFNOSUPPORT);
>  
> +                     wild |= INPLOOKUP_IPV6;
>                       if ((error = in6_pcbaddrisavail(inp, sin6, wild, p)))
>                               return (error);
> -                     inp->inp_laddr6 = sin6->sin6_addr;
> +                     laddr = &sin6->sin6_addr;
>                       lport = sin6->sin6_port;
>                       break;
>               }
> @@ -332,7 +334,7 @@ in_pcbbind(struct inpcb *inp, struct mbu
>  
>                       if ((error = in_pcbaddrisavail(inp, sin, wild, p)))
>                               return (error);
> -                     inp->inp_laddr = sin->sin_addr;
> +                     laddr = &sin->sin_addr;
>                       lport = sin->sin_port;
>                       break;
>               }
> @@ -342,8 +344,20 @@ in_pcbbind(struct inpcb *inp, struct mbu
>       }
>  
>       if (lport == 0)
> -             if ((error = in_pcbpickport(&lport, wild, inp, p)))
> +             if ((error = in_pcbpickport(&lport, laddr, wild, inp, p)))
>                       return (error);
> +     if (nam) {
> +             switch (sotopf(so)) {
> +#ifdef INET6
> +             case PF_INET6:
> +                     inp->inp_laddr6 = *(struct in6_addr *)laddr;
> +                     break;
> +#endif
> +             case PF_INET:
> +                     inp->inp_laddr = *(struct in_addr *)laddr;
> +                     break;
> +             }
> +     }
>       inp->inp_lport = lport;
>       in_pcbrehash(inp);
>       return (0);
> @@ -418,12 +432,12 @@ in_pcbaddrisavail(struct inpcb *inp, str
>  }
>  
>  int
> -in_pcbpickport(u_int16_t *lport, int wild, struct inpcb *inp, struct proc *p)
> +in_pcbpickport(u_int16_t *lport, void *laddr, int wild, struct inpcb *inp,
> +    struct proc *p)
>  {
>       struct socket *so = inp->inp_socket;
>       struct inpcbtable *table = inp->inp_table;
>       u_int16_t first, last, lower, higher, candidate, localport;
> -     void *laddr;
>       int count;
>  
>       if (inp->inp_flags & INP_HIGHPORT) {
> @@ -453,10 +467,6 @@ in_pcbpickport(u_int16_t *lport, int wil
>  
>       count = higher - lower;
>       candidate = lower + arc4random_uniform(count);
> -     if (sotopf(so) == PF_INET6)
> -             laddr = &inp->inp_laddr6;
> -     else
> -             laddr = &inp->inp_laddr;
>  
>       do {
>               if (count-- < 0)        /* completely used? */
> Index: netinet/in_pcb.h
> ===================================================================
> RCS file: /cvs/src/sys/netinet/in_pcb.h,v
> retrieving revision 1.96
> diff -u -p -r1.96 in_pcb.h
> --- netinet/in_pcb.h  23 Mar 2016 15:50:36 -0000      1.96
> +++ netinet/in_pcb.h  3 Apr 2016 19:16:37 -0000
> @@ -290,6 +290,6 @@ int       in6_pcbnotify(struct inpcbtable *, s
>       u_int, const struct sockaddr_in6 *, u_int, u_int, int, void *,
>       void (*)(struct inpcb *, int));
>  int  in6_selecthlim(struct inpcb *);
> -int  in_pcbpickport(u_int16_t *, int, struct inpcb *, struct proc *);
> +int  in_pcbpickport(u_int16_t *, void *, int, struct inpcb *, struct proc *);
>  #endif /* _KERNEL */
>  #endif /* _NETINET_IN_PCB_H_ */

Reply via email to