April 24, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 --- Comment #10 from Walter Bright <bugzilla@digitalmars.com> 2013-04-23 18:23:56 PDT --- To quote from http://docs.oracle.com/cd/E19060-01/stud8.compiler/817-0932/ncg_goldberg.html: “Of course, this form of double-rounding is highly unlikely to affect any practical program adversely.” Therefore, rather than retard the precision of all programs, I suggest creating two standard functions, double roundToDouble(real x); float roundToFloat(real x); which will guarantee a result rounded to the return type precision. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
April 24, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 --- Comment #11 from Don <clugdbug@yahoo.com.au> 2013-04-24 06:36:53 PDT --- (In reply to comment #10) > To quote from http://docs.oracle.com/cd/E19060-01/stud8.compiler/817-0932/ncg_goldberg.html: > > “Of course, this form of double-rounding is highly unlikely to affect any practical program adversely.” > > Therefore, rather than retard the precision of all programs, This is not about retarding precision of all programs (the way Java does). This is about making compile-time behave the same as runtime. Specifically: 1. A manifest constant should not be carrying extra precision. That's simply incorrect. 2. JIT compilation onto the target machine should be valid for CTFE. 3. The results of CTFE should be as reproducible as runtime results are. Right now, there is lots of stuff which appears to work, but relies on the current DMD implementation. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
April 24, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 --- Comment #12 from Walter Bright <bugzilla@digitalmars.com> 2013-04-24 14:24:50 PDT --- (In reply to comment #11) > This is about making compile-time behave the same as runtime. Floating point answers can (and do) vary depending on optimization settings. This is true for C and C++ compilers, too, even though the arithmetic is Standard compliant. > Specifically: > 1. A manifest constant should not be carrying extra precision. That's simply > incorrect. This is an assertion that earlier I would have accepted without question. I question it now. > 2. JIT compilation onto the target machine should be valid for CTFE. I agree. > 3. The results of CTFE should be as reproducible as runtime results are. The definition should provide a minimum precision, not a maximum. As long as the runtime results comply with a minimum precision, they are D standard compliant. I feel kinda strongly about this. (Note that Go uses infinite precision for all integer constant folding. I think that is superior to what D does, which limits the precision to the target integer size.) My earlier proposal to provide functions roundToFloat and roundToDouble at least provide solid documentation at points in an algorithm where precision ceilings are required. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
April 25, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 --- Comment #13 from Don <clugdbug@yahoo.com.au> 2013-04-25 08:07:33 PDT --- (In reply to comment #12) > (In reply to comment #11) > > > This is about making compile-time behave the same as runtime. > > Floating point answers can (and do) vary depending on optimization settings. This is true for C and C++ compilers, too, even though the arithmetic is Standard compliant. Sure, but in practice the semantics are predictable. It's not "all bets are off". The reality is, x87, 68K and Itanium may do intermediate operations at 80 bit precision, some embedded systems use alias float = double and all other systems use the precision of the largest operands. There are only these three possibilities to worry about. And there will never be any more. All new systems will use the precision of the largest operands. That's completely different from "the semantics are not even consistent during compilation of a single module". > > Specifically: > > 1. A manifest constant should not be carrying extra precision. That's simply > > incorrect. > > This is an assertion that earlier I would have accepted without question. I question it now. If you can have a floating point constant that's between float.max and float.infinity, it's not an IEEE value. That sucks. > > 2. JIT compilation onto the target machine should be valid for CTFE. > > I agree. > > > 3. The results of CTFE should be as reproducible as runtime results are. > > The definition should provide a minimum precision, not a maximum. As long as the runtime results comply with a minimum precision, they are D standard compliant. > > I feel kinda strongly about this. So do I. I think it is completely wrong. The D spec also says that you can assume IEEE behaviour. If extra arbitrary precision is possible, it is not IEEE. It's back to the bad old days. Basically it makes ALL floating point operations into implementation-defined behaviour! > (Note that Go uses infinite precision for all integer constant folding. I think that is superior to what D does, which limits the precision to the target integer size.) I think infinite precision is a big mistake. When CTFE becomes capable of running BigInt, it can be used in those rare cases when it's actually required. > My earlier proposal to provide functions roundToFloat and roundToDouble at least provide solid documentation at points in an algorithm where precision ceilings are required. That would be a useful guarantee. That would be enough to deal with my original test case. It does not deal with the second one. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
April 25, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 bearophile_hugs@eml.cc changed: What |Removed |Added ---------------------------------------------------------------------------- CC| |bearophile_hugs@eml.cc --- Comment #14 from bearophile_hugs@eml.cc 2013-04-25 08:33:01 PDT --- (In reply to comment #13) > I think infinite precision is a big mistake. When CTFE becomes capable of running BigInt, it can be used in those rare cases when it's actually required. I think multi-precision for integral constant folding is a different discussion topic. I think it's better to keep this discussion focused on floating point values only. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
April 25, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 --- Comment #15 from Walter Bright <bugzilla@digitalmars.com> 2013-04-25 12:11:21 PDT --- Don, I think we've reached an impasse here. How about we duke it out at Dcon? I think some beers will get us to a solution! -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
April 26, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 --- Comment #16 from bearophile_hugs@eml.cc 2013-04-25 17:57:36 PDT --- (In reply to comment #8) > There's a nice discussion here: > > http://www.exploringbinary.com/double-rounding-errors-in-floating-point-conversions/ That's a nice article. I have converted his two examples to a single D program: import std.stdio; void main() { real r = 0.5000000894069671353303618843710864894092082977294921875L; double d = 0.5000000894069671353303618843710864894092082977294921875; float f = 0.5000000894069671353303618843710864894092082977294921875f; float fd = 0.5000000894069671353303618843710864894092082977294921875; writefln("r = %a", r); writefln("d = %a", d); writefln("f = %a", f); writefln("fd = %a", fd); double r2 = 0.5000000298023224154508881156289135105907917022705078125L; double d2 = 0.5000000298023224154508881156289135105907917022705078125; float f2 = 0.5000000298023224154508881156289135105907917022705078125f; float fd2 = 0.5000000298023224154508881156289135105907917022705078125; writefln("r2 = %a", r2); writefln("d2 = %a", d2); writefln("f2 = %a", f2); writefln("fd2 = %a", fd2); } It seems dmd on Windows lacks both rounding problems discussed there. Output (the gdc and ldc tests are done on dpaste): dmd 32 bit Windows: r = 0x1.000002fffffffbfep-1 d = 0x1.000003p-1 f = 0x1.000002p-1 fd = 0x1.000002p-1 r2 = 0x1.000001p-1 d2 = 0x1.000001p-1 f2 = 0x1.000002p-1 fd2 = 0x1.000002p-1 GDC 2.060 64 bit Linux: r = 0x8.000017ffffffep-4 d = 0x1.000003p-1 f = 0x1.000002p-1 fd = 0x1.000002p-1 r2 = 0x1.000001p-1 d2 = 0x1.000001p-1 f2 = 0x1.000002p-1 fd2 = 0x1.000002p-1 LDC 2.060 64 bit Linux: r = 0x8.000017ffffffep-4 d = 0x1.000003p-1 f = 0x1.000004p-1 fd = 0x1.000004p-1 r2 = 0x1.000001p-1 d2 = 0x1.000001p-1 f2 = 0x1p-1 fd2 = 0x1p-1 -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
April 26, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 --- Comment #17 from Don <clugdbug@yahoo.com.au> 2013-04-26 00:52:04 PDT --- (In reply to comment #15) > Don, I think we've reached an impasse here. How about we duke it out at Dcon? I think some beers will get us to a solution! I was going to suggest the same thing! -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
August 02, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 yebblies <yebblies@gmail.com> changed: What |Removed |Added ---------------------------------------------------------------------------- CC| |yebblies@gmail.com --- Comment #18 from yebblies <yebblies@gmail.com> 2013-08-02 14:34:14 EST --- (In reply to comment #15) > Don, I think we've reached an impasse here. How about we duke it out at Dcon? I think some beers will get us to a solution! And the result is....? -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
August 22, 2013 [Issue 9937] CTFE floats don't overflow correctly | ||||
---|---|---|---|---|
| ||||
Posted in reply to Don | http://d.puremagic.com/issues/show_bug.cgi?id=9937 --- Comment #19 from Don <clugdbug@yahoo.com.au> 2013-08-22 00:57:25 PDT --- (In reply to comment #18) > (In reply to comment #15) > > Don, I think we've reached an impasse here. How about we duke it out at Dcon? I think some beers will get us to a solution! > > And the result is....? Well, we didn't spend much time on it. I've realized a few things since then: (1) My statement about x87 being the only case where you can get extra precision, is wrong. Machines with FMA can effectively have twice double precision on some operations. The 80-precision that DMD currently uses, is actually not enough, even for x86-64. (2) We have a few things conflated here. The most severe bug in the current situation is the example in comment 4: the compiler acts as though extra bits of precision can be transferred from compile time to run time. This has a simple solution, see below. (3) The solution to my initial test case is less clear. There needs to be a way to reliably dump extra precision from a calculation. Walter's example in comment 10 is one possibility. ---- Now, to fix comment 4: All that needs to happen to fix this, is that floating point values should be rounded to fit the target type *at the end of CTFE*, as part of the existing scrubbing process. They should not be carrying extra precision that could not possibly exist at runtime. This rounding does not apply to const-folding (where things such as inlining could happen which might preserve more precision). The philosophy then would be, const-folding never reduces precision below what the machine can support. But in cases where a CTFE value must be created, such as in a template value parameter, the result has a single value throughout the program. Any extra precision it used in generating that value is entirely CTFE's business and should not leak into the rest of the compiler. Now that I've split CTFE off completely from const-folding, it's possible to make this distinction. This would fix the issue in comment 4, but doesn't affect anything else. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: ------- |
Copyright © 1999-2021 by the D Language Foundation