__rvalue and Move Semantics first draft - aliasing problem/danger
kinke
noone at nowhere.com
Mon Nov 11 11:31:43 UTC 2024
On Sunday, 10 November 2024 at 17:36:25 UTC, Timon Gehr wrote:
> On 11/9/24 23:44, Walter Bright wrote:
>> I'm not sure it's a problem or a danger.
>>
>> Timon mentioned the related problem with:
>>
>> ```
>> callee(__rvalue s, __rvalue s);
>> ```
>>
>> where s would be destroyed twice. This isn't always detectable:
>> ```
>> S* ps = ...;
>> callee(__rvalue *s, __rvalue(*s));
>> ```
>> But can be rendered benign with the blit of S.init after the
>> destructor call.
But that's at least already invalid/undefined in your proposal.
I've used `callee(lval, __rvalue(lval))` to show that the
aliasing problem can occur in valid code too - `lval` isn't
accessed lexically after __rvalue'ing it. __rvalue'ing a global
variable and checking that the global isn't accessed in the
callee is even harder.
> I think the main potential trouble is that there is usually an
> assumption that there is no aliasing between rvalue arguments.
It's not just an assumption, it's an implicit guarantee - a
by-value parameter is analogous to a local in high-level terms,
so of course with its own distinct private memory. Well, until
now. :)
> For example, if a compiler backend assumes no aliasing,
> undefined behavior might be introduced if one of the arguments
> is modified and then the other is read.
This isn't just a problem with compiler optimizations, but in
general:
```D
void callee(const ref S x, S y) {
y.bla = x.bla - 1;
assert(y.bla != x.bla, "have changed ref via value alias!");
}
```
More information about the dip.development
mailing list