Date: Thu, 07 Mar 2013 04:41:57 -0800 From: Colin Percival <cperciva@freebsd.org> To: Mark Felder <feld@feld.me> Cc: freebsd-xen@freebsd.org Subject: Re: misc. questions Message-ID: <51388B15.1060105@freebsd.org> In-Reply-To: <op.wtks8wgc34t2sn@tech304.office.supranet.net> References: <000901ce1aa7$90704320$b150c960$@ezwind.net> <5137C5E6.2070802@freebsd.org> <op.wtks8wgc34t2sn@tech304.office.supranet.net>
next in thread | previous in thread | raw e-mail | index | archive | help
This is a multi-part message in MIME format. --------------020105010609080700090803 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit On 03/07/13 04:35, Mark Felder wrote: > On Wed, 06 Mar 2013 16:40:38 -0600, Colin Percival <cperciva@freebsd.org> wrote: >> You'll want to turn off tso, since it produces long mbuf chains which most >> xn netbacks choke on. (I have a very ugly workaround patch for this which I >> use on EC2, but simply turning off tso is enough unless you need Gbps+ speeds). > > Can you link me to this patch? I have an environment that might warrant using it > for now. Attached. And remember that I said it was a *very ugly* workaround... :-) -- Colin Percival Security Officer Emeritus, FreeBSD | The power to serve Founder, Tarsnap | www.tarsnap.com | Online backups for the truly paranoid --------------020105010609080700090803 Content-Type: text/plain; charset=us-ascii; name="tcp_mbuf_chain_limit.patch" Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename="tcp_mbuf_chain_limit.patch" --- sys/kern/uipc_mbuf.c (revision 223824) +++ sys/kern/uipc_mbuf.c (working copy) @@ -525,12 +525,14 @@ * only their reference counts are incremented. */ struct mbuf * -m_copym(struct mbuf *m, int off0, int len, int wait) +m_copy_nbufs(struct mbuf *m, int off0, int len, int wait, long * outlen, + int nbufmax) { struct mbuf *n, **np; int off = off0; struct mbuf *top; int copyhdr = 0; + int len_orig = len; KASSERT(off >= 0, ("m_copym, negative off %d", off)); KASSERT(len >= 0, ("m_copym, negative len %d", len)); @@ -546,7 +548,7 @@ } np = ⊤ top = 0; - while (len > 0) { + while (len > 0 && nbufmax-- > 0) { if (m == NULL) { KASSERT(len == M_COPYALL, ("m_copym, length > size of mbuf chain")); @@ -584,6 +586,9 @@ if (top == NULL) mbstat.m_mcfail++; /* XXX: No consistency. */ + if (outlen) + *outlen = len_orig - len; + return (top); nospace: m_freem(top); @@ -591,6 +596,13 @@ return (NULL); } +struct mbuf * +m_copym(struct mbuf *m, int off0, int len, int wait) +{ + + return (m_copy_nbufs(m, off0, len, wait, NULL, INT_MAX)); +} + /* * Returns mbuf chain with new head for the prepending case. * Copies from mbuf (chain) n from off for len to mbuf (chain) m --- sys/netinet/tcp_output.c (revision 228872) +++ sys/netinet/tcp_output.c (working copy) @@ -183,6 +183,7 @@ int sack_rxmit, sack_bytes_rxmt; struct sackhole *p; int tso; + int max_mbuf_chain_len = 16; /* XXX Set this based on interface? */ struct tcpopt to; #if 0 int maxburst = TCP_MAXBURST; @@ -806,16 +807,6 @@ struct mbuf *mb; u_int moff; - if ((tp->t_flags & TF_FORCEDATA) && len == 1) - TCPSTAT_INC(tcps_sndprobe); - else if (SEQ_LT(tp->snd_nxt, tp->snd_max) || sack_rxmit) { - tp->t_sndrexmitpack++; - TCPSTAT_INC(tcps_sndrexmitpack); - TCPSTAT_ADD(tcps_sndrexmitbyte, len); - } else { - TCPSTAT_INC(tcps_sndpack); - TCPSTAT_ADD(tcps_sndbyte, len); - } MGETHDR(m, M_DONTWAIT, MT_DATA); if (m == NULL) { SOCKBUF_UNLOCK(&so->so_snd); @@ -847,7 +838,8 @@ mtod(m, caddr_t) + hdrlen); m->m_len += len; } else { - m->m_next = m_copy(mb, moff, (int)len); + m->m_next = m_copy_nbufs(mb, moff, len, M_DONTWAIT, + &len, max_mbuf_chain_len); if (m->m_next == NULL) { SOCKBUF_UNLOCK(&so->so_snd); (void) m_free(m); @@ -856,6 +848,18 @@ } } + /* Update stats here as m_copy_nbufs may have adjusted len. */ + if ((tp->t_flags & TF_FORCEDATA) && len == 1) + TCPSTAT_INC(tcps_sndprobe); + else if (SEQ_LT(tp->snd_nxt, tp->snd_max) || sack_rxmit) { + tp->t_sndrexmitpack++; + TCPSTAT_INC(tcps_sndrexmitpack); + TCPSTAT_ADD(tcps_sndrexmitbyte, len); + } else { + TCPSTAT_INC(tcps_sndpack); + TCPSTAT_ADD(tcps_sndbyte, len); + } + /* * If we're sending everything we've got, set PUSH. * (This will keep happy those implementations which only --- sys/sys/mbuf.h (revision 223824) +++ sys/sys/mbuf.h (working copy) @@ -849,6 +849,7 @@ int, int, int, int); struct mbuf *m_copypacket(struct mbuf *, int); void m_copy_pkthdr(struct mbuf *, struct mbuf *); +struct mbuf *m_copy_nbufs(struct mbuf *, int, int, int, long *, int); struct mbuf *m_copyup(struct mbuf *n, int len, int dstoff); struct mbuf *m_defrag(struct mbuf *, int); void m_demote(struct mbuf *, int); --------------020105010609080700090803--
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?51388B15.1060105>