Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 22 Feb 2001 20:44:41 Gmt +0200
From:      idobarnea@NewMail.Net
To:        Ruslan Ermilov <ru@FreeBSD.org>, idobarnea@NewMail.Net, bmilekic@FreeBSD.org, mouss <usebsd@free.fr>, hackers@FreeBSD.org
Subject:   Re: Bug in creating ICMP error messages in FreeBSD4.2
Message-ID:  <3a957a39.178.0@NewMail.Net>

next in thread | raw e-mail | index | archive | help
>[redirected to -net]
>
>On Wed, Feb 21, 2001 at 09:50:58AM +0000, idobarnea@NewMail.Net wrote:
>> >On Mon, Feb 19, 2001 at 08:26:56PM +0100, mouss wrote:
>> > > At 14:25 19/02/01 +0200, idobarnea@NewMail.Net wrote:
>> > > > Hi,
>> > > > I encountered the following problem in the 4.2 version.
>> > > > In ip_forward, the following lines intend to save the mbuf in
>> > > > case we want to send ICMP error later:
>> > > >  mcopy = m_copy(m, 0, imin((int)ip->ip_len, 64));
>> > > >  if (mcopy && (mcopy->m_flags & M_EXT))
>> > > >      m_copydata(mcopy, 0, sizeof(struct ip), mtod(mcopy, caddr_t));

>> > > >
>> > > > Later on, before sending the ICMP packet we do:
>> > > >  if (mcopy->m_flags & M_EXT)
>> > > >      m_copyback(mcopy, 0, sizeof(struct ip), mtod(mcopy, caddr_t));

>> > > >
>> > > > The problem as I understand it is that the m_copydata and m_copyback,

>> > > > actually do nothing (It just copies from mcopy to itself).
>> 
>You are right, the code does nothing, though it was supposed to
>preserve the byte order of IP header fields in case ip_output()
>modifies them.  The idea was to save the standard IP header in
>some area in mbuf that is unused for M_EXT mbufs, but obviously
>mtod() place is wrong, it points to the external data for M_EXT
>mbuf.  Could you please try this patch:
>
>Index: ip_input.c
>===================================================================
>RCS file: /home/ncvs/src/sys/netinet/ip_input.c,v
>retrieving revision 1.130.2.12
>diff -u -p -r1.130.2.12 ip_input.c
>--- ip_input.c 2001/02/01 20:25:09 1.130.2.12
>+++ ip_input.c 2001/02/21 16:48:10
>@@ -1513,7 +1513,8 @@ ip_forward(m, srcrt)
>   */
>  mcopy = m_copy(m, 0, imin((int)ip->ip_len, 64));
>  if (mcopy && (mcopy->m_flags & M_EXT))
>-  m_copydata(mcopy, 0, sizeof(struct ip), mtod(mcopy, caddr_t));
>+  m_copydata(mcopy, 0, sizeof(struct ip),
>+      (caddr_t)(&mcopy->m_ext + 1));
> 
> #ifdef IPSTEALTH
>  if (!ipstealth) {
>@@ -1661,7 +1662,8 @@ ip_forward(m, srcrt)
>   return;
>  }
>  if (mcopy->m_flags & M_EXT)
>-  m_copyback(mcopy, 0, sizeof(struct ip), mtod(mcopy, caddr_t));
>+  m_copyback(mcopy, 0, sizeof(struct ip),
>+      (caddr_t)(&mcopy->m_ext + 1));
>  icmp_error(mcopy, type, code, dest, destifp);
> }
>
>And if that does not work, this (more clear but slower) one:
>
>Index: ip_input.c
>===================================================================
>RCS file: /home/ncvs/src/sys/netinet/ip_input.c,v
>retrieving revision 1.130.2.13
>diff -u -p -r1.130.2.13 ip_input.c
>--- ip_input.c 2001/02/07 01:03:13 1.130.2.13
>+++ ip_input.c 2001/02/21 16:10:35
>@@ -1510,9 +1510,17 @@ ip_forward(m, srcrt)
>   * we need to generate an ICMP message to the src.
>   */
>  mcopy = m_copy(m, 0, imin((int)ip->ip_len, 64));
>- if (mcopy && (mcopy->m_flags & M_EXT))
>-  m_copydata(mcopy, 0, sizeof(struct ip), mtod(mcopy, caddr_t));
> 
>+ /*
>+  * Make sure the copy is read-write.
>+  */
>+ if (mcopy && (mcopy->m_flags & M_EXT)) {
>+  struct mbuf *mtemp = mcopy;
>+
>+  mcopy = m_dup(mtemp, M_DONTWAIT);
>+  m_freem(mtemp);
>+ }
>+
> #ifdef IPSTEALTH
>  if (!ipstealth) {
> #endif
>@@ -1658,8 +1666,6 @@ ip_forward(m, srcrt)
>   m_freem(mcopy);
>   return;
>  }
>- if (mcopy->m_flags & M_EXT)
>-  m_copyback(mcopy, 0, sizeof(struct ip), mtod(mcopy, caddr_t));
>  icmp_error(mcopy, type, code, dest, destifp);
> }
> 
>
>Cheers, 
>-- 
>Ruslan Ermilov  Oracle Developer/DBA,
>ru@sunbay.com  Sunbay Software AG,
>ru@FreeBSD.org  FreeBSD committer,
>+380.652.512.251 Simferopol, Ukraine
>
>http://www.FreeBSD.org The Power To Serve
>http://www.oracle.com Enabling The Information Age


The first one works (I guess the second one also). Its nice trick.
If you could just add a line or two of remarks it would be great.
something like:
/* saving ip header for future use because ip_output might change it */

Thanks, Ido



_________________________________________
Get Your Free Virus Protection Tool at http://www.VCatch.com

To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-hackers" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?3a957a39.178.0>