Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-19 Thread Timoses via Digitalmars-d-learn

On Thursday, 19 July 2018 at 06:35:36 UTC, Simen Kjærås wrote:

On Wednesday, 18 July 2018 at 11:28:54 UTC, Timoses wrote:
But why is a context pointer a problem? Is it problematic 
because the context pointer to the main scope can not 
guarantee `immutable`? E.g. if I happened to use data from 
main in a function of the immutable struct then... well then 
what?
The struct would still be immutable, but what would prevent a 
function from using non-immutable data?


It's a known bug: https://issues.dlang.org/show_bug.cgi?id=18563
In the associated discussion 
(https://forum.dlang.org/thread/p7lp2b$1jod$1...@digitalmars.com), 
Steven Schveighoffer points out that an immutable struct may be 
passed to other threads, which would give one thread access to 
another thread's stack. This could be a good enough reason to 
prevent this kind of conversion, but a better error message 
would still make sense.


--
  Simen


Thanks so much for the pointer, Simen. Interesting discussion.


Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-18 Thread Simen Kjærås via Digitalmars-d-learn

On Wednesday, 18 July 2018 at 11:28:54 UTC, Timoses wrote:
But why is a context pointer a problem? Is it problematic 
because the context pointer to the main scope can not guarantee 
`immutable`? E.g. if I happened to use data from main in a 
function of the immutable struct then... well then what?
The struct would still be immutable, but what would prevent a 
function from using non-immutable data?


It's a known bug: https://issues.dlang.org/show_bug.cgi?id=18563
In the associated discussion 
(https://forum.dlang.org/thread/p7lp2b$1jod$1...@digitalmars.com), 
Steven Schveighoffer points out that an immutable struct may be 
passed to other threads, which would give one thread access to 
another thread's stack. This could be a good enough reason to 
prevent this kind of conversion, but a better error message would 
still make sense.


--
  Simen


Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-18 Thread Timoses via Digitalmars-d-learn

On Tuesday, 17 July 2018 at 06:24:12 UTC, Simen Kjærås wrote:


That makes sense. The problem is F has a context pointer to the 
main() block, since it's a non-static struct with methods 
inside a block. It doesn't actually use the context pointer for 
anything, so it possibly shouldn't have one, but it does, so we 
have to work around it.


The fix is to mark F as static, or move it outside the main() 
block.


--
  Simen


Thanks for the explanation.

But why is a context pointer a problem? Is it problematic because 
the context pointer to the main scope can not guarantee 
`immutable`? E.g. if I happened to use data from main in a 
function of the immutable struct then... well then what?
The struct would still be immutable, but what would prevent a 
function from using non-immutable data?

E.g. I could do this

int gnumber = 3;

struct F
{
int i;
void fun() immutable
{
gnumber = 5;
}
}

void main ()
{
immutable F f = F();
f.fun;
}

I declared `fun()` to be an immutable function. So calling the 
immutable struct function `F.fun()` changes a module scope int. 
The same could be applied to local data of the main scope, 
however the following fails:


void main ()
{
int mnumber = 3;
struct F
{
int i;
void fun() immutable
{
// Error: immutable function onlineapp.main.F.fun 
cannot access mutable data mnumber

mnumber = 5;
}
}

immutable F f = F();
f.fun;
}

Is this connected why I can't implicitly convert a local struct 
with a context pointer to immutable? What's the reason behind it?


Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-16 Thread Simen Kjærås via Digitalmars-d-learn

On Monday, 16 July 2018 at 13:13:53 UTC, Timoses wrote:

On Monday, 16 July 2018 at 12:00:57 UTC, Simen Kjærås wrote:

On Monday, 16 July 2018 at 11:43:03 UTC, Timoses wrote:

Why does this fail?


It doesn't. Not using DMD 2.081.1 under Windows, at least. I 
tried adding a bitfield since you mentioned it, but it 
compiles nicely for me. Which version of DMD are you using, 
and are you having the issues with the exact code you posted 
here?


--
  Simen


https://run.dlang.io/is/Pgs527

I'm on 2.080.1. But above is on latest 2.081.1 I believe.

Note that the bottom code snippet in the original post does 
work, while the first one does not.


That makes sense. The problem is F has a context pointer to the 
main() block, since it's a non-static struct with methods inside 
a block. It doesn't actually use the context pointer for 
anything, so it possibly shouldn't have one, but it does, so we 
have to work around it.


The fix is to mark F as static, or move it outside the main() 
block.


--
  Simen


Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-16 Thread Seb via Digitalmars-d-learn

On Monday, 16 July 2018 at 13:13:53 UTC, Timoses wrote:

On Monday, 16 July 2018 at 12:00:57 UTC, Simen Kjærås wrote:

On Monday, 16 July 2018 at 11:43:03 UTC, Timoses wrote:

Why does this fail?


It doesn't. Not using DMD 2.081.1 under Windows, at least. I 
tried adding a bitfield since you mentioned it, but it 
compiles nicely for me. Which version of DMD are you using, 
and are you having the issues with the exact code you posted 
here?


--
  Simen


https://run.dlang.io/is/Pgs527

I'm on 2.080.1. But above is on latest 2.081.1 I believe.

Note that the bottom code snippet in the original post does 
work, while the first one does not.


Yep, run.dlang.io automatically updates itself to the latest 
compiler (you can check this e.g. with -v).


Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-16 Thread Timoses via Digitalmars-d-learn

On Monday, 16 July 2018 at 12:00:57 UTC, Simen Kjærås wrote:

On Monday, 16 July 2018 at 11:43:03 UTC, Timoses wrote:

Why does this fail?


It doesn't. Not using DMD 2.081.1 under Windows, at least. I 
tried adding a bitfield since you mentioned it, but it compiles 
nicely for me. Which version of DMD are you using, and are you 
having the issues with the exact code you posted here?


--
  Simen


https://run.dlang.io/is/Pgs527

I'm on 2.080.1. But above is on latest 2.081.1 I believe.

Note that the bottom code snippet in the original post does work, 
while the first one does not.


Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-16 Thread Simen Kjærås via Digitalmars-d-learn

On Monday, 16 July 2018 at 11:43:03 UTC, Timoses wrote:

Why does this fail?


It doesn't. Not using DMD 2.081.1 under Windows, at least. I 
tried adding a bitfield since you mentioned it, but it compiles 
nicely for me. Which version of DMD are you using, and are you 
having the issues with the exact code you posted here?


--
  Simen


Implicit conversion of struct with methods to immutable in pure function fails

2018-07-16 Thread Timoses via Digitalmars-d-learn

Why does this fail?

struct F
{
int i;
ushort _x;
void x(ushort v) pure
{_x = v;}
ushort x() const
{ return _x; }
}

immutable F f1 = () pure {
F lf = F();
return lf; }();
// Error: cannot implicitly convert expression delegate () => 
lf() of type F to immutable(F)


F makeF() pure
{
F lf = F();
return lf;
}
immutable F f2 = makeF();
// Error: cannot implicitly convert expression makeF() of 
type F to immutable(F)


Removing the methods in struct F compiles fine.

Background: I have a mixin(bitfields!(...)) in the struct which 
utilizes member functions.



/
Idea:
Just found out that it works when making the struct static. But 
why does that help?


Is it because the compiler wouldn't be able to check whether 
methods in the struct are accessing non-immutable data in the 
enclosing context?

That would not make much sense though because the following works:

// Compiles fine!
int modi = 3;
void main ()
{
static struct F
{
int var() immutable { return modi; } // accessing modi 
from module scope

}
immutable f = () pure { F f = F(); return f; }();
}

So my explanation wouldn't make sense, since why would it be okay 
to use module-scope data and not enclosing context data?


So where does that limitation come from that I implicitly convert 
a nested struct to immutable in a pure function?