From alex@cichlids.com  Mon May 29 08:24:29 2000
Return-Path: <alex@cichlids.com>
Received: from mail.surf1.de (mail.surf1.de [194.25.165.21])
	by hub.freebsd.org (Postfix) with ESMTP id BB6A837BA88
	for <FreeBSD-gnats-submit@freebsd.org>; Mon, 29 May 2000 08:24:26 -0700 (PDT)
	(envelope-from alex@cichlids.com)
Received: from cichlids.com (p3E9EE6F6.dip0.t-ipconnect.de [62.158.230.246])
	by mail.surf1.de (8.9.3/8.9.3) with ESMTP id RAA00827
	for <FreeBSD-gnats-submit@freebsd.org>; Mon, 29 May 2000 17:24:54 +0200
Received: from cichlids.cichlids.com (cichlids.cichlids.com [192.168.0.10])
	by cichlids.com (Postfix) with ESMTP id 57F01AC30
	for <FreeBSD-gnats-submit@freebsd.org>; Mon, 29 May 2000 17:24:43 +0200 (CEST)
Received: (from alex@localhost)
	by cichlids.cichlids.com (8.9.3/8.9.3) id RAA02241;
	Mon, 29 May 2000 17:24:23 +0200 (CEST)
	(envelope-from alex)
Message-Id: <200005291524.RAA02241@cichlids.cichlids.com>
Date: Mon, 29 May 2000 17:24:23 +0200 (CEST)
From: alex@big.endian.de
Sender: alex@cichlids.com
To: FreeBSD-gnats-submit@freebsd.org
Subject: 32bit NFS servers export wrong negative values to 64bit clients
X-Send-Pr-Version: 3.2

>Number:         18874
>Category:       kern
>Synopsis:       [2TB] 32bit NFS servers export wrong negative values to 64bit clients
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    freebsd-fs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:  
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Mon May 29 08:30:00 PDT 2000
>Closed-Date:    
>Last-Modified:  Mon May 18 04:34:15 UTC 2009
>Originator:     Alexander Langer
>Release:        FreeBSD 5.0-CURRENT i386
>Organization:
none
>Environment:

NFS-Server: FreeBSD 4.0-CURRENT/i386
NFS-Client: FreeBSD 4.0-STABLE/alpha

>Description:

NFS Server wants to export that fs:
/dev/ad0s4g   2482878  2361105   -76857   103%    /usr

NFS client sees:
neutron:/usr/obj         2482878  2361105 18014398509405127     0%    /usr/obj

>How-To-Repeat:

see above

>Fix:

I'm not a NFS-Nerd, but in my eyes there _should_ be a handshake between server
and client _in some way_ and casts to the correct types should be done
then depending on the machine archs of the server and client.

I know that NFS is a standardized protocol, but this _is_ a bug and must be
fixed.


>Release-Note:
>Audit-Trail:

From: Anatoly Vorobey <mellon@pobox.com>
To: alex@big.endian.de
Cc: FreeBSD-gnats-submit@FreeBSD.ORG
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Mon, 29 May 2000 13:14:59 -0400

 You, alex@big.endian.de, were spotted writing this on Mon, May 29, 2000 at 05:24:23PM +0200:
 > NFS Server wants to export that fs:
 > /dev/ad0s4g   2482878  2361105   -76857   103%    /usr
 > 
 > NFS client sees:
 > neutron:/usr/obj         2482878  2361105 18014398509405127     0%    /usr/obj
 
 Gotta love those signed<-->unsigned bugs ;)
 
 This seemed interesting enough for me to rummage around in sources,
 but I don't really have a working setup with Alpha NFS to test this against.
 I wonder if you could try this patch, which seems to do The Right Thing
 to me. I won't be surprised if it fails to work at all though :)
 
 A brief explanation: tquad is 64-bit unsigned, and holds the available
 bytes value which is really signed long. Suppose the real value is negative.
 If we divide it by NFS_FABLKSIZE first, and then
 cast to long, we risk turning it into a positive value by division.
 
 --- /usr/src/sys/nfs/nfs_vfsops.c	Sun Aug 29 12:30:31 1999
 +++ nfs_vfsops.c	Mon May 29 13:08:50 2000
 @@ -297,7 +297,7 @@
  		fxdr_hyper(&sfp->sf_fbytes, &tquad);
  		sbp->f_bfree = (long)(tquad / ((u_quad_t)NFS_FABLKSIZE));
  		fxdr_hyper(&sfp->sf_abytes, &tquad);
 -		sbp->f_bavail = (long)(tquad / ((u_quad_t)NFS_FABLKSIZE));
 +		sbp->f_bavail = ((long)tquad) / (long)NFS_FABLKSIZE);
  		sbp->f_files = (fxdr_unsigned(int32_t,
  		    sfp->sf_tfiles.nfsuquad[1]) & 0x7fffffff);
  		sbp->f_ffree = (fxdr_unsigned(int32_t,
 
 -- 
 Anatoly Vorobey,
 mellon@pobox.com http://pobox.com/~mellon/
 "Angels can fly because they take themselves lightly" - G.K.Chesterton
 

From: Alexander Langer <alex@big.endian.de>
To: Anatoly Vorobey <mellon@pobox.com>
Cc: FreeBSD-gnats-submit@FreeBSD.ORG
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Mon, 29 May 2000 19:21:40 +0200

 Thus spake Anatoly Vorobey (mellon@pobox.com):
 
 > Gotta love those signed<-->unsigned bugs ;)
 
 Isn't that 32bit signed vs. 64bit signed?
 
 > but I don't really have a working setup with Alpha NFS to test this against.
 
 On the client, I guess? (the patch). Will it break the i386 nfs?
 
 > A brief explanation: tquad is 64-bit unsigned, and holds the available
 > bytes value which is really signed long. Suppose the real value is negative.
 > If we divide it by NFS_FABLKSIZE first, and then
 > cast to long, we risk turning it into a positive value by division.
 
 Yes, but what about i386, where long is only 32bit and can't hold that
 value?
 
 
 Alex
 
 -- 
 I need a new ~/.sig.
 

From: Anatoly Vorobey <mellon@pobox.com>
To: Alexander Langer <alex@big.endian.de>
Cc: FreeBSD-gnats-submit@FreeBSD.ORG
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Mon, 29 May 2000 13:34:47 -0400

 You, Alexander Langer, were spotted writing this on Mon, May 29, 2000 at 07:21:40PM +0200:
 > Thus spake Anatoly Vorobey (mellon@pobox.com):
 > 
 > > Gotta love those signed<-->unsigned bugs ;)
 > 
 > Isn't that 32bit signed vs. 64bit signed?
 
 I thought that was the case at first too, but it doesn't appear so. 
 NFS transfers
 available values for statfs as 32-bit unsigned in v2, and 64-bit
 unsigned in v3, regardless of platforms it runs on (your setup uses
 NFSv3, right?). See the nfs_statfs structure in sys/nfs/nfsproto.h .
 Now the bug says that either the server puts the value in nfs_statfs
 incorrectly (maybe, but I couldn't find any fault with the
 sources in nfs_serv.c), or the client takes it out incorrectly (I
 think that's likely, hence the attached patch), or the xdr
 conversion routines work incorrectly for quad values (very unlikely,
 would've broken lots of things in NFS).
 
 > > but I don't really have a working setup with Alpha NFS to test this against.
 > 
 > On the client, I guess? (the patch). Will it break the i386 nfs?
 
 Yes, on the client, and no, shouldn't break anything at all.
 
 > > A brief explanation: tquad is 64-bit unsigned, and holds the available
 > > bytes value which is really signed long. Suppose the real value is negative.
 > > If we divide it by NFS_FABLKSIZE first, and then
 > > cast to long, we risk turning it into a positive value by division.
 > 
 > Yes, but what about i386, where long is only 32bit and can't hold that
 > value?
 
 Hmm. I haven't thought of that. A simple test I made on i386 showed
 that (long)(u_quad_t)(long)(-100) == -100, so I guess the conversion
 works fine, even though long is 32bit, and I can't really explain why
 at the moment :)
 
 If you want to be extra sure, you can cast tquad to quad_t before casting
 it to long. Then it'll hold the real negative value which must be correctly
 converted into long. I know that you can point out that Alpha's long was
 bigger than i386's long -- but there's not much you can do about *that*,
 since you have to start from struct statfs on Alpha and finish with struct
 statfs on i386, and f_bavail is long on both. You'll just have to hope that
 the underlying filesystem restricts this value to 32 bits or something.
 
 -- 
 Anatoly Vorobey,
 mellon@pobox.com http://pobox.com/~mellon/
 "Angels can fly because they take themselves lightly" - G.K.Chesterton
 

From: Alexander Langer <alex@big.endian.de>
To: Anatoly Vorobey <mellon@pobox.com>
Cc: FreeBSD-gnats-submit@FreeBSD.ORG
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Mon, 29 May 2000 19:48:21 +0200

 Thus spake Anatoly Vorobey (mellon@pobox.com):
 
 > it to long. Then it'll hold the real negative value which must be correctly
 > converted into long. I know that you can point out that Alpha's long was
 > bigger than i386's long -- but there's not much you can do about *that*,
 > since you have to start from struct statfs on Alpha and finish with struct
 > statfs on i386, and f_bavail is long on both. You'll just have to hope that
 > the underlying filesystem restricts this value to 32 bits or something.
 
 What about taking quad_t and not u_quat_t?
 
 I think that would be _much_ more appreciated, isn't it? (for the
 conversion)
 
 Alex
 
 -- 
 I need a new ~/.sig.
 

From: Anatoly Vorobey <mellon@pobox.com>
To: Alexander Langer <alex@big.endian.de>,
	FreeBSD-gnats-submit@FreeBSD.ORG
Cc:  
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Mon, 29 May 2000 13:53:16 -0400

 You, Anatoly Vorobey, were spotted writing this on Mon, May 29, 2000 at 01:34:46PM -0400:
 > Hmm. I haven't thought of that. A simple test I made on i386 showed
 > that (long)(u_quad_t)(long)(-100) == -100, so I guess the conversion
 > works fine, even though long is 32bit, and I can't really explain why
 > at the moment :)
 
 Can't I? I can ;) If the negative value is small enough to fit into 32bit,
 then it'll get converted via u_quad_t just fine, because the high quadword
 will only contain 1's. The conversion from u_quad_t to long will just chop
 off the high word:
 
 Scenario A. Source long is 32-bit, destination long is 32-bit:
 
 (src long)-10 is 0xfffffff6
 (u_quad_t)(src long)-10 is 0x00000000fffffff6
 (dst long)(u_quad_t)(src long)-10 is 0xfffffff6 == -10
 
 Senario B. Source long is 64-bit, destination long is 32-bit:
 
 (src long)-10 is 0xfffffffffffffff6
 (u_quad_t)(dst long)-10 is 0xfffffffffffffff6
 (dst long)(u_quad_t)(src long)-10 is 0xfffffff6 == -10
  
 Scenario C. Source long is 32-bit, destination long is 64-bit:
 
 (src long)-10 is 0xfffffff6
 (u_quad_t)(src long)-10 is 0x00000000fffffff6
 (dst long)(u_quad_t)(src long)-10 is 0x00000000fffffff6 == 4294967286
 
 Scenario D. Source long is 64-bit, destination long is 64-bit,
 left to the reader ;)
 
 Bummer, scenario C shouldn't work at all -- can you check? But this
 isn't your case, your case is scenario B IIRC -- and the conversion
 should work fine, my patch corrects the problem which might happen
 because the value gets divided before the third stage, when the compiler
 still thinks it's unsigned 64bit.
 
 -- 
 Anatoly Vorobey,
 mellon@pobox.com http://pobox.com/~mellon/
 "Angels can fly because they take themselves lightly" - G.K.Chesterton
 

From: Alexander Langer <alex@big.endian.de>
To: Anatoly Vorobey <mellon@pobox.com>
Cc: FreeBSD-gnats-submit@FreeBSD.ORG
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Mon, 29 May 2000 19:57:59 +0200

 Thus spake Anatoly Vorobey (mellon@pobox.com):
 
 > Bummer, scenario C shouldn't work at all -- can you check? But this
 > isn't your case, your case is scenario B IIRC -- and the conversion
 > should work fine, my patch corrects the problem which might happen
 > because the value gets divided before the third stage, when the compiler
 > still thinks it's unsigned 64bit.
 
 I'll test soon. At the moment I'm building world. I'll also try the
 quad_t cast instead of the long cast.
 
 Thanks anyways.
 
 Alex
 
 -- 
 I need a new ~/.sig.
 

From: Anatoly Vorobey <mellon@pobox.com>
To: Alexander Langer <alex@big.endian.de>
Cc: FreeBSD-gnats-submit@FreeBSD.ORG
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Mon, 29 May 2000 13:59:24 -0400

 You, Alexander Langer, were spotted writing this on Mon, May 29, 2000 at 07:48:21PM +0200:
 > Thus spake Anatoly Vorobey (mellon@pobox.com):
 > 
 > > it to long. Then it'll hold the real negative value which must be correctly
 > > converted into long. I know that you can point out that Alpha's long was
 > > bigger than i386's long -- but there's not much you can do about *that*,
 > > since you have to start from struct statfs on Alpha and finish with struct
 > > statfs on i386, and f_bavail is long on both. You'll just have to hope that
 > > the underlying filesystem restricts this value to 32 bits or something.
 > 
 > What about taking quad_t and not u_quat_t?
 > 
 > I think that would be _much_ more appreciated, isn't it? (for the
 > conversion)
 
 NFS seems to transfer everything unsigned, and I think it's a reasonable
 decision. It gets cast back to signed on the receiving end if needed.
 
 I think that casting to quad_t *before* casting to u_quad_t would solve
 the problem I've outlined as Scenario C in my previous mail. That change
 would have to be inserted in nfs_serv.c, in the server nfs_statfs() call.
 But I haven't even verified that the problem exists yet (I've no access
 to any Alphas anyway). I don't see how using quad_t would help in
 *your* case, on the other hand.
 
 
 
 -- 
 Anatoly Vorobey,
 mellon@pobox.com http://pobox.com/~mellon/
 "Angels can fly because they take themselves lightly" - G.K.Chesterton
 

From: Alexander Langer <alex@big.endian.de>
To: Anatoly Vorobey <mellon@pobox.com>
Cc: FreeBSD-gnats-submit@FreeBSD.ORG
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Mon, 29 May 2000 20:04:53 +0200

 Thus spake Anatoly Vorobey (mellon@pobox.com):
 
 > But I haven't even verified that the problem exists yet (I've no access
 > to any Alphas anyway). I don't see how using quad_t would help in
 > *your* case, on the other hand.
 
 Not in my case, but the i386 case.
 
 Since long is only 32bit, you need to cast that to 64bit signed in
 order to work.
 
 As I said, I'll try.
 
 Alex
 
 -- 
 I need a new ~/.sig.
 
State-Changed-From-To: open->feedback 
State-Changed-By: asmodai 
State-Changed-When: Thu Nov 15 11:56:52 PST 2001 
State-Changed-Why:  
Does this still happen in recent STABLEs? 

http://www.FreeBSD.org/cgi/query-pr.cgi?pr=18874 
Responsible-Changed-From-To: freebsd-bugs->peter 
Responsible-Changed-By: peter 
Responsible-Changed-When: Thu Nov 15 12:55:28 PST 2001 
Responsible-Changed-Why:  
I'll finish this if it isn't already done. 

http://www.FreeBSD.org/cgi/query-pr.cgi?pr=18874 

From: "KAREN THODE" <thode12@msn.com>
To: <freebsd-gnats-submit@FreeBSD.org>, <alex@big.endian.de>
Cc:  
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to 64bit clients
Date: Thu, 3 Jul 2003 13:33:22 -0500

 ------=_NextPart_001_0002_01C34167.AC3CF9A0
 Content-Type: text/plain; charset="iso-8859-1"
 Content-Transfer-Encoding: quoted-printable
 
 Here's a routine to sign-extend a 32-bit number to a 64-bit number.
 
 long long sgn_ex_3264(long old_num)    /*Prototype: long long sgn_ex_3264=
 (long)*/
 {
     long tmp_num=3Dold_num;
     long long tmp_num_2=3D0LL;
     if(tmp_num & 0x80000000L)
     {
         tmp_num_2=3D0xffffffff00000000LL | ((long long)old_num)
     }
     else
     {
         tmp_num_2=3D(long long)old_num
     }
     return(tmp_num_2);
 }
 
 ------=_NextPart_001_0002_01C34167.AC3CF9A0
 Content-Type: text/html; charset="iso-8859-1"
 Content-Transfer-Encoding: quoted-printable
 
 <HTML><BODY STYLE=3D"font:10pt verdana; border:none;"><DIV> <DIV><FONT fa=
 ce=3DArial size=3D2>Here's a routine to sign-extend a 32-bit number&nbsp;=
 to a 64-bit number.</FONT></DIV> <DIV><FONT face=3DArial size=3D2></FONT>=
 &nbsp;</DIV> <DIV><FONT face=3DArial size=3D2>long long sgn_ex_3264(long =
 old_num)&nbsp;&nbsp;&nbsp; /*Prototype: long long sgn_ex_3264(long)*/</FO=
 NT></DIV> <DIV><FONT face=3DArial size=3D2>{</FONT></DIV> <DIV><FONT face=
 =3DArial size=3D2>&nbsp;&nbsp;&nbsp; long tmp_num=3Dold_num;</FONT></DIV>=
  <DIV><FONT face=3DArial size=3D2>&nbsp;&nbsp;&nbsp; long long tmp_num_2=3D=
 0LL;</FONT></DIV> <DIV><FONT face=3DArial size=3D2>&nbsp;&nbsp;&nbsp; if(=
 tmp_num &amp; 0x80000000L)</FONT></DIV> <DIV><FONT face=3DArial size=3D2>=
 &nbsp;&nbsp;&nbsp; {</FONT></DIV> <DIV><FONT face=3DArial size=3D2>&nbsp;=
 &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; tmp_num_2=3D0xffffffff00000000LL | (=
 (long long)old_num)</FONT></DIV> <DIV><FONT face=3DArial size=3D2>&nbsp;&=
 nbsp;&nbsp; }</FONT></DIV> <DIV><FONT face=3DArial size=3D2>&nbsp;&nbsp;&=
 nbsp; else</FONT></DIV> <DIV><FONT face=3DArial size=3D2>&nbsp;&nbsp;&nbs=
 p; {</FONT></DIV> <DIV><FONT face=3DArial size=3D2>&nbsp;&nbsp;&nbsp; &nb=
 sp;&nbsp;&nbsp; tmp_num_2=3D(long long)old_num</FONT></DIV> <DIV><FONT fa=
 ce=3DArial size=3D2>&nbsp;&nbsp;&nbsp; }</FONT></DIV> <DIV><FONT face=3DA=
 rial size=3D2>&nbsp;&nbsp;&nbsp; return(tmp_num_2);</FONT></DIV> <DIV><FO=
 NT face=3DArial size=3D2>}</FONT></DIV><BR><BR></DIV></BODY></HTML>
 
 ------=_NextPart_001_0002_01C34167.AC3CF9A0--
Responsible-Changed-From-To: peter->tjr 
Responsible-Changed-By: kris 
Responsible-Changed-When: Sat Nov 15 13:46:56 PST 2003 
Responsible-Changed-Why:  
tjr has a patch for this 

http://www.freebsd.org/cgi/query-pr.cgi?pr=18874 

From: Andre Oppermann <andre@freebsd.org>
To: freebsd-gnats-submit@FreeBSD.org, alex@big.endian.de,
	tjr@freebsd.org
Cc:  
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to
 64bit clients
Date: Mon, 29 Dec 2003 00:14:26 +0100

 Tim,
 
 any news on this one?
 
 -- 
 Andre
 
 

From: Tim Robbins <tjr@freebsd.org>
To: Andre Oppermann <andre@freebsd.org>
Cc: freebsd-gnats-submit@freebsd.org, alex@big.endian.de
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to
 64bit clients
Date: Mon, 29 Dec 2003 22:29:31 +1100

 This is a multi-part message in MIME format.
 --------------060400090503020502010805
 Content-Type: text/plain; charset=us-ascii; format=flowed
 Content-Transfer-Encoding: 7bit
 
 Andre Oppermann wrote:
 
 > Tim,
 >
 > any news on this one?
 >
 Not really - I don't have the hardware to test this on. I've attached my 
 best guess at a patch, but I haven't even compile-tested it yet.
 
 
 Tim
 
 --------------060400090503020502010805
 Content-Type: text/plain;
  name="nfs.diff"
 Content-Transfer-Encoding: 7bit
 Content-Disposition: inline;
  filename="nfs.diff"
 
 ==== //depot/user/tjr/freebsd-tjr/src/sys/nfsserver/nfs_serv.c#6 - /p4/src/sys/nfsserver/nfs_serv.c ====
 @@ -3779,7 +3779,6 @@
  	nfsfh_t nfh;
  	fhandle_t *fhp;
  	struct statfs statfs;
 -	u_quad_t tval;
  
  	nfsdbprintf(("%s %d\n", __FILE__, __LINE__));
  	fhp = &nfh.fh_generic;
 @@ -3806,21 +3805,12 @@
  	}
  	sfp = nfsm_build(struct nfs_statfs *, NFSX_STATFS(v3));
  	if (v3) {
 -		tval = (u_quad_t)sf->f_blocks;
 -		tval *= (u_quad_t)sf->f_bsize;
 -		txdr_hyper(tval, &sfp->sf_tbytes);
 -		tval = (u_quad_t)sf->f_bfree;
 -		tval *= (u_quad_t)sf->f_bsize;
 -		txdr_hyper(tval, &sfp->sf_fbytes);
 -		tval = (u_quad_t)sf->f_bavail;
 -		tval *= (u_quad_t)sf->f_bsize;
 -		txdr_hyper(tval, &sfp->sf_abytes);
 -		sfp->sf_tfiles.nfsuquad[0] = 0;
 -		sfp->sf_tfiles.nfsuquad[1] = txdr_unsigned(sf->f_files);
 -		sfp->sf_ffiles.nfsuquad[0] = 0;
 -		sfp->sf_ffiles.nfsuquad[1] = txdr_unsigned(sf->f_ffree);
 -		sfp->sf_afiles.nfsuquad[0] = 0;
 -		sfp->sf_afiles.nfsuquad[1] = txdr_unsigned(sf->f_ffree);
 +		txdr_hyper(sf->f_blocks * sf->f_bsize, &sfp->sf_tbytes);
 +		txdr_hyper(sf->f_bfree * sf->f_bsize, &sfp->sf_fbytes);
 +		txdr_hyper(sf->f_bavail * sf->f_bsize, &sfp->sf_abytes);
 +		txdr_hyper(sf->f_files, &sfp->sf_tfiles);
 +		txdr_hyper(sf->f_ffree, &sfp->sf_ffiles);
 +		txdr_hyper(sf->f_ffree, &sfp->sf_afiles);
  		sfp->sf_invarsec = 0;
  	} else {
  		sfp->sf_tsize = txdr_unsigned(NFS_MAXDGRAMDATA);
 
 --------------060400090503020502010805--

From: Alexander Langer <alex@big.endian.de>
To: Tim Robbins <tjr@freebsd.org>
Cc: Andre Oppermann <andre@freebsd.org>,
	freebsd-gnats-submit@freebsd.org
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to
 64bit clients
Date: Sun, 04 Jan 2004 19:49:51 +0100

 Thus spake Tim Robbins (tjr@freebsd.org):
 
 > Not really - I don't have the hardware to test this on. I've attached my 
 > best guess at a patch, but I haven't even compile-tested it yet.
 
 I might give you an account on my Alpha once I'm back in town to test
 this.
 
 Alex
 
 
State-Changed-From-To: feedback->suspended 
State-Changed-By: tjr 
State-Changed-When: Sat Feb 14 22:56:25 PST 2004 
State-Changed-Why:  
Suspended until I can find a way to test patches. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=18874 
State-Changed-From-To: suspended->patched 
State-Changed-By: tjr 
State-Changed-When: Fri Apr 23 06:15:28 PDT 2004 
State-Changed-Why:  
Fixed in -current by mux@. 


Responsible-Changed-From-To: tjr->freebsd-bugs 
Responsible-Changed-By: tjr 
Responsible-Changed-When: Fri Apr 23 06:15:28 PDT 2004 
Responsible-Changed-Why:  
I am no longer working on this. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=18874 

From: Bruce Evans <bde@zeta.org.au>
To: "Tim J. Robbins" <tjr@freebsd.org>
Cc: alex@big.endian.de, freebsd-gnats-submit@freebsd.org
Subject: Re: kern/18874: 32bit NFS servers export wrong negative values to
 64bit clients
Date: Sat, 24 Apr 2004 00:58:48 +1000 (EST)

 On Fri, 23 Apr 2004, Tim J. Robbins wrote:
 
 > Synopsis: 32bit NFS servers export wrong negative values to 64bit clients
 >
 > State-Changed-From-To: suspended->patched
 > State-Changed-By: tjr
 > State-Changed-When: Fri Apr 23 06:15:28 PDT 2004
 > State-Changed-Why:
 > Fixed in -current by mux@.
 
 The fix is wrong, since it breaks sending negative block counts to
 clients which understand them.  BSD clients have supported this since at
 least 4.4BSD, but the code is broken for the nfsv3 case.  This is fixed
 for small negative values in NetBSD by casting to a signed type as
 discussed in the followup to this PR.
 
 Sign extension bugs are closely related to overflow bugs here and
 elsewhere.  Overflow occurs for block counts that represent byte
 counts >= 1TB (PR 56606).  FreeBSD has wrong fixes for this.  See
 the PR followup for more details.
 
 The bugs have now mostly moved to cvtstatfs().  They now also affect
 callers of the old statfs() family.  Overflow problems in nfs_statfs()
 should have gone away, since 64-bit byte counts easily fit in 64-bit
 block counters after dividing by the 512.  However, nfs still thinks
 that block counters are longs and it makes messes trying to get the
 64-bit counts to fit in possibly-32-bit longs.  See the followup to
 PR 56606 for a hopefully working version.  This code needs to move
 to RELENG_4's nfs_statfs() and -current's cvtstatfs().  cvstatfs() is
 simple and broken.  It attempts to truncate large values but has some
 sign bugs:
 
 % static void
 % cvtstatfs(td, nsp, osp)
 % 	struct thread *td;
 % 	struct statfs *nsp;
 % 	struct ostatfs *osp;
 % {
 %
 % 	bzero(osp, sizeof(*osp));
 % 	osp->f_bsize = MIN(nsp->f_bsize, LONG_MAX);
 % 	osp->f_iosize = MIN(nsp->f_iosize, LONG_MAX);
 % 	osp->f_blocks = MIN(nsp->f_blocks, LONG_MAX);
 % 	osp->f_bfree = MIN(nsp->f_bfree, LONG_MAX);
 % 	osp->f_bavail = MIN(nsp->f_bavail, LONG_MAX);
 % 	osp->f_files = MIN(nsp->f_files, LONG_MAX);
 % 	osp->f_ffree = MIN(nsp->f_ffree, LONG_MAX);
 
 Mount of the fields in the new statfs struct are (bogusly) unsigned
 where they used to be signed.  The clamps work for these.  However,
 f_bavail and f_free are signed, so the above assignments to their "old"
 values overflow if their "new" values are < LONG_MIN.
 
 Bruce
State-Changed-From-To: patched->closed 
State-Changed-By: remko 
State-Changed-When: Mon Mar 26 20:23:33 UTC 2007 
State-Changed-Why:  
thishad been done ages ago. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=18874 
State-Changed-From-To: closed->open 
State-Changed-By: remko 
State-Changed-When: Tue Mar 27 05:27:04 UTC 2007 
State-Changed-Why:  
Bruce reported that I was wrong, reopen the ticket (Thanks Bruce) 

http://www.freebsd.org/cgi/query-pr.cgi?pr=18874 
Responsible-Changed-From-To: freebsd-bugs->freebsd-fs 
Responsible-Changed-By: linimon 
Responsible-Changed-When: Mon May 18 04:34:04 UTC 2009 
Responsible-Changed-Why:  
Over to maintainer(s). 

http://www.freebsd.org/cgi/query-pr.cgi?pr=18874 
>Unformatted:
