Subject: Re: X with new math libs
To: None <randyt@cse.unl.edu>
From: J.T. Conklin <conklin@ngai.kaleida.com>
List: current-users
Date: 03/04/1994 10:02:13
Randy> Martin Husemann writes:
>> I just rebuild XFree-2.0 using Feb. 26 tar_files und the XFree-patches 
>> from ftp.laas.fr:
>> 
>> Everything compiled fine.
>> 
>> But when I move the cursor very near to 'xeyes', they start to
>> destroy their own border. I suppose this is due to some differences
>> in the new math library.

Randy> I have noticed some similar problems with swisswatch.  I have not yet
Randy> had time to go looking for solutions.  It did seem to occur after the
Randy> math lib update.

I think I fixed this yesterday.

Many fdlibm functions take the address of a double, casts it to an int
pointer, adds n0 (which is either 0 or one, depending on the byte
order), dereferences the address, and then assigns a value to it.

	x = 0.0;
	*(((int *)&x) + n0) = 0x7fff0000;

But when GCC compiles these functions with optimization, it doesn't
recognize that x is be changed.  Depending on the circumstances, the
modified value may or may not be used.  The above sequence (which
occurs in hypot()), where a variable is assigned zero and then
modified is particularly vulnerable to this optimization.

I asked the language-lawyer types in comp.std.c and found that GCC is
within it's rights to do this.  The above expression is undefined.

	ANSI Classic section 3.3, page 39 lines 18 to 27: An object
	shall have its stored value accessed only by an lvalue that
	has one of the following types:
		* the declared type of the object,
		* a qualified version of the declared type of the
		  object,
		* a type that is the signed or unsigned type
		  corresponding to the declared type of the object,
		* an aggregate or union type that includes one of the
		  aforementioned types among its members (including,
		  recursively, a member of a subaggregate or contained
		  union), or
		* a character type.

GCC does the right thing when n0 is a constant 0 or 1, and since run
time byte order detection is (IMHO) very silly, I replaced n0 with a
macro that expanded to 0 or 1 depending on the byte order.  Hypot()
returns correct values now.

	--jtc

------------------------------------------------------------------------------