On Saturday, 19 February 2022 at 12:24:04 UTC, Mike Parker wrote:
> This is the discussion thread for the Final Review of DIP 1035, "@system Variables":
https://github.com/dlang/DIPs/blob/4d73e17901a3a620bf59a2a5bfb8c433069c5f52/DIPs/DIP1035.md
The review period will end at 11:59 PM ET on March 5, or when I make a post declaring it complete. Discussion in this thread may continue beyond that point.
Here in the discussion thread, you are free to discuss anything and everything related to the DIP. Express your support or opposition, debate alternatives, argue the merits, etc.
However, if you have any specific feedback on how to improve the proposal itself, then please post it in the feedback thread. The feedback thread will be the source for the review summary I write at the end of this review round. I will post a link to that thread immediately following this post. Just be sure to read and understand the Reviewer Guidelines before posting there:
https://github.com/dlang/DIPs/blob/master/docs/guidelines-reviewers.md
And my blog post on the difference between the Discussion and Feedback threads:
https://dlang.org/blog/2020/01/26/dip-reviews-discussion-vs-feedback/
Please stay on topic here. I will delete posts that are completely off-topic.
While this DIP will solve most of the issues of @safe
__traits(getMember, xxx, yyy)
fetching private members, there is one thing that will remain a problem: destructors.
The issue is that we want a way to specify a destructor so that it could be called by @safe
code at end of the lifetime of an instance, but not early:
auto shouldBeSafe()
{ ObjectWithDestructor x;
}
auto shouldBeSystem()
{ ObjectWithDestructor x;
__traits(getMember, x, "__dtor")();
}
For that to work, we will either have to make privacy inviolable from @safe
(the destructor that does not want to be called early would be private, and object.destroy
would be changed to be @system
for private destructors), or add some alternative way to define destructors.
Why we want to do that at all? DIP1000. Most of the potential of DIP1000 is wasted if you cannot prevent destruction before end of the scope:
@safe void abuse()
{ auto cont = SomeRaiiContainer([1,2,3]);
scope ptr = &cont.front;
destroy(cont);
int oops = *ptr;
}
Yes, you can prevent that by also marking abuse
@live
. But I think we ought to do better than that. As I see it, @live
is mainly meant as a partial memory safety mechanishm for low-level code that cannot be @safe
. It isn't intended that you start to mark your average @safe
code as @live
, that would be terribly onerous. So we don't want to settle for our libraries being memory safe in @live
, if we can make them memory safe in normal @safe
.
This is not intended as an argument against DIP1035, in fact I'm still in favour of it. I just wanted to point out that it does not entirely solve the problem of __traits(getMember, xxx, yyy)
bypassing privacy.