On Thursday, 4 April 2013 at 01:07:08 UTC, Zach the Mystic wrote:
'scope ref': The only existing documentation on scope
parameters: http://dlang.org/function.html suggests that
references to them simply cannot leave the function they find
themselves in. But this is *not* what the temp ref feature is
about. Say you have this temp ref function:
ref int func(@temp ref int a) { return a; }
According to the spec, it clearly violates 'scope', but is
nonetheless valid and safe, as far as I can tell. The compiler
can easily track the scope of a given lvalue at the call site:
static int* x;
static int y;
x = *func(3); // Error: result of func(3) is assumed to be local
x = *func(y); // Pass: address of y is known to be global
This kind of safety checking is not yet implemented, but is
suggested in DIP25, http://wiki.dlang.org/DIP25 . I believe it
is the right way to go. The locality of the return by reference
is assumed to be as local as the reference which is passed into
it. So the temp '3' reference would make the result of func(3)
yield a local, barring any other information which would allow
the compiler to safely assume otherwise. In essence, '@temp
ref' can escape its scope safely because the locality of the
result is not its responsibility.
On the other hand, a '@temp ref' parameter *should* be prevented
from being assigned directly to a global, since it might be
stack-allocated:
static int* x;
void func(@temp ref int a) {
x = &a; // Error, 'a' might be stack-allocated
}
This *would* be an acceptable error. It's completely unsafe to
assume that 'a' is located anywhere but the stack. But it's very
different from a 'scope' parameter, which expressly forbids this,
as opposed to the fortuitous coincidence that allows you to know
that 'x = &a' is an error in this particular case. To have 'scope
ref' implicitly mean '@temp ref' would be conflating two
different features, I think, which only happen to have one thing
in common.