Date: Sun, 8 Mar 2020 19:02:31 +0000 (UTC) From: Rick Macklem <rmacklem@FreeBSD.org> To: src-committers@freebsd.org, svn-src-projects@freebsd.org Subject: svn commit: r358770 - projects/nfs-over-tls/sys/fs/nfs Message-ID: <202003081902.028J2VPG036166@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: rmacklem Date: Sun Mar 8 19:02:30 2020 New Revision: 358770 URL: https://svnweb.freebsd.org/changeset/base/358770 Log: Add support for reception of ext_pgs mbuf chains to the common NFS code. Also, simplify the check for ext_pgs mbufs to just test for M_NOMAP. Get rid of a couple of functions that are no longer needed. And fix newnfs_realign() so that it works for ext_pgs mbufs. Modified: projects/nfs-over-tls/sys/fs/nfs/nfs_commonkrpc.c projects/nfs-over-tls/sys/fs/nfs/nfs_commonport.c projects/nfs-over-tls/sys/fs/nfs/nfs_commonsubs.c projects/nfs-over-tls/sys/fs/nfs/nfs_var.h Modified: projects/nfs-over-tls/sys/fs/nfs/nfs_commonkrpc.c ============================================================================== --- projects/nfs-over-tls/sys/fs/nfs/nfs_commonkrpc.c Sun Mar 8 18:54:59 2020 (r358769) +++ projects/nfs-over-tls/sys/fs/nfs/nfs_commonkrpc.c Sun Mar 8 19:02:30 2020 (r358770) @@ -898,11 +898,9 @@ tryagain: * These could cause pointer alignment problems, so copy them to * well aligned mbufs. */ -#ifdef notnow newnfs_realign(&nd->nd_mrep, M_WAITOK); -#endif nd->nd_md = nd->nd_mrep; - nfsm_set(nd, false); + nfsm_set(nd, ext.rc_mbufoffs, false); nd->nd_repstat = 0; if (nd->nd_procnum != NFSPROC_NULL && nd->nd_procnum != NFSV4PROC_CBNULL) { Modified: projects/nfs-over-tls/sys/fs/nfs/nfs_commonport.c ============================================================================== --- projects/nfs-over-tls/sys/fs/nfs/nfs_commonport.c Sun Mar 8 18:54:59 2020 (r358769) +++ projects/nfs-over-tls/sys/fs/nfs/nfs_commonport.c Sun Mar 8 19:02:30 2020 (r358770) @@ -180,8 +180,34 @@ newnfs_realign(struct mbuf **pm, int how) { struct mbuf *m, *n; int off, space; + bool copyit; ++nfs_realign_test; + + /* + * For ext_pgs mbufs, just copy the entire chain if there is an + * alignment problem. + */ + copyit = false; + m = *pm; + while ((m->m_flags & M_NOMAP) != 0) { + if ((m->m_len & 0x3) != 0 || + (m->m_ext.ext_pgs->first_pg_off & 0x3) != 0) { + copyit = true; + break; + } + m = m->m_next; + if (m == NULL) + return (0); + } + if (copyit) { + m = mb_unmapped_to_ext(*pm); + if (m == NULL) + return (ENOMEM); + *pm = m; + return (0); + } + while ((m = *pm) != NULL) { if ((m->m_len & 0x3) || (mtod(m, intptr_t) & 0x3)) { /* Modified: projects/nfs-over-tls/sys/fs/nfs/nfs_commonsubs.c ============================================================================== --- projects/nfs-over-tls/sys/fs/nfs/nfs_commonsubs.c Sun Mar 8 18:54:59 2020 (r358769) +++ projects/nfs-over-tls/sys/fs/nfs/nfs_commonsubs.c Sun Mar 8 19:02:30 2020 (r358770) @@ -383,7 +383,7 @@ nfscl_reqstart(struct nfsrv_descript *nd, int procnum, mb = mb_alloc_ext_plus_pages(PAGE_SIZE, M_WAITOK, false, mb_free_mext_pgs); nd->nd_mreq = nd->nd_mb = mb; - nfsm_set(nd, true); + nfsm_set(nd, 0, true); } else { if (nfs_bigrequest[procnum]) NFSMCLGET(mb, M_WAITOK); @@ -656,8 +656,7 @@ nfsm_mbufuio(struct nfsrv_descript *nd, struct uio *ui left = siz; uiosiz = left; while (left > 0) { - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP)) + if ((nd->nd_md->m_flags & M_NOMAP) != 0) xfer = nfsm_copyfrommbuf_extpgs(nd, uiocp, uiop->uio_segflg, left); else @@ -708,15 +707,14 @@ nfsm_dissct(struct nfsrv_descript *nd, int siz, int ho caddr_t retp; retp = NULL; - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP)) + if ((nd->nd_md->m_flags & M_NOMAP) != 0) left = nd->nd_dextpgsiz; else left = mtod(nd->nd_md, char *) + nd->nd_md->m_len - nd->nd_dpos; while (left == 0) { - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP) && nd->nd_dextpg < + if ((nd->nd_md->m_flags & M_NOMAP) != 0 && + nd->nd_dextpg < nd->nd_md->m_ext.ext_pgs->npgs - 1) { pgs = nd->nd_md->m_ext.ext_pgs; nd->nd_dextpg++; @@ -730,15 +728,13 @@ nfsm_dissct(struct nfsrv_descript *nd, int siz, int ho if (left >= siz) { retp = nd->nd_dpos; nd->nd_dpos += siz; - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP)) + if ((nd->nd_md->m_flags & M_NOMAP) != 0) nd->nd_dextpgsiz -= siz; } else if (siz > ncl_mbuf_mhlen) { panic("nfs S too big"); } else { /* Make sure an ext_pgs mbuf is at the last page. */ - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP)) { + if ((nd->nd_md->m_flags & M_NOMAP) != 0) { if (nd->nd_dextpg < nd->nd_md->m_ext.ext_pgs->npgs - 1) { mp2 = nfsm_splitatpgno(nd->nd_md, @@ -775,9 +771,8 @@ nfsm_dissct(struct nfsrv_descript *nd, int siz, int ho while (siz2 > 0) { if (nd->nd_md == NULL) return (NULL); - nfsm_set(nd, false); - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP)) + nfsm_set(nd, 0, false); + if ((nd->nd_md->m_flags & M_NOMAP) != 0) xfer = nfsm_copyfrommbuf_extpgs(nd, p, UIO_SYSSPACE, siz2); else @@ -819,8 +814,7 @@ nfsm_advance(struct nfsrv_descript *nd, int offs, int * If left == -1, calculate it here. */ if (left == -1) { - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP)) + if ((nd->nd_md->m_flags & M_NOMAP) != 0) left = nd->nd_dextpgsiz; else left = mtod(nd->nd_md, char *) + @@ -831,8 +825,8 @@ nfsm_advance(struct nfsrv_descript *nd, int offs, int * Loop around, advancing over the mbuf data. */ while (offs > left) { - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP) && nd->nd_dextpg < + if ((nd->nd_md->m_flags & M_NOMAP) != 0 && + nd->nd_dextpg < nd->nd_md->m_ext.ext_pgs->npgs - 1) { xfer = nfsm_copyfrommbuf_extpgs(nd, NULL, UIO_SYSSPACE, offs); @@ -846,8 +840,7 @@ nfsm_advance(struct nfsrv_descript *nd, int offs, int } } if (offs > 0) { - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP)) + if ((nd->nd_md->m_flags & M_NOMAP) != 0) nfsm_copyfrommbuf_extpgs(nd, NULL, UIO_SYSSPACE, offs); else @@ -1104,13 +1097,12 @@ nfsm_trimtrailing(struct nfsrv_descript *nd, struct mb struct mbuf_ext_pgs *pgs; vm_page_t pg; int fullpgsiz, i; - char *ppos; if (mb->m_next != NULL) { m_freem(mb->m_next); mb->m_next = NULL; } - if ((mb->m_flags & (M_EXT | M_NOMAP)) == (M_EXT | M_NOMAP)) { + if ((mb->m_flags & M_NOMAP) != 0) { pgs = mb->m_ext.ext_pgs; /* First, get rid of any pages after this position. */ for (i = pgs->npgs - 1; i > bextpg; i--) { @@ -1127,10 +1119,6 @@ nfsm_trimtrailing(struct nfsrv_descript *nd, struct mb mb->m_len = mbuf_ext_pg_len(pgs, 0, pgs->first_pg_off); for (i = 1; i < pgs->npgs; i++) mb->m_len += mbuf_ext_pg_len(pgs, i, 0); - ppos = (char *)(void *)PHYS_TO_DMAP(pgs->pa[bextpg]); - ppos += pgs->last_pg_len; - if (ppos != bpos) - printf("EEK trimtrail\n"); nd->nd_bextpgsiz = bextpgsiz; nd->nd_bextpg = bextpg; } else @@ -2492,8 +2480,7 @@ nfsrv_mtostr(struct nfsrv_descript *nd, char *str, int rem = NFSM_RNDUP(siz) - siz; while (siz > 0) { - if ((nd->nd_md->m_flags & (M_EXT | M_NOMAP)) == - (M_EXT | M_NOMAP)) + if ((nd->nd_md->m_flags & M_NOMAP) != 0) xfer = nfsm_copyfrommbuf_extpgs(nd, str, UIO_SYSSPACE, siz); else @@ -4892,7 +4879,7 @@ nfsv4_findmirror(struct nfsmount *nmp) * The build argument is true for build and false for dissect. */ int -nfsm_set(struct nfsrv_descript *nd, bool build) +nfsm_set(struct nfsrv_descript *nd, u_int offs, bool build) { struct mbuf *m; struct mbuf_ext_pgs *pgs; @@ -4902,29 +4889,68 @@ nfsm_set(struct nfsrv_descript *nd, bool build) m = nd->nd_mb; else m = nd->nd_md; - if ((m->m_flags & (M_EXT | M_NOMAP)) == (M_EXT | M_NOMAP)) { + if ((m->m_flags & M_NOMAP) != 0) { if (build) { pgs = m->m_ext.ext_pgs; - nd->nd_bpos = (char *)(void *) - PHYS_TO_DMAP(pgs->pa[0]); - nd->nd_bpos += pgs->first_pg_off; nd->nd_bextpg = 0; - /* For build, set the size that can be filled. */ - rlen = nd->nd_bextpgsiz = PAGE_SIZE - - pgs->first_pg_off; + while (offs > 0) { + if (nd->nd_bextpg == 0) + rlen = mbuf_ext_pg_len(pgs, 0, + pgs->first_pg_off); + else + rlen = mbuf_ext_pg_len(pgs, + nd->nd_bextpg, 0); + if (offs <= rlen) + break; + offs -= rlen; + nd->nd_bextpg++; + if (nd->nd_bextpg == pgs->npgs) { + printf("nfsm_set: build offs " + "out of range\n"); + nd->nd_bextpg--; + break; + } + } + nd->nd_bpos = (char *)(void *) + PHYS_TO_DMAP(pgs->pa[nd->nd_bextpg]); + if (nd->nd_bextpg == 0) + nd->nd_bpos += pgs->first_pg_off; + if (offs > 0) { + nd->nd_bpos += offs; + rlen = nd->nd_bextpgsiz = rlen - offs; + } else if (nd->nd_bextpg == 0) + rlen = nd->nd_bextpgsiz = PAGE_SIZE - + pgs->first_pg_off; + else + rlen = nd->nd_bextpgsiz = PAGE_SIZE; } else { pgs = m->m_ext.ext_pgs; - nd->nd_dpos = (char *)(void *) - PHYS_TO_DMAP(pgs->pa[0]); - nd->nd_dpos += pgs->first_pg_off; nd->nd_dextpg = 0; - /* For dissect, set the size already filled. */ - rlen = nd->nd_dextpgsiz = mbuf_ext_pg_len(pgs, 0, - pgs->first_pg_off); + do { + nd->nd_dpos = (char *)(void *) + PHYS_TO_DMAP(pgs->pa[nd->nd_dextpg]); + if (nd->nd_dextpg == 0) { + nd->nd_dpos += pgs->first_pg_off; + rlen = nd->nd_dextpgsiz = + mbuf_ext_pg_len(pgs, 0, + pgs->first_pg_off); + } else + rlen = nd->nd_dextpgsiz = + mbuf_ext_pg_len(pgs, + nd->nd_dextpg, 0); + if (offs > rlen) { + nd->nd_dextpg++; + offs -= rlen; + } else if (offs > 0) { + nd->nd_dpos += offs; + nd->nd_dextpgsiz -= offs; + offs = 0; + } + } while (offs > 0); } } else if (build) { - nd->nd_bpos = mtod(m, char *); - rlen = m->m_len; + nd->nd_bpos = mtod(m, char *) + offs; + rlen = m->m_len - offs; } else { nd->nd_dpos = mtod(m, char *); rlen = m->m_len; @@ -5026,6 +5052,7 @@ nfsm_splitatpgno(struct mbuf *mp, int pgno, int how) if (m == NULL) return (m); pgs0 = m->m_ext.ext_pgs; + pgs0->flags |= MBUF_PEXT_FLAG_ANON; /* Move the pages beyond pgno to the new mbuf. */ for (i = pgno + 1, j = 0; i < pgs->npgs; i++, j++) @@ -5066,7 +5093,7 @@ nfsm_shiftnext(struct nfsrv_descript *nd, int *leftp) nd->nd_md = nd->nd_md->m_next; if (nd->nd_md == NULL) return (false); - *leftp = nfsm_set(nd, false); + *leftp = nfsm_set(nd, 0, false); return (true); } @@ -5105,70 +5132,28 @@ nfsm_add_ext_pgs(struct mbuf *m, int maxextsiz, int *b } /* - * Trim the ext_pgs mbuf to the current dissect position. + * Calculate the data offset of m for dextpg and dextpgsiz. */ -void -nfsm_trimatpos_extpgs(struct nfsrv_descript *nd) +int +nfsm_extpgs_calc_offs(struct mbuf *m, int dextpg, int dextpgsiz) { struct mbuf_ext_pgs *pgs; - vm_page_t pg; - int i, j; + int cnt, offs; - pgs = nd->nd_md->m_ext.ext_pgs; - for (i = 0; i < nd->nd_dextpg; i++) { - pg = PHYS_TO_VM_PAGE(pgs->pa[0]); - vm_page_unwire_noq(pg); - vm_page_free(pg); - nd->nd_md->m_len -= mbuf_ext_pg_len(pgs, i, - pgs->first_pg_off); - pgs->first_pg_off = 0; - for (j = 0; j < pgs->npgs - 1; j++) - pgs->pa[j] = pgs->pa[j + 1]; - pgs->npgs--; - } - nd->nd_dextpg = 0; - if (nd->nd_dextpgsiz > 0) { - j = mbuf_ext_pg_len(pgs, 0, pgs->first_pg_off); - j -= nd->nd_dextpgsiz; - pgs->first_pg_off += j; - nd->nd_md->m_len -= j; - if (nd->nd_dextpg == pgs->npgs - 1) - pgs->last_pg_len -= j; - } -} - -/* - * Trim the ext_pgs mbuf back to "tlen" bytes in length. - */ -void -nfsm_trimback_extpgs(struct mbuf *m, int len) -{ - struct mbuf_ext_pgs *pgs; - vm_page_t pg; - int i, j, pgno, tlen; - + offs = 0; pgs = m->m_ext.ext_pgs; - pgno = 0; - tlen = len; - while (len > 0 && pgno < pgs->npgs) { - if (pgno == 0) - i = mbuf_ext_pg_len(pgs, pgno, + for (cnt = 0; cnt < dextpg; cnt++) { + if (cnt == 0) + offs += mbuf_ext_pg_len(pgs, 0, pgs->first_pg_off); else - i = mbuf_ext_pg_len(pgs, pgno, 0); - if (len <= i) { - /* Free pages past pgno. */ - for (j = pgno + 1; j < pgs->npgs; j++) { - pg = PHYS_TO_VM_PAGE(pgs->pa[j]); - vm_page_unwire_noq(pg); - vm_page_free(pg); - } - pgs->npgs = pgno + 1; - pgs->last_pg_len = len; - } - len -= i; - pgno++; + offs += mbuf_ext_pg_len(pgs, cnt, 0); } - m->m_len = tlen; + if (dextpg == 0) + cnt = mbuf_ext_pg_len(pgs, 0, + pgs->first_pg_off); + else + cnt = mbuf_ext_pg_len(pgs, dextpg, 0); + offs += cnt - dextpgsiz; + return (offs); } - Modified: projects/nfs-over-tls/sys/fs/nfs/nfs_var.h ============================================================================== --- projects/nfs-over-tls/sys/fs/nfs/nfs_var.h Sun Mar 8 18:54:59 2020 (r358769) +++ projects/nfs-over-tls/sys/fs/nfs/nfs_var.h Sun Mar 8 19:02:30 2020 (r358770) @@ -361,14 +361,13 @@ int nfsv4_sequencelookup(struct nfsmount *, struct nfs void nfsv4_freeslot(struct nfsclsession *, int); struct ucred *nfsrv_getgrpscred(struct ucred *); struct nfsdevice *nfsv4_findmirror(struct nfsmount *); -int nfsm_set(struct nfsrv_descript *, bool); +int nfsm_set(struct nfsrv_descript *, u_int, bool); bool nfsm_shiftnext(struct nfsrv_descript *, int *); -void nfsm_trimatpos_extpgs(struct nfsrv_descript *); -void nfsm_trimback_extpgs(struct mbuf *, int); +int nfsm_extpgs_calc_offs(struct mbuf *, int, int); /* nfs_clcomsubs.c */ void nfsm_uiombuf(struct nfsrv_descript *, struct uio *, int); -struct mbuf *nfsm_uiombuflist(int, int, struct uio *, int, struct mbuf **, char **); +struct mbuf *nfsm_uiombuflist(bool, int, struct uio *, int, struct mbuf **, char **); nfsuint64 *nfscl_getcookie(struct nfsnode *, off_t off, int); u_int8_t *nfscl_getmyip(struct nfsmount *, struct in6_addr *, int *); int nfsm_getfh(struct nfsrv_descript *, struct nfsfh **); @@ -687,8 +686,8 @@ int nfsvno_readlink(vnode_t, struct ucred *, int, NFSP mbuf_t *, int *); int nfsvno_read(vnode_t, off_t, int, struct ucred *, int, NFSPROC_T *, mbuf_t *, mbuf_t *); -int nfsvno_write(vnode_t, off_t, int, int *, mbuf_t, char *, int, int, - struct ucred *, NFSPROC_T *); +int nfsvno_write(vnode_t, off_t, int, int *, struct nfsrv_descript *, + NFSPROC_T *); int nfsvno_createsub(struct nfsrv_descript *, struct nameidata *, vnode_t *, struct nfsvattr *, int *, int32_t *, NFSDEV_T, struct nfsexstuff *);
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?202003081902.028J2VPG036166>