On Wednesday, 26 June 2013 at 23:02:47 UTC, H. S. Teoh wrote:
Maybe a type distinction akin to C++'s auto_ptr might help?

Yeah, that's what I'm thinking, but I don't really like it. Perhaps I'm trying too hard to cover everything, and should be happier with just doing what C++ does. Full memory safety is prolly out the window anyway.

In std.typecons, there's a Unique!T, but it doesn't look complete. A lot of the code is commented out, maybe it was started back in the days of bug city.

Yeah, I'm started to wonder if it even makes sense to try to mix-n-match GC-based and non-GC-based allocators.

It might not be so bad if we modified D to add a lent storage class, or something, similar to some discussions about scope in the past.

These would be values you may work with, but never keep; assigning them to anything is not allowed and you may only pass them to a function or return them from a function if that is also marked lent. Any regular reference would be implicitly usable as lent.

int* ptr;

void bar(int* a) {
  foo(a); // ok
}

int* foo(lent int* a) {
   bar(a); // error, cannot call bar with lent pointer
   ptr = a; // error, cannot assign lent value to non-lent field
   foo2(a); // ok
   foo(foo2(a)); // ok
   return a; // error, cannot return a lent value
}

lent int* foo2(lent int* a) {
   return a; // ok
}

foo(ptr); // ok (if foo actually compiled)

And finally, if you take the address of a lent reference, that itself is lent; &(lent int*) == lent int**.


Then, if possible, it would be cool if:

lent int* a;
{
  int* b;
  a = b;
}


That was an error, because a outlived b. But since you can't store a anywhere, the only time this would happen would be something like here. And hell maybe we could hammer around that by making lent variables head const and say they must be initialized at declaration, so "lent int* a;" is illegal as well as "a = b;". But we wouldn't want it transitively const, because then:

void fillBuffer(lent char[] buffer) {}

would be disallowed and that is something I would definitely want.



Part of me thinks pure might help with this too.... but eh maybe not because even a pure function could in theory escape a reference via its other parameters.



But with this kind of thing, we could do a nicer pointer type that does:

lent T getThis() { return _this; }
alias getThis this;

and thus implicitly convert our inner pointer to something we can use on the outside world with some confidence that they won't sneak away any references to it. If combined with @disabling the address of operator on the container itself, we could really lock down ownership.

Reply via email to