Author: andre
Date: Mon Jun 22 22:20:38 2009
New Revision: 194667
URL: http://svn.freebsd.org/changeset/base/194667

Log:
  Add m_mbuftouio() helper function to copy(out) an arbitrary
  long mbuf chain into an arbitrary large uio in a single step.
  It is a functional mirror image of m_uiotombuf().
  
  This function is supposed to be used instead of hand rolled code
  with the same purpose and to concentrate it into one place for
  potential further optimization or hardware assistance.

Modified:
  head/sys/kern/uipc_mbuf.c
  head/sys/sys/mbuf.h

Modified: head/sys/kern/uipc_mbuf.c
==============================================================================
--- head/sys/kern/uipc_mbuf.c   Mon Jun 22 22:09:19 2009        (r194666)
+++ head/sys/kern/uipc_mbuf.c   Mon Jun 22 22:20:38 2009        (r194667)
@@ -1770,6 +1770,34 @@ m_uiotombuf(struct uio *uio, int how, in
 }
 
 /*
+ * Copy an mbuf chain into a uio limited by len if set.
+ */
+int
+m_mbuftouio(struct uio *uio, struct mbuf *m, int len)
+{
+       int error, length, total;
+       int progress = 0;
+
+       if (len > 0)
+               total = min(uio->uio_resid, len);
+       else
+               total = uio->uio_resid;
+
+       /* Fill the uio with data from the mbufs. */
+       for (; m != NULL; m = m->m_next) {
+               length = min(m->m_len, total - progress);
+
+               error = uiomove(mtod(m, void *), length, uio);
+               if (error)
+                       return (error);
+
+               progress += length;
+       }
+
+       return (0);
+}
+
+/*
  * Set the m_data pointer of a newly-allocated mbuf
  * to place an object of the specified size at the
  * end of the mbuf, longword aligned.

Modified: head/sys/sys/mbuf.h
==============================================================================
--- head/sys/sys/mbuf.h Mon Jun 22 22:09:19 2009        (r194666)
+++ head/sys/sys/mbuf.h Mon Jun 22 22:20:38 2009        (r194667)
@@ -813,6 +813,7 @@ void                 m_freem(struct mbuf *);
 struct mbuf    *m_getm2(struct mbuf *, int, int, short, int);
 struct mbuf    *m_getptr(struct mbuf *, int, int *);
 u_int           m_length(struct mbuf *, struct mbuf **);
+int             m_mbuftouio(struct uio *, struct mbuf *, int);
 void            m_move_pkthdr(struct mbuf *, struct mbuf *);
 struct mbuf    *m_prepend(struct mbuf *, int, int);
 void            m_print(const struct mbuf *, int);
_______________________________________________
svn-src-all@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-all
To unsubscribe, send any mail to "svn-src-all-unsubscr...@freebsd.org"

Reply via email to