> On 5. Jul 2018, at 15:13, Brooks Davis <bro...@freebsd.org> wrote: > > Author: brooks > Date: Thu Jul 5 13:13:48 2018 > New Revision: 335979 > URL: https://svnweb.freebsd.org/changeset/base/335979 > > Log: > Make struct xinpcb and friends word-size independent. > > Replace size_t members with ksize_t (uint64_t) and pointer members > (never used as pointers in userspace, but instead as unique > idenitifiers) with kvaddr_t (uint64_t). This makes the structs > identical between 32-bit and 64-bit ABIs. > > On 64-bit bit systems, the ABI is maintained. On 32-bit systems, > this is an ABI breaking change. The ABI of most of these structs > was previously broken in r315662. This also imposes a small API > change on userspace consumers who must handle kernel pointers > becoming virtual addresses. > > PR: 228301 (exp-run by antoine) > Reviewed by: jtl, kib, rwatson (various versions) > Sponsored by: DARPA, AFRL > Differential Revision: https://reviews.freebsd.org/D15386 > > Modified: > head/UPDATING > head/lib/libkvm/kvm.h > head/sys/kern/kern_descrip.c > head/sys/kern/uipc_socket.c > head/sys/kern/uipc_usrreq.c > head/sys/netinet/in_pcb.c > head/sys/netinet/in_pcb.h > head/sys/netinet/sctp_sysctl.c > head/sys/netinet/sctp_uio.h > head/sys/netinet/tcp_var.h > head/sys/sys/file.h > head/sys/sys/param.h > head/sys/sys/socketvar.h > head/sys/sys/types.h > head/sys/sys/unpcb.h > head/usr.bin/netstat/inet.c > head/usr.bin/netstat/unix.c > head/usr.bin/sockstat/sockstat.c > > Modified: head/UPDATING > ============================================================================== > --- head/UPDATING Thu Jul 5 11:50:59 2018 (r335978) > +++ head/UPDATING Thu Jul 5 13:13:48 2018 (r335979) > @@ -31,6 +31,14 @@ NOTE TO PEOPLE WHO THINK THAT FreeBSD 12.x IS SLOW: > disable the most expensive debugging functionality run > "ln -s 'abort:false,junk:false' /etc/malloc.conf".) > > +20180705: > + The ABI of syscalls used by management tools like sockstat and > + netstat has been broken to allow 32-bit binaries to work on > + 64-bit kernels without modification. These programs will need > + to match the kernel in order to function. External programs may > + require minor modifications to accommodate a change of type in > + structures from pointers to 64-bit virtual addresses. > + > 20180702: > On i386 and amd64 atomics are now inlined. Out of tree modules using > atomics will need to be rebuilt. > > Modified: head/lib/libkvm/kvm.h > ============================================================================== > --- head/lib/libkvm/kvm.h Thu Jul 5 11:50:59 2018 (r335978) > +++ head/lib/libkvm/kvm.h Thu Jul 5 13:13:48 2018 (r335979) > @@ -61,8 +61,6 @@ typedef __ssize_t ssize_t; > #define _SSIZE_T_DECLARED > #endif > > -typedef uint64_t kvaddr_t; /* An address in a target > image. */ > - > struct kvm_nlist { > const char *n_name; > unsigned char n_type; > > Modified: head/sys/kern/kern_descrip.c > ============================================================================== > --- head/sys/kern/kern_descrip.c Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/sys/kern/kern_descrip.c Thu Jul 5 13:13:48 2018 > (r335979) > @@ -3362,10 +3362,10 @@ sysctl_kern_file(SYSCTL_HANDLER_ARGS) > if ((fp = fdp->fd_ofiles[n].fde_file) == NULL) > continue; > xf.xf_fd = n; > - xf.xf_file = fp; > - xf.xf_data = fp->f_data; > - xf.xf_vnode = fp->f_vnode; > - xf.xf_type = fp->f_type; > + xf.xf_file = (kvaddr_t)fp; > + xf.xf_data = (kvaddr_t)fp->f_data; > + xf.xf_vnode = (kvaddr_t)fp->f_vnode; > + xf.xf_type = (kvaddr_t)fp->f_type; > xf.xf_count = fp->f_count; > xf.xf_msgcount = 0; > xf.xf_offset = foffset_get(fp); > > Modified: head/sys/kern/uipc_socket.c > ============================================================================== > --- head/sys/kern/uipc_socket.c Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/sys/kern/uipc_socket.c Thu Jul 5 13:13:48 2018 > (r335979) > @@ -3985,12 +3985,12 @@ sotoxsocket(struct socket *so, struct xsocket *xso) > { > > xso->xso_len = sizeof *xso; > - xso->xso_so = so; > + xso->xso_so = (kvaddr_t)so; > xso->so_type = so->so_type; > xso->so_options = so->so_options; > xso->so_linger = so->so_linger; > xso->so_state = so->so_state; > - xso->so_pcb = so->so_pcb; > + xso->so_pcb = (kvaddr_t)so->so_pcb; > xso->xso_protocol = so->so_proto->pr_protocol; > xso->xso_family = so->so_proto->pr_domain->dom_family; > xso->so_timeo = so->so_timeo; > > Modified: head/sys/kern/uipc_usrreq.c > ============================================================================== > --- head/sys/kern/uipc_usrreq.c Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/sys/kern/uipc_usrreq.c Thu Jul 5 13:13:48 2018 > (r335979) > @@ -1853,7 +1853,7 @@ unp_pcblist(SYSCTL_HANDLER_ARGS) > > if (freeunp == 0 && unp->unp_gencnt <= gencnt) { > xu->xu_len = sizeof *xu; > - xu->xu_unpp = unp; > + xu->xu_unpp = (kvaddr_t)unp; > /* > * XXX - need more locking here to protect against > * connect/disconnect races for SMP. > @@ -1870,10 +1870,10 @@ unp_pcblist(SYSCTL_HANDLER_ARGS) > unp->unp_conn->unp_addr->sun_len); > else > bzero(&xu->xu_caddr, sizeof(xu->xu_caddr)); > - xu->unp_vnode = unp->unp_vnode; > - xu->unp_conn = unp->unp_conn; > - xu->xu_firstref = LIST_FIRST(&unp->unp_refs); > - xu->xu_nextref = LIST_NEXT(unp, unp_reflink); > + xu->unp_vnode = (kvaddr_t)unp->unp_vnode; > + xu->unp_conn = (kvaddr_t)unp->unp_conn; > + xu->xu_firstref = (kvaddr_t)LIST_FIRST(&unp->unp_refs); > + xu->xu_nextref = (kvaddr_t)LIST_NEXT(unp, unp_reflink); > xu->unp_gencnt = unp->unp_gencnt; > sotoxsocket(unp->unp_socket, &xu->xu_socket); > UNP_PCB_UNLOCK(unp); > > Modified: head/sys/netinet/in_pcb.c > ============================================================================== > --- head/sys/netinet/in_pcb.c Thu Jul 5 11:50:59 2018 (r335978) > +++ head/sys/netinet/in_pcb.c Thu Jul 5 13:13:48 2018 (r335979) > @@ -2906,7 +2906,7 @@ in_pcbtoxinpcb(const struct inpcb *inp, struct xinpcb > bzero(&xi->xi_socket, sizeof(struct xsocket)); > bcopy(&inp->inp_inc, &xi->inp_inc, sizeof(struct in_conninfo)); > xi->inp_gencnt = inp->inp_gencnt; > - xi->inp_ppcb = inp->inp_ppcb; > + xi->inp_ppcb = (kvaddr_t)inp->inp_ppcb; > xi->inp_flow = inp->inp_flow; > xi->inp_flowid = inp->inp_flowid; > xi->inp_flowtype = inp->inp_flowtype; > > Modified: head/sys/netinet/in_pcb.h > ============================================================================== > --- head/sys/netinet/in_pcb.h Thu Jul 5 11:50:59 2018 (r335978) > +++ head/sys/netinet/in_pcb.h Thu Jul 5 13:13:48 2018 (r335979) > @@ -366,12 +366,12 @@ struct inpcb { > */ > #ifdef _SYS_SOCKETVAR_H_ > struct xinpcb { > - size_t xi_len; /* length of this structure */ > + ksize_t xi_len; /* length of this structure */ > struct xsocket xi_socket; /* (s,p) */ > struct in_conninfo inp_inc; /* (s,p) */ > uint64_t inp_gencnt; /* (s,p) */ > union { > - void *inp_ppcb; /* (s) netstat(1) */ > + kvaddr_t inp_ppcb; /* (s) netstat(1) */ > int64_t ph_ppcb; > }; > int64_t inp_spare64[4]; > @@ -394,10 +394,12 @@ struct xinpcb { > } __aligned(8); > > struct xinpgen { > - size_t xig_len; /* length of this structure */ > + ksize_t xig_len; /* length of this structure */ > u_int xig_count; /* number of PCBs at this time */ > + uint32_t _xig_spare32; > inp_gen_t xig_gen; /* generation count at this time */ > so_gen_t xig_sogen; /* socket generation count this time */ > + uint64_t _xig_spare64[4]; > } __aligned(8); > #ifdef _KERNEL > void in_pcbtoxinpcb(const struct inpcb *, struct xinpcb *); > > Modified: head/sys/netinet/sctp_sysctl.c > ============================================================================== > --- head/sys/netinet/sctp_sysctl.c Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/sys/netinet/sctp_sysctl.c Thu Jul 5 13:13:48 2018 > (r335979) > @@ -409,7 +409,7 @@ sctp_sysctl_handle_assoclist(SYSCTL_HANDLER_ARGS) > xinpcb.total_recvs = inp->total_recvs; > xinpcb.total_nospaces = inp->total_nospaces; > xinpcb.fragmentation_point = inp->sctp_frag_point; > - xinpcb.socket = inp->sctp_socket; > + xinpcb.socket = (kvaddr_t)inp->sctp_socket; This breaks compilation on 32-bit PPC:
cc -c -O -pipe -g -nostdinc -I. -I../../.. -I../../../contrib/ck/include -I../../../contrib/libfdt -D_KERNEL -DHAVE_KERNEL_OPTION_HEADERS -include opt_global.h -msoft-float -fPIC -fno-omit-frame-pointer -MD -MF.depend.sctp_sysctl.o -MTsctp_sysctl.o -mno-altivec -msoft-float -ffreestanding -fwrapv -fstack-protector -gdwarf-2 -Wall -Wredundant-decls -Wnested-externs -Wstrict-prototypes -Wmissing-prototypes -Wpointer-arith -Wcast-qual -Wundef -Wno-pointer-sign -fformat-extensions -Wmissing-include-dirs -fdiagnostics-show-option -Wno-unknown-pragmas -Wno-uninitialized -fno-common -fms-extensions -finline-limit=15000 --param inline-unit-growth=100 --param large-function-growth=1000 -Wa,-many -std=iso9899:1999 -Werror ../../../netinet/sctp_sysctl.c cc1: warnings being treated as errors ../../../netinet/sctp_sysctl.c: In function 'sctp_sysctl_handle_assoclist': ../../../netinet/sctp_sysctl.c:412: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast] *** Error code 1 Stop. make: stopped in /usr/home/tuexen/head/sys/powerpc/compile/TCP-NODEBUG Best regards Michael > so = inp->sctp_socket; > if ((so == NULL) || > (!SCTP_IS_LISTENING(inp)) || > > Modified: head/sys/netinet/sctp_uio.h > ============================================================================== > --- head/sys/netinet/sctp_uio.h Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/sys/netinet/sctp_uio.h Thu Jul 5 13:13:48 2018 > (r335979) > @@ -1175,14 +1175,11 @@ struct xsctp_inpcb { > uint16_t local_port; > uint16_t qlen_old; > uint16_t maxqlen_old; > - void *socket; > + uint16_t __spare16; > + kvaddr_t socket; > uint32_t qlen; > uint32_t maxqlen; > -#if defined(__LP64__) > - uint32_t extra_padding[27]; /* future */ > -#else > - uint32_t extra_padding[28]; /* future */ > -#endif > + uint32_t extra_padding[26]; /* future */ > }; > > struct xsctp_tcb { > > Modified: head/sys/netinet/tcp_var.h > ============================================================================== > --- head/sys/netinet/tcp_var.h Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/sys/netinet/tcp_var.h Thu Jul 5 13:13:48 2018 > (r335979) > @@ -677,7 +677,7 @@ void hhook_run_tcp_est_out(struct tcpcb *tp, > */ > #if defined(_NETINET_IN_PCB_H_) && defined(_SYS_SOCKETVAR_H_) > struct xtcpcb { > - size_t xt_len; /* length of this structure */ > + ksize_t xt_len; /* length of this structure */ > struct xinpcb xt_inp; > char xt_stack[TCP_FUNCTION_NAME_LEN_MAX]; /* (s) */ > char xt_logid[TCP_LOG_ID_LEN]; /* (s) */ > > Modified: head/sys/sys/file.h > ============================================================================== > --- head/sys/sys/file.h Thu Jul 5 11:50:59 2018 (r335978) > +++ head/sys/sys/file.h Thu Jul 5 13:13:48 2018 (r335979) > @@ -209,18 +209,23 @@ struct file { > * Userland version of struct file, for sysctl > */ > struct xfile { > - size_t xf_size; /* size of struct xfile */ > + ksize_t xf_size; /* size of struct xfile */ > pid_t xf_pid; /* owning process */ > uid_t xf_uid; /* effective uid of owning process */ > int xf_fd; /* descriptor number */ > - void *xf_file; /* address of struct file */ > + int _xf_int_pad1; > + kvaddr_t xf_file; /* address of struct file */ > short xf_type; /* descriptor type */ > + short _xf_short_pad1; > int xf_count; /* reference count */ > int xf_msgcount; /* references from message queue */ > + int _xf_int_pad2; > off_t xf_offset; /* file offset */ > - void *xf_data; /* file descriptor specific data */ > - void *xf_vnode; /* vnode pointer */ > + kvaddr_t xf_data; /* file descriptor specific data */ > + kvaddr_t xf_vnode; /* vnode pointer */ > u_int xf_flag; /* flags (see fcntl.h) */ > + int _xf_int_pad3; > + int64_t _xf_int64_pad[6]; > }; > > #ifdef _KERNEL > > Modified: head/sys/sys/param.h > ============================================================================== > --- head/sys/sys/param.h Thu Jul 5 11:50:59 2018 (r335978) > +++ head/sys/sys/param.h Thu Jul 5 13:13:48 2018 (r335979) > @@ -60,7 +60,7 @@ > * in the range 5 to 9. > */ > #undef __FreeBSD_version > -#define __FreeBSD_version 1200071 /* Master, propagated to newvers */ > +#define __FreeBSD_version 1200072 /* Master, propagated to newvers */ > > /* > * __FreeBSD_kernel__ indicates that this system uses the kernel of FreeBSD, > > Modified: head/sys/sys/socketvar.h > ============================================================================== > --- head/sys/sys/socketvar.h Thu Jul 5 11:50:59 2018 (r335978) > +++ head/sys/sys/socketvar.h Thu Jul 5 13:13:48 2018 (r335979) > @@ -474,13 +474,13 @@ int accept_filt_generic_mod_event(module_t mod, int > ev > * Structure to export socket from kernel to utilities, via sysctl(3). > */ > struct xsocket { > - size_t xso_len; /* length of this structure */ > + ksize_t xso_len; /* length of this structure */ > union { > - void *xso_so; /* kernel address of struct socket */ > + kvaddr_t xso_so; /* kernel address of struct socket */ > int64_t ph_so; > }; > union { > - void *so_pcb; /* kernel address of struct inpcb */ > + kvaddr_t so_pcb; /* kernel address of struct inpcb */ > int64_t ph_pcb; > }; > uint64_t so_oobmark; > > Modified: head/sys/sys/types.h > ============================================================================== > --- head/sys/sys/types.h Thu Jul 5 11:50:59 2018 (r335978) > +++ head/sys/sys/types.h Thu Jul 5 13:13:48 2018 (r335979) > @@ -251,6 +251,15 @@ struct cap_rights; > typedef struct cap_rights cap_rights_t; > #endif > > +/* > + * Types suitable for exporting size and pointers (as virtual addresses) > + * from the kernel independent of native word size. These should be > + * used in place of size_t and (u)intptr_t in structs which contain such > + * types that are shared with userspace. > + */ > +typedef __uint64_t kvaddr_t; > +typedef __uint64_t ksize_t; > + > typedef __vm_offset_t vm_offset_t; > typedef __int64_t vm_ooffset_t; > typedef __vm_paddr_t vm_paddr_t; > > Modified: head/sys/sys/unpcb.h > ============================================================================== > --- head/sys/sys/unpcb.h Thu Jul 5 11:50:59 2018 (r335978) > +++ head/sys/sys/unpcb.h Thu Jul 5 13:13:48 2018 (r335979) > @@ -138,12 +138,12 @@ struct unpcb { > */ > #ifdef _SYS_SOCKETVAR_H_ > struct xunpcb { > - size_t xu_len; /* length of this structure */ > - void *xu_unpp; /* to help netstat, fstat */ > - void *unp_vnode; /* (s) */ > - void *unp_conn; /* (s) */ > - void *xu_firstref; /* (s) */ > - void *xu_nextref; /* (s) */ > + ksize_t xu_len; /* length of this structure */ > + kvaddr_t xu_unpp; /* to help netstat, fstat */ > + kvaddr_t unp_vnode; /* (s) */ > + kvaddr_t unp_conn; /* (s) */ > + kvaddr_t xu_firstref; /* (s) */ > + kvaddr_t xu_nextref; /* (s) */ > unp_gen_t unp_gencnt; /* (s) */ > int64_t xu_spare64[8]; > int32_t xu_spare32[8]; > @@ -159,7 +159,7 @@ struct xunpcb { > } __aligned(8); > > struct xunpgen { > - size_t xug_len; > + ksize_t xug_len; > u_int xug_count; > unp_gen_t xug_gen; > so_gen_t xug_sogen; > > Modified: head/usr.bin/netstat/inet.c > ============================================================================== > --- head/usr.bin/netstat/inet.c Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/usr.bin/netstat/inet.c Thu Jul 5 13:13:48 2018 > (r335979) > @@ -159,12 +159,12 @@ sotoxsocket(struct socket *so, struct xsocket *xso) > > bzero(xso, sizeof *xso); > xso->xso_len = sizeof *xso; > - xso->xso_so = so; > + xso->xso_so = (kvaddr_t)so; > xso->so_type = so->so_type; > xso->so_options = so->so_options; > xso->so_linger = so->so_linger; > xso->so_state = so->so_state; > - xso->so_pcb = so->so_pcb; > + xso->so_pcb = (kvaddr_t)so->so_pcb; > if (kread((uintptr_t)so->so_proto, &proto, sizeof(proto)) != 0) > return (-1); > xso->xso_protocol = proto.pr_protocol; > > Modified: head/usr.bin/netstat/unix.c > ============================================================================== > --- head/usr.bin/netstat/unix.c Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/usr.bin/netstat/unix.c Thu Jul 5 13:13:48 2018 > (r335979) > @@ -153,7 +153,7 @@ pcblist_kvm(u_long count_off, u_long gencnt_off, u_lon > xu.xu_len = sizeof xu; > KREAD(head_off, &head, sizeof(head)); > LIST_FOREACH(unp, &head, unp_link) { > - xu.xu_unpp = unp; > + xu.xu_unpp = (kvaddr_t)unp; > KREAD(unp, &unp0, sizeof (*unp)); > unp = &unp0; > > > Modified: head/usr.bin/sockstat/sockstat.c > ============================================================================== > --- head/usr.bin/sockstat/sockstat.c Thu Jul 5 11:50:59 2018 > (r335978) > +++ head/usr.bin/sockstat/sockstat.c Thu Jul 5 13:13:48 2018 > (r335979) > @@ -108,8 +108,8 @@ struct addr { > }; > > struct sock { > - void *socket; > - void *pcb; > + kvaddr_t socket; > + kvaddr_t pcb; > int shown; > int vflag; > int family; > @@ -789,8 +789,8 @@ gather_unix(int proto) > warnx("struct xunpcb size mismatch"); > goto out; > } > - if ((xup->unp_conn == NULL && !opt_l) || > - (xup->unp_conn != NULL && !opt_c)) > + if ((xup->unp_conn == 0 && !opt_l) || > + (xup->unp_conn != 0 && !opt_c)) > continue; > if ((sock = calloc(1, sizeof(*sock))) == NULL) > err(1, "malloc()"); > @@ -806,8 +806,8 @@ gather_unix(int proto) > if (xup->xu_addr.sun_family == AF_UNIX) > laddr->address = > *(struct sockaddr_storage *)(void *)&xup->xu_addr; > - else if (xup->unp_conn != NULL) > - *(void **)&(faddr->address) = xup->unp_conn; > + else if (xup->unp_conn != 0) > + *(kvaddr_t*)&(faddr->address) = xup->unp_conn; > laddr->next = NULL; > faddr->next = NULL; > sock->laddr = laddr; > @@ -1008,7 +1008,7 @@ sctp_path_state(int state) > static void > displaysock(struct sock *s, int pos) > { > - void *p; > + kvaddr_t p; > int hash, first, offset; > struct addr *laddr, *faddr; > struct sock *s_tmp; > @@ -1054,8 +1054,8 @@ displaysock(struct sock *s, int pos) > break; > } > /* client */ > - p = *(void **)&(faddr->address); > - if (p == NULL) { > + p = *(kvaddr_t*)&(faddr->address); > + if (p == 0) { > pos += xprintf("(not connected)"); > offset += opt_w ? 92 : 44; > break; > @@ -1174,13 +1174,13 @@ display(void) > } > setpassent(1); > for (xf = xfiles, n = 0; n < nxfiles; ++n, ++xf) { > - if (xf->xf_data == NULL) > + if (xf->xf_data == 0) > continue; > if (opt_j >= 0 && opt_j != getprocjid(xf->xf_pid)) > continue; > hash = (int)((uintptr_t)xf->xf_data % HASHSIZE); > for (s = sockhash[hash]; s != NULL; s = s->next) { > - if ((void *)s->socket != xf->xf_data) > + if (s->socket != xf->xf_data) > continue; > if (!check_ports(s)) > continue; > _______________________________________________ svn-src-head@freebsd.org mailing list https://lists.freebsd.org/mailman/listinfo/svn-src-head To unsubscribe, send any mail to "svn-src-head-unsubscr...@freebsd.org"