structs holding on to reference data by pointer

Daniel Davidson nospam at spam.com
Thu Oct 31 10:34:20 PDT 2013


On Thursday, 31 October 2013 at 16:16:36 UTC, bearophile wrote:
>
> That's wrong code, you are escaping a reference to memory (of 
> rc variable) allocated in the stack frame of foo(). The D 
> compiler is not smart enough to recognize the bug. There are 
> optimizations that patch and avoid this bug (like inlining, or 
> allocating rc inside the stack frame of the main) but you can't 
> rely on them.
>

Ahh ok. Because of issues with const members (copying them when 
they are composed in other classes does not work well) I'm trying 
to get around the copy by storing reference data as const(T) *. 
This is why I'm asking. So here are some follow ups:

- As I see it there is grave risk. Is the risk introduced by the 
fact that I am storing a member as const(T)*?
- I assume that if I had created the RC instance on the heap 
there would be no problems. Is there a way in general to ensure 
that a const(T)* is referring to something on the heap as opposed 
to the stack (ideally at compile time).
- What is the root problem - having a const(T)* member which then 
requires code to take address, or taking address? My first 
thought was, just never take address of local static variable - 
which is generally good advice. But once you are in a function 
that takes ref const(T) you can take the address of that as well 
- see modification below. This suffers the same problem but in a 
less obvious way.

Any suggestions welcome.

Thanks
Dan

import opmix.mix;
import plus.tvm.rate_curve;
import std.stdio;

struct RC {
   this(this) { data = data.dup; }
   int[] data;
}

struct T {
   const(RC) *rc;
   void goo() {
     writeln("Data is ", rc.data);
   }
}

T goo(ref RC rc) {
   return T(&rc);
}

T foo() {
   RC rc = { [1,2,3] };
   writeln("Address is ", &rc);
   return goo(rc);
}

void main() {
   T t = foo();
   t.goo();
   writeln("Address is ", t.rc);
}


More information about the Digitalmars-d-learn mailing list