[dmd-internals] Painting literals in CTFE

Iain Buclaw ibuclaw at ubuntu.com
Wed Aug 28 03:08:57 PDT 2013


On 28 August 2013 10:18, Don Clugston <dclugston at gmail.com> wrote:
> There are actually two operations being performed.
> (1) Converting an IEEE float <-> int and double<->long.  This is 100%
> portable. It does not depend on endianness. (Unless endianness of floating
> point values is different from endianness of integer values, but I don't
> think you could define BigEndian/LittleEndian in that case, so I'm not sure
> that D could ever support such a system, and according to Wikipedia there
> are no such systems which support IEEE754).
>
> (2) Converting the compilers internal representation, into an IEEE float.
> This is not portable.
>
> In theory, CTFE only needs (1). But, because it is currently using the
> compiler's internal representation, it's using (2).
>
> I plan to move CTFE to a JIT-compatible implementation, which will mean it
> will only be using (1) internally. But it will still need (2) when doing the
> CTFE compile step.
>

My stance of course would be to avoid using IEEE floats directly, and
instead perform all operation on an internal type in JIT (eg:
std.numeric.CustomFloat as an example).

> Really what should happen is that (2) should be put into port.c/target.c.
> To some degree I'm waiting for the D port, when we will have defined sizes
> for builtin types.
>

OK, I propose port.c, as that is really where all compiler specific
things should go...  However target.c does look more convenient.

---
assert(to->size() == 4 || to->size() == 8);
return Target::paintFloatInt(fromVal, to);
---

vs.

---
if (to->size() == 4)
{
    if (to->isintegral())
    {
        real_t f = fromVal->toReal();
        return new IntegerExp(fromVal->loc, Port::paintToInt(f), to);
    }
    else
    {
        dinteger_t x = fromVal->toInteger();
        return new RealExp(fromVal->loc, Port::paintToFloat(x), to);
    }
}
else if (to->size() == 8)
{
    if (to->isintegral())
    {
        real_t f = fromVal->toReal();
        return new IntegerExp(fromVal->loc, Port::paintToLong(f), to);
    }
    else
    {
        dinteger_t = fromVal->toInteger();
        return new RealExp(fromVal->loc, Port::paintToDouble(x), to);
    }
}

assert(0);
---



-- 
Iain Buclaw

*(p < e ? p++ : p) = (c & 0x0f) + '0';


More information about the dmd-internals mailing list