Thread overview
[Issue 8562] New: math.pow fails at compile-time
Aug 20, 2012
Caligo
Aug 20, 2012
Caligo
Aug 20, 2012
Don
Aug 20, 2012
Caligo
Aug 20, 2012
Jonathan M Davis
Aug 20, 2012
Caligo
Aug 20, 2012
Caligo
August 20, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=8562

           Summary: math.pow fails at compile-time
           Product: D
           Version: D2
          Platform: x86_64
        OS/Version: Linux
            Status: NEW
          Severity: major
          Priority: P2
         Component: Phobos
        AssignedTo: nobody@puremagic.com
        ReportedBy: iteronvexor@gmail.com


--- Comment #0 from Caligo <iteronvexor@gmail.com> 2012-08-19 22:02:58 PDT ---
template T(){
  enum a = pow(3.0, 6);
  enum b = pow(2, 4.0);
}

unittest
{
  alias T!() t;
}

compiling that I get:

/home/b/phobos/std/math.d(2369): Error: Cannot convert &real to ushort* at
compile time
/home/b/phobos/std/math.d(3292):        called from here: isNaN(y)
/home/b/phobos/std/math.d(3403):        called from here: impl(x,cast(real)y)
/home/b/phobos/std/math.d(3239):        called from here: pow(cast(real)x,y)
t.d(478):        called from here: pow(2,4)
t.d(485): Error: template instance units.T!() error instantiating


I guess technically it's math.isNaN() that's failing?

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 20, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=8562



--- Comment #1 from Caligo <iteronvexor@gmail.com> 2012-08-19 22:09:30 PDT ---
yup, it's math.isNaN().

template T() {
  enum a = isNaN(1.3);
}

unittest
{
  alias T!() t;
}

/home/b/phobos/std/math.d(2369): Error: Cannot convert &real to ushort* at
compile time
t.d(474):        called from here: isNaN(1.3L)
t.d(479): Error: template instance units.T!() error instantiating


God please, will somebody fix this?

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 20, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=8562


Don <clugdbug@yahoo.com.au> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |clugdbug@yahoo.com.au


--- Comment #2 from Don <clugdbug@yahoo.com.au> 2012-08-20 08:29:25 PDT ---
isNan(x) can be implemented at compile time by:

return (x != x);

It's not exactly the same at run time, because it sets the floating point hardware exception flags, whereas isNaN does not. But there are no exception flags at compile time.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 20, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=8562



--- Comment #3 from Caligo <iteronvexor@gmail.com> 2012-08-20 09:57:19 PDT ---
(In reply to comment #2)
> isNan(x) can be implemented at compile time by:
> 
> return (x != x);
> 
> It's not exactly the same at run time, because it sets the floating point hardware exception flags, whereas isNaN does not. But there are no exception flags at compile time.

To avoid the casting in isNaN() you would need to know when it's getting called
at compile-time and when it's getting called at run-time, correct?  There is no
way to know that, so we end up with two functions, isNaN() and staticIsNaN(),
correct?

bool staticIsNaN(R)(R x) if(isFloatingPoint!R)
{
  return x != x;
}

p.s.
why are exception flags being set in a nothrow?

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 20, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=8562


Jonathan M Davis <jmdavisProg@gmx.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |jmdavisProg@gmx.com


--- Comment #4 from Jonathan M Davis <jmdavisProg@gmx.com> 2012-08-20 10:04:39 PDT ---
> To avoid the casting in isNaN() you would need to know when it's getting called at compile-time and when it's getting called at run-time, correct?  There is no way to know that, so we end up with two functions, isNaN() and staticIsNaN(), correct?

Wrong. __ctfe is true during CTFE and not during runtime. So, you can do

if(__ctfe)
{
    //ctfe version
}
else
{
    //normal version
}

http://dlang.org/function.html#interpretation

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 20, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=8562



--- Comment #5 from Caligo <iteronvexor@gmail.com> 2012-08-20 10:23:00 PDT ---
(In reply to comment #4)

great, I didn't know about __ctfe.

Now isInfinity() is failing at compile time because of the same reasons as
isNaN().  How do you check to see if a floating point is infinity at compile?

return x == real.infinity

???

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
August 20, 2012
http://d.puremagic.com/issues/show_bug.cgi?id=8562



--- Comment #6 from Caligo <iteronvexor@gmail.com> 2012-08-20 11:46:03 PDT ---
(In reply to comment #5)

ok, so pow() calls exp2(), which contains tons of asm statements, which means
pow() can't be executed at compile time.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------