grauzone wrote:
Andrei Alexandrescu wrote:
grauzone wrote:
Andrei Alexandrescu wrote:
Something just dawned on me: in safe mode, struct static member functions will be preferred to struct non-static member functions.

Why?

Consider:

struct List(T) {
    T payload;
    List * next;

    void prepend(List * newNode) {
        newNode.next = &this;
    }
}

This code can't make it in safe mode because it takes the address of this. In general, the compiler must assume that you might have created a List object on the stack, e.g.:

List * someFun() {
    List local;
    List * lst = new List;
    local.prepend(lst);
    return lst;
}

Now even if there is no ostensible local address taking, the code is in error because it has escaped the address of a local.

So prepend() cannot be compiled. The way to make it compile in safe mode is:


struct List(T) {
    T payload;
    List * next;

    static void prepend(List * zis, List * newNode) {
        newNode.next = zis;
    }
}

Now the code compiles and is actually safe because it is impossible to pass the address of a local into prepend.

Maybe I don't get it, but how to you call prepend() from safe code?

module(safe) wyda;

void main() {
    auto lst1 = new List;
    auto lst2 = new List;
    List.prepend(lst1, lst2)
}

I see... in this case, I'd say the user should be forced to allocate List on the heap by making List a class.

Well we'd still like to benefit from structs and pointers in safe mode. The point is to tighten the screws just as much as needed to achieve interesting properties, but not (much) tighter.


Andrei

Reply via email to