consider:
string foo(){
return q{pragma(msg,"foo");};
}
struct T{
mixin(foo());
mixin(q{
static string foo(){
return q{pragma(msg,"T.foo");};
}
});
}
this prints "foo";
versus:
string foo(){
return q{pragma(msg,"foo");};
}
struct T{
mixin(q{
static string foo(){
return q{pragma(msg,"T.foo");};
}
});
mixin(foo());
}
which prints "T.foo" with DMD 2.054.
To make mixins less bug prone and hacky, I suggest to disallow shadowing
any declaration that is referred to in a mixin declaration in the same
scope.
Another example that demonstrates how weird the current lookup rules are:
string foo(){
return q{pragma(msg,foo);};
}
struct T{
static string qux(){return foo();} // this refers to T.foo.
mixin(q{ // this mixin shadows foo
static string foo(){
return q{pragma(msg,"T.foo");};
}
});
mixin(qux());
}
---
string foo(){
return q{pragma(msg,foo);};
}
struct T{
static string qux(){return foo();} // this refers to foo
mixin(qux()); // because this is evaluated first now.
mixin(q{ // this mixin shadows foo
static string foo(){
return q{pragma(msg,"T.foo");};
}
});
}
I am strongly in favor of disallowing any cases where mixin declarations
shadow declarations that were used to compute mixin declarations in a
scope that allows forward references.
Any thoughts on this?