Ethereal-dev: [ethereal-dev] [okir@xxxxxxxxxxxx: Re: 2.2.14-pre10 NFS bug: off by sizeof(int)]

Note: This archive is from the project's previous web site, ethereal.com. This list is no longer active.

From: Gilbert Ramirez <gram@xxxxxxxxxx>
Date: Tue, 07 Dec 1999 19:10:49 -0600
For those following the Linux 2.2.14-pre10 NFS-bug thread, Olaf responded
with this. To answer his question, yes, I was sniffing on the NFS
server.

--gilbert

----- Forwarded message from Olaf Kirch <okir@xxxxxxxxxxxx> -----

Envelope-to: gram@localhost
X-Envelope-To: <gram@xxxxxxxxxx>
Date: Tue, 7 Dec 1999 13:41:00 +0100
From: Olaf Kirch <okir@xxxxxxxxxxxx>
To: "Gilbert Ramirez Jr." <gram@xxxxxxxxxx>
Cc: linux-kernel@xxxxxxxxxxxxxxxx, nfs-devel@xxxxxxxxxxxxxxxx
Subject: Re: 2.2.14-pre10 NFS bug: off by sizeof(int)
X-Mailer: Mutt 0.95.6i
In-Reply-To: <19991203173919.A390@xxxxxxxxxx>; from Gilbert Ramirez Jr. on Fri, Dec 03, 1999 at 05:39:20PM -0500
X-UIDL: b87bbc8cfd7a76dc2752aaaa1dfd9668

On Fri, Dec 03, 1999 at 05:39:20PM -0500, Gilbert Ramirez Jr. wrote:
> I've been doing some network traces (I'm one of the authors of
> Ethereal, BTW), and these strange "mkdir-latency" problems co-occur
> with another symptom: bad NFS packets.
> 
> The following NFS packet was sent from the NFS client to the NFS
> server. It's an NFS v2 LOOKUP packet. The RPC string, i.e., the
> NFS filename, is misplaced. It's off by 4 bytes. (hence the subject
> line of this e-mail) In my trace, the client sent over 2,000 *good*
> LOOKUP packets, but at this point it sent a few *bad* ones, including
> this one.

I'm not sure whether that you see is really a bad NFS packet. It's
much more likely a side effect of the server side XDR routines. I'm
assuming you've been running your network sniffer on the NFS server? Try
again running it on a different box.

When XDR is asked to decode a string, it avoid allocating memory
for it (this has been a major bottleneck). What it does instead
is just use the string as given in the RPC packet, and tack on
a NUL byte. What if there's no room in the packet because
the string is an exact multiple of 4 bytes, which is the alignment
XDR uses? It just moves the string by four bytes, and tacks on the
NUL byte then.

Here's how the RPC packet looks

	0000 0008 636f 6e66 6967 2e68
		  ^^^^^^^^^^^^^^^^^^^- config.h, without NUL byte
	^^^^^^^^^--------------------- string length, i.e. 8

When the XDR routine decodes the packet, it finds the string length is
a multiple of 4, and moves the string

	636f 6e66 6967 2e68 0067 2e68
	^^^^^^^^^^^^^^^^^^^----------- config.h, moved 4 bytes
			    ^^-------- NUL byte added
			      ^^^^^^^- junk

The obvious gain is of course that this avoids all memory allocations,
and even 3 out of 4 string copies.

The drawback of the approach is that it confuses the Linux raw packet
handling, which expects that skb's once received never get modified.
I know it's evil, but so far you're the first one to notice :-)

Olaf
-- 
Olaf Kirch         |  --- o --- Nous sommes du soleil we love when we play
okir@xxxxxxxxxxxx  |    / | \   sol.dhoop.naytheet.ah kin.ir.samse.qurax
okir@xxxxxxxxxx    +-------------------- Why Not?! -----------------------
         UNIX, n.: Spanish manufacturer of fire extinguishers.            


----- End forwarded message -----