]> git.ipfire.org Git - thirdparty/gcc.git/commit
d/dmd: Merge upstream dmd e9420cfbf
authorIain Buclaw <ibuclaw@gdcproject.org>
Fri, 13 Mar 2020 20:03:02 +0000 (21:03 +0100)
committerIain Buclaw <ibuclaw@gdcproject.org>
Fri, 13 Mar 2020 20:03:02 +0000 (21:03 +0100)
commit5b74dd0a2278365eb562d9d1999c3c11cddb733c
treed50cf33dd430febb733c654fc1ea60dc7a34609f
parentdb3fa3476e9e922ca3e283df03ebd14be7220b6e
d/dmd: Merge upstream dmd e9420cfbf

1. Implement DIP 1010 - (Static foreach)

Support for 'static foreach' has been added.  'static foreach' is a conditional
compilation construct that is to 'foreach' what 'static if' is to 'if'.  It is
a convenient way to generate declarations and statements by iteration.

    import std.conv: to;

    static foreach(i; 0 .. 10)
    {

        // a 'static foreach' body does not introduce a nested scope
        // (similar to 'static if').

        // The following mixin declaration is at module scope:
        // declares 10 variables x0, x1, ..., x9
        mixin('enum x' ~ to!string(i) ~ ' = i;');
    }

    import std.range: iota;
    // all aggregate types that can be iterated with a standard 'foreach'
    // loop are also supported by static foreach:
    static foreach(i; iota(10))
    {
        // we access the declarations generated in the first 'static foreach'
        pragma(msg, "x", i, ": ", mixin(`x` ~ to!string(i)));
        static assert(mixin(`x` ~ to!string(i)) == i);
    }

    void main()
    {
        import std.conv: text;
        import std.typecons: tuple;
        import std.algorithm: map;
        import std.stdio: writeln;

        // 'static foreach' has both declaration and statement forms
        // (similar to 'static if').

        static foreach(x; iota(3).map!(i => tuple(text("x", i), i)))
        {
            // generates three local variables x0, x1 and x2.
            mixin(text(`int `,x[0],` = x[1];`));

            scope(exit) // this is within the scope of 'main'
            {
                writeln(mixin(x[0]));
            }
        }

        writeln(x0," ",x1," ",x2); // first runtime output
    }

2. Aliases can be created directly from a '__trait'.

Aliases can be created directly from the traits that return symbol(s) or
tuples.  This includes 'getMember', 'allMembers', 'derivedMembers', 'parent',
'getOverloads', 'getVirtualFunctions', 'getVirtualMethods', 'getUnitTests',
'getAttributes' and finally 'getAliasThis'.  Previously an 'AliasSeq' was
necessary in order to alias their return.  Now the grammar allows to write
shorter declarations:

    struct Foo
    {
        static int a;
    }

    alias oldWay = AliasSeq!(__traits(getMember, Foo, "a"))[0];
    alias newWay = __traits(getMember, Foo, "a");

To permit this it was more interesting to include '__trait' in the basic types
rather than just changing the alias syntax. So additionally, wherever a type
appears a '__trait' can be used, for example in a variable declaration:

    struct Foo { static struct Bar {} }
    const(__traits(getMember, Foo, "Bar")) fooBar;
    static assert(is(typeof(fooBar) == const(Foo.Bar)));

3. fix Issue 10100 - Identifiers with double underscores and allMembers

The identifer whitelist has been converted into a blacklist of all possible
internal D language declarations.

Reviewed-on: https://github.com/dlang/dmd/pull/10791
57 files changed:
gcc/d/dmd/MERGE
gcc/d/dmd/attrib.c
gcc/d/dmd/attrib.h
gcc/d/dmd/cond.c
gcc/d/dmd/cond.h
gcc/d/dmd/cppmangle.c
gcc/d/dmd/declaration.c
gcc/d/dmd/dinterpret.c
gcc/d/dmd/dmangle.c
gcc/d/dmd/dsymbol.c
gcc/d/dmd/dsymbol.h
gcc/d/dmd/expression.c
gcc/d/dmd/expression.h
gcc/d/dmd/expressionsem.c
gcc/d/dmd/func.c
gcc/d/dmd/hdrgen.c
gcc/d/dmd/init.c
gcc/d/dmd/intrange.c
gcc/d/dmd/json.c
gcc/d/dmd/mtype.c
gcc/d/dmd/mtype.h
gcc/d/dmd/parse.c
gcc/d/dmd/parse.h
gcc/d/dmd/scope.h
gcc/d/dmd/statement.c
gcc/d/dmd/statement.h
gcc/d/dmd/statementsem.c
gcc/d/dmd/traits.c
gcc/d/dmd/visitor.h
gcc/testsuite/gdc.test/compilable/b12001.d [new file with mode: 0644]
gcc/testsuite/gdc.test/compilable/json.d
gcc/testsuite/gdc.test/compilable/staticforeach.d [new file with mode: 0644]
gcc/testsuite/gdc.test/compilable/test11169.d
gcc/testsuite/gdc.test/compilable/test17819.d [new file with mode: 0644]
gcc/testsuite/gdc.test/compilable/test18871.d [new file with mode: 0644]
gcc/testsuite/gdc.test/compilable/test7815.d [moved from gcc/testsuite/gdc.test/fail_compilation/fail7815.d with 92% similarity]
gcc/testsuite/gdc.test/compilable/test7886.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/e7804_1.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/e7804_2.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/fail11169.d [deleted file]
gcc/testsuite/gdc.test/fail_compilation/fail19182.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/fail19336.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/fail19520.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/fail2195.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/fail7886.d [deleted file]
gcc/testsuite/gdc.test/fail_compilation/staticforeach1.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/staticforeach2.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/staticforeach3.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/test17307.d [new file with mode: 0644]
gcc/testsuite/gdc.test/fail_compilation/traits_alone.d [new file with mode: 0644]
gcc/testsuite/gdc.test/runnable/arrayop.d
gcc/testsuite/gdc.test/runnable/constfold.d
gcc/testsuite/gdc.test/runnable/e7804.d [new file with mode: 0644]
gcc/testsuite/gdc.test/runnable/imports/template13478a.d
gcc/testsuite/gdc.test/runnable/staticforeach.d [new file with mode: 0644]
gcc/testsuite/gdc.test/runnable/test42.d
gcc/testsuite/gdc.test/runnable/traits.d