NetBSD-Bugs archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: kern/34799: IP Filter does not work correctly with gem(4) when hardware chec

The following reply was made to PR kern/34799; it has been noted by GNATS.

From: Julian Coleman <>
Subject: Re: kern/34799: IP Filter does not work correctly with gem(4) when 
hardware chec
Date: Sun, 27 Jan 2008 17:47:42 +0000

 Content-Type: text/plain; charset=us-ascii
 Content-Disposition: inline
 >  Okay, here's the tcpdump output when TCP checksumming isn't enabled:
 >  And here's the output when TCP checksumming is enabled:
 Two perfectly fine TCP packets.  I had a chance to look at this again (it's
 bugging me that I can't reproduce it).  I'm fairly sure that ipfilter is
 correct here and that the hardware checksum is not correct.  However, I'm
 not sure why this is only picked up by ipf.  Also, for some reason, the ipf
 check must not be enabled on sparc64 (I didn't immediately spot why).
 I starting instrumenting the receive checksum code, and I see that the
 bytes that are meant to contain the checksum always contain a value related
 to the packet length and the remote IP address.  For example:
        IP              csum - length     7e36     7e37
         ...     7e42
  49b6  49b7
 If you try the attached patch (which prints out the received packet flags
 from the hardware), I imagine that you will see a constant for each site
 you connect to.  (It will print a line on the console for each TCP packet
 received when tcp4csum_rx is enabled.)
 So, either receive checksums are always broken (seems odd to me), or we
 are setting up the card incorrectly.   I'll see if I can spot where.
 PS.  The patch is against -current, but it should apply against 4.0 with an
   My other computer also runs NetBSD    /        Sailing at Newbiggin        /
 Content-Type: text/plain; charset=us-ascii
 Content-Disposition: attachment; filename="gem.diffs"
 --- gem.c.dist 2008-01-27 17:26:05.000000000 +0000
 +++ gem.c      2008-01-27 16:53:57.000000000 +0000
 @@ -1860,16 +1860,17 @@
                                        ~((~m->m_pkthdr.csum_data) - ~optsum);
                                while (m->m_pkthdr.csum_data >> 16)
                                        m->m_pkthdr.csum_data =
                                                (m->m_pkthdr.csum_data >> 16) +
                                                (m->m_pkthdr.csum_data &
 +printf("%s: rxstat = 0x%016lx: len=%4d (%03x); csum=%04x; c - l=%04x\n", 
sc->sc_dev.dv_xname, rxstat, (int) ((rxstat & GEM_RD_BUFSIZE) >> 
GEM_RD_BUFSHIFT), (int) ((rxstat & GEM_RD_BUFSIZE) >> GEM_RD_BUFSHIFT), (int) 
(rxstat & GEM_RD_CHECKSUM), (int) ((rxstat & GEM_RD_CHECKSUM) - ((rxstat & 
                        m->m_pkthdr.csum_flags |= M_CSUM_DATA |
                } else
                        m->m_pkthdr.csum_flags = 0;
                /* Pass it on. */

Home | Main Index | Thread Index | Old Index