www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Qualified destructors / immutable objects

reply "Marc =?UTF-8?B?U2Now7x0eiI=?= <schuetzm gmx.net> writes:
     struct S {
         int x;
         ~this() {
             import std.stdio;
             writeln("mutable ~this()");
             x = 1;
         }
     }

     void main() {
         const(S) s1;
         immutable(S) s2;
     }

Prints:

     mutable ~this()
     mutable ~this()

This looks very wrong, although I cannot find a way to actually 
modify immutable memory with it...

Is it a bug?
Jun 12 2015
next sibling parent reply "anonymous" <a b.de> writes:
 I cannot find a way to actually modify immutable memory with 
 it...
a.d: class C { int a; this(int a) { this.a = a; } } struct S { int x; C elem = new C(42); ~this() { import std.stdio; writeln("mutable ~this()"); x = 1; elem.a = 123; } } void foo() { S s2; } void main() { import std.stdio; immutable(S) s1; // Error: cannot modify immutable expression s1.elem.a // s1.elem.a = 43; writeln(s1.elem.a); foo(); writeln(s1.elem.a); } dmd a.d ./a prints: 42 mutable ~this() 123 mutable ~this()
 Is it a bug?
I'll wait with a bug report, but I think this should be forbidden.
Jun 12 2015
parent reply "anonymous" <a b.de> writes:
no need for ~this() to modify immutable data:

class C {
	int a;

	this(int a) {
		this.a = a;
	}
}

struct S {
	C elem = new C(42);
}

void main() {
	import std.stdio;
     immutable(S) s1;

	//  Error: cannot modify immutable expression s1.elem.a
	// s1.elem.a = 43;
	
	writeln(s1.elem.a);

	S s2;
	s2.elem.a = 123;
	writeln(s1.elem.a);
}

Prints:
42
123
Jun 12 2015
next sibling parent "Marc =?UTF-8?B?U2Now7x0eiI=?= <schuetzm gmx.net> writes:
On Friday, 12 June 2015 at 15:36:22 UTC, anonymous wrote:
 no need for ~this() to modify immutable data:
<snip> I think that's a another bug related to init values.
Jun 12 2015
prev sibling parent reply "Daniel Kozak" <kozzi11 gmail.com> writes:
On Friday, 12 June 2015 at 15:36:22 UTC, anonymous wrote:
 no need for ~this() to modify immutable data:

 class C {
 	int a;

 	this(int a) {
 		this.a = a;
 	}
 }

 struct S {
 	C elem = new C(42);
 }

 void main() {
 	import std.stdio;
     immutable(S) s1;

 	//  Error: cannot modify immutable expression s1.elem.a
 	// s1.elem.a = 43;
 	
 	writeln(s1.elem.a);

 	S s2;
 	s2.elem.a = 123;
 	writeln(s1.elem.a);
 }

 Prints:
 42
 123
Is there an existing issue on issue.dlang.org? If not can you report it
Jun 13 2015
parent "anonymous" <a b.de> writes:
 Is there an existing issue on issue.dlang.org? If not can you 
 report it
https://issues.dlang.org/show_bug.cgi?id=10376
Jun 13 2015
prev sibling parent reply "anonymous" <a b.cd> writes:
To come back to destructors and immutable objects:

Even without the default initialized variables issue it is 
possible to modify immutable data:

struct S {
   int[] bar;

   ~this() {
     bar[0] = 123;
   }
}

void foo(immutable(int[]) i) {
   immutable(S) s = immutable S(i);
}

void main() {
   immutable array = [42, 42];
   foo(array);
   // fails
   assert(array == [42, 42]);
}

I'm not sure whether ~this() should be forbidden to modify 
immutable data. Consider e.g. some fields need to be free'd. If 
someone else is using references to such a field after ~this() -> 
segfault, but it could be seen as analogon to the list of 
undefined operations on pointer to GC memory.
Additionally the same happens already for stack allocated fields 
like int[4] inside a (mutable/const/immutable) struct.
Jun 14 2015
parent "Marc =?UTF-8?B?U2Now7x0eiI=?= <schuetzm gmx.net> writes:
On Sunday, 14 June 2015 at 07:28:39 UTC, anonymous wrote:
 To come back to destructors and immutable objects:

 Even without the default initialized variables issue it is 
 possible to modify immutable data:

 struct S {
   int[] bar;

   ~this() {
     bar[0] = 123;
   }
 }

 void foo(immutable(int[]) i) {
   immutable(S) s = immutable S(i);
 }

 void main() {
   immutable array = [42, 42];
   foo(array);
   // fails
   assert(array == [42, 42]);
 }

 I'm not sure whether ~this() should be forbidden to modify 
 immutable data. Consider e.g. some fields need to be free'd. If 
 someone else is using references to such a field after ~this() 
 -> segfault, but it could be seen as analogon to the list of 
 undefined operations on pointer to GC memory.
 Additionally the same happens already for stack allocated 
 fields like int[4] inside a (mutable/const/immutable) struct.
Found this bug report [1], in which Andrei says: "Mutable destructors shouldn't apply to objects that were immutable, otherwise they can mutate immutable objects." [1] https://issues.dlang.org/show_bug.cgi?id=4338#c6
Jun 14 2015