Constancy lost when compiling template mixin

Janice Caron caron800 at googlemail.com
Tue Dec 11 02:54:48 PST 2007


The following program won't compile (and I think it should)

    void main()
    {
        A!(float) a;
    }

    struct A(V:V)
    {
        pragma(msg,"Compiling A!(" ~ V.stringof ~ ")");
        alias typeof(V) M;
        pragma(msg,"type of M is " ~ M.stringof);

        V[] a;

        template B(U:U)
        {
            pragma(msg,"Compiling A.B!(" ~ U.stringof ~ ")");
            U* p() { return a.ptr; }
            pragma(msg,"Compiled A.B!(" ~ U.stringof ~ ")");
        }

        const
        {
            pragma(msg,"About to compile A.B!(const(" ~ M.stringof ~ "))");
            mixin B!(const(M));
            pragma(msg,"Finished compiling A.B!(const(" ~ M.stringof ~ "))");
        }

        pragma(msg,"Compiled A!(" ~V.stringof ~ ")");
    }


During compilation, the following gets printed out:

    Compiling A!(float)
    type of M is float
    About to compile A.B!(const(float))
    Compiling A.B!(float)
    Compiled A.B!(float)
    Finished compiling A.B!(const(float))
    Compiled A!(float)
    test.d(17): Error: cannot implicitly convert expression
(cast(const(float)*)(this.a)) of type const(float)* to float*
    test.d(3): template instance test.A!(float) error instantiating


As you can see, the pragma within the const block spits out "About to
compile A.B!(const(float))". However, when A.B is mixed in, the pragma
at the start of A.B prints "Compiling A.B!(float)" - NOT (as one might
expect) "Compiling A.B!(const(float))".

The constancy of "const(float)" has been lost! U is now just "float",
instead of "const(float)".

In consequence, the return type of p() is wrong, and the "cannot
implicitly convert" error results.

The REAL error, however, is that U should be "const(float)", not
"float". What happened? Is this a bug, or am I doing something wrong?



More information about the Digitalmars-d mailing list