Bug 4988 – Floats in structs are not equal on 0.0f vs -0.0f
Status
RESOLVED
Resolution
DUPLICATE
Severity
critical
Priority
P2
Component
dmd
Product
D
Version
D2
Platform
Other
OS
Windows
Creation time
2010-10-04T01:34:00Z
Last change time
2011-02-03T04:40:44Z
Keywords
wrong-code
Assigned to
nobody
Creator
simen.kjaras
Comments
Comment #0 by simen.kjaras — 2010-10-04T01:34:30Z
The following code asserts:
struct Foo {
float data;
}
void bug( ) {
assert( Foo( 0.0f ) == Foo( -0.0f ) ); // Works fine
auto a = Foo( 0.0f );
auto b = Foo( -0.0f );
assert( b == a ); // Asserts
}
Comment #1 by clugdbug — 2010-10-06T23:57:21Z
This also applies to NaNs:
assert( Foo( float.nan ) != Foo( float.nan ) ); // Works fine
auto a = Foo( float.nan );
auto b = Foo( float.nan );
assert( b != a ); // Asserts
The real problem is e2ir.c, line 2313, EqualExp::toElem(), which does a bitwise compare for structs. That isn't valid if there are floating point numbers inside.
This is a pain, because it needs to be considered recursively.
A quick-and-dirty fix would be to construct an opEquals whenever this happens:
clone.c StructDeclaration::needOpEquals() line 106.
if (tv->ty == Tstruct)
{ TypeStruct *ts = (TypeStruct *)tv;
StructDeclaration *sd = ts->sym;
if (sd->eq)
goto Lneed;
}
+ if (tv->isfloating())
+ goto Lneed;
}
Ldontneed:
But the problem with this is that it slows down all equality tests involving floats. Maybe the inliner can take care of it, but generally I don't think it's an acceptable solution.
Comment #2 by bearophile_hugs — 2010-10-07T04:21:33Z
Performance is important, but correct semantics is more important.
Comment #3 by simen.kjaras — 2011-02-03T04:40:44Z
*** This issue has been marked as a duplicate of issue 3789 ***