On Mon, Mar 21, 2022 at 02:17:21PM +1000, David Gwynne wrote:
> in_pcbselsrc has this:
> 
>               ifp = if_get(mopts->imo_ifidx);
>               if (ifp != NULL) {
>                       if (ifp->if_rdomain == rtable_l2(rtableid))
>                               IFP_TO_IA(ifp, ia);
>                       if (ia == NULL) {
>                               if_put(ifp);
>                               return (EADDRNOTAVAIL);
>                       }
> 
>                       *insrc = ia->ia_addr.sin_addr;
>                       if_put(ifp);
>                       return (0);
>               }
> 
> which looks very much like it releases a reference to the interface
> holding the address it's passing back to the caller to use.
> 
> this diff has it copy the address to memory the caller provides instead.
> 
> ok?

I think this is a good time to commit this. OK claudio@
 
> Index: in_pcb.c
> ===================================================================
> RCS file: /cvs/src/sys/netinet/in_pcb.c,v
> retrieving revision 1.262
> diff -u -p -r1.262 in_pcb.c
> --- in_pcb.c  21 Mar 2022 03:51:09 -0000      1.262
> +++ in_pcb.c  21 Mar 2022 04:10:24 -0000
> @@ -476,7 +476,7 @@ in_pcbpickport(u_int16_t *lport, void *l
>  int
>  in_pcbconnect(struct inpcb *inp, struct mbuf *nam)
>  {
> -     struct in_addr *ina = NULL;
> +     struct in_addr ina;
>       struct sockaddr_in *sin;
>       int error;
>  
> @@ -495,7 +495,7 @@ in_pcbconnect(struct inpcb *inp, struct 
>               return (error);
>  
>       if (in_pcbhashlookup(inp->inp_table, sin->sin_addr, sin->sin_port,
> -         *ina, inp->inp_lport, inp->inp_rtableid) != NULL)
> +         ina, inp->inp_lport, inp->inp_rtableid) != NULL)
>               return (EADDRINUSE);
>  
>       KASSERT(inp->inp_laddr.s_addr == INADDR_ANY || inp->inp_lport);
> @@ -506,13 +506,13 @@ in_pcbconnect(struct inpcb *inp, struct 
>                       if (error)
>                               return (error);
>                       if (in_pcbhashlookup(inp->inp_table, sin->sin_addr,
> -                         sin->sin_port, *ina, inp->inp_lport,
> +                         sin->sin_port, ina, inp->inp_lport,
>                           inp->inp_rtableid) != NULL) {
>                               inp->inp_lport = 0;
>                               return (EADDRINUSE);
>                       }
>               }
> -             inp->inp_laddr = *ina;
> +             inp->inp_laddr = ina;
>       }
>       inp->inp_faddr = sin->sin_addr;
>       inp->inp_fport = sin->sin_port;
> @@ -870,7 +870,7 @@ in_pcbrtentry(struct inpcb *inp)
>   * an entry to the caller for later use.
>   */
>  int
> -in_pcbselsrc(struct in_addr **insrc, struct sockaddr_in *sin,
> +in_pcbselsrc(struct in_addr *insrc, struct sockaddr_in *sin,
>      struct inpcb *inp)
>  {
>       struct ip_moptions *mopts = inp->inp_moptions;
> @@ -886,9 +886,9 @@ in_pcbselsrc(struct in_addr **insrc, str
>        * If the socket(if any) is already bound, use that bound address
>        * unless it is INADDR_ANY or INADDR_BROADCAST.
>        */
> -     if (laddr && laddr->s_addr != INADDR_ANY &&
> +     if (laddr->s_addr != INADDR_ANY &&
>           laddr->s_addr != INADDR_BROADCAST) {
> -             *insrc = laddr;
> +             *insrc = *laddr;
>               return (0);
>       }
>  
> @@ -911,7 +911,7 @@ in_pcbselsrc(struct in_addr **insrc, str
>                               return (EADDRNOTAVAIL);
>                       }
>  
> -                     *insrc = &ia->ia_addr.sin_addr;
> +                     *insrc = ia->ia_addr.sin_addr;
>                       if_put(ifp);
>                       return (0);
>               }
> @@ -962,7 +962,7 @@ in_pcbselsrc(struct in_addr **insrc, str
>                       struct ifaddr *ifa;
>                       if ((ifa = ifa_ifwithaddr(ip4_source, rtableid)) !=
>                           NULL && ISSET(ifa->ifa_ifp->if_flags, IFF_UP)) {
> -                             *insrc = &satosin(ip4_source)->sin_addr;
> +                             *insrc = satosin(ip4_source)->sin_addr;
>                               return (0);
>                       }
>               }
> @@ -971,7 +971,7 @@ in_pcbselsrc(struct in_addr **insrc, str
>       if (ia == NULL)
>               return (EADDRNOTAVAIL);
>  
> -     *insrc = &ia->ia_addr.sin_addr;
> +     *insrc = ia->ia_addr.sin_addr;
>       return (0);
>  }
>  
> Index: in_pcb.h
> ===================================================================
> RCS file: /cvs/src/sys/netinet/in_pcb.h,v
> retrieving revision 1.125
> diff -u -p -r1.125 in_pcb.h
> --- in_pcb.h  14 Mar 2022 22:38:43 -0000      1.125
> +++ in_pcb.h  21 Mar 2022 04:10:25 -0000
> @@ -305,7 +305,7 @@ void       in_setpeeraddr(struct inpcb *, str
>  void  in_setsockaddr(struct inpcb *, struct mbuf *);
>  int   in_baddynamic(u_int16_t, u_int16_t);
>  int   in_rootonly(u_int16_t, u_int16_t);
> -int   in_pcbselsrc(struct in_addr **, struct sockaddr_in *, struct inpcb *);
> +int   in_pcbselsrc(struct in_addr *, struct sockaddr_in *, struct inpcb *);
>  struct rtentry *
>       in_pcbrtentry(struct inpcb *);
>  
> Index: udp_usrreq.c
> ===================================================================
> RCS file: /cvs/src/sys/netinet/udp_usrreq.c,v
> retrieving revision 1.274
> diff -u -p -r1.274 udp_usrreq.c
> --- udp_usrreq.c      14 Mar 2022 22:38:43 -0000      1.274
> +++ udp_usrreq.c      21 Mar 2022 04:10:25 -0000
> @@ -857,7 +857,7 @@ udp_output(struct inpcb *inp, struct mbu
>       u_int32_t ipsecflowinfo = 0;
>       struct sockaddr_in src_sin;
>       int len = m->m_pkthdr.len;
> -     struct in_addr *laddr;
> +     struct in_addr laddr;
>       int error = 0;
>  
>  #ifdef DIAGNOSTIC
> @@ -957,14 +957,14 @@ udp_output(struct inpcb *inp, struct mbu
>                           (error =
>                           in_pcbaddrisavail(inp, &src_sin, 0, curproc)))
>                               goto release;
> -                     laddr = &src_sin.sin_addr;
> +                     laddr = src_sin.sin_addr;
>               }
>       } else {
>               if (inp->inp_faddr.s_addr == INADDR_ANY) {
>                       error = ENOTCONN;
>                       goto release;
>               }
> -             laddr = &inp->inp_laddr;
> +             laddr = inp->inp_laddr;
>       }
>  
>       /*
> @@ -985,7 +985,7 @@ udp_output(struct inpcb *inp, struct mbu
>       bzero(ui->ui_x1, sizeof ui->ui_x1);
>       ui->ui_pr = IPPROTO_UDP;
>       ui->ui_len = htons((u_int16_t)len + sizeof (struct udphdr));
> -     ui->ui_src = *laddr;
> +     ui->ui_src = laddr;
>       ui->ui_dst = sin ? sin->sin_addr : inp->inp_faddr;
>       ui->ui_sport = inp->inp_lport;
>       ui->ui_dport = sin ? sin->sin_port : inp->inp_fport;
> Index: raw_ip.c
> ===================================================================
> RCS file: /cvs/src/sys/netinet/raw_ip.c,v
> retrieving revision 1.124
> diff -u -p -r1.124 raw_ip.c
> --- raw_ip.c  21 Mar 2022 04:00:56 -0000      1.124
> +++ raw_ip.c  21 Mar 2022 04:10:25 -0000
> @@ -271,13 +271,9 @@ rip_output(struct mbuf *m, struct socket
>       }
>  
>       if (ip->ip_src.s_addr == INADDR_ANY) {
> -             struct in_addr *laddr;
> -
> -             error = in_pcbselsrc(&laddr, dst, inp);
> +             error = in_pcbselsrc(&ip->ip_src, dst, inp);
>               if (error != 0)
>                       return (error);
> -
> -             ip->ip_src = *laddr;
>       }
>  
>  #ifdef INET6
> 

-- 
:wq Claudio

Reply via email to