Re: testing if data is allocated on the stack or heap

2017-10-18 Thread Biotronic via Digitalmars-d-learn
It's worth pointing out, btw, that the main reason for this code 
is to help drug diagnose his or her problem, not to be the 
be-all, end-all of stack identifying functions. :)


It will of course not correctly identify pointers to variables on 
other threads' stacks, and fiber stacks probably trip it up bad.


--
  Biotronic


Re: testing if data is allocated on the stack or heap

2017-10-18 Thread Biotronic via Digitalmars-d-learn
On Tuesday, 17 October 2017 at 23:59:19 UTC, Steven Schveighoffer 
wrote:

On 10/17/17 7:32 PM, flamencofantasy wrote:

On Tuesday, 17 October 2017 at 17:27:17 UTC, Biotronic wrote:

On Tuesday, 17 October 2017 at 15:33:02 UTC, drug wrote:

[...]


I have very little knowledge about sbrk, so here's my 
solution.


Tested on win32 and win64.

[...]


Try this;

unittest {
     int[5*1024] n;
     int* p = new int;

     assert(n.onStack);
     assert(!p.onStack);
}


The second is wrong. You are asserting that the storage of p is 
not on the stack, but it is.


What p *points at* is not on the stack.

So the correct call should be:

assert(!(*p).onStack);

or (IMO) less ugly: assert(!onStack(*p));

-Steve


No, the second is correct - the ref overload is only chosen when 
p is not implicitly castable to void*. In fact, the second assert 
passes, it's the first one that causes problems.


I've written an improved version, that probably still has 
problems. If flamencofantasy would like to point out other 
shortcomings, I'd love to learn.


module stackCheck;

private size_t stackStart;
enum size_t pageSize = 0x1000;

static this() {
import core.stdc.stdlib : alloca;
stackStart = cast(size_t)alloca(size_t.sizeof);
}

bool onStack(void* p) {
size_t end = cast(size_t)
size_t pp = cast(size_t)p;
size_t ss = stackStart;

if (end > ss) {
end &= ~(pageSize-1);
ss  &= ~(pageSize-1);
end += pageSize;
return pp >= ss && pp <= end;
} else {
end &= ~(pageSize-1);
ss  &= ~(pageSize-1);
ss += pageSize;
return pp <= ss && pp >= end;
}
}

bool onStack(T)(ref T p) {
return ().onStack;
}

unittest {
int n;
int* p = new int;

assert(n.onStack);
assert(!p.onStack);
}

unittest {
int[5*1023] n;
int* p = new int;

assert(n.onStack);
assert(!p.onStack);
}


Re: testing if data is allocated on the stack or heap

2017-10-18 Thread Jonathan M Davis via Digitalmars-d-learn
On Tuesday, October 17, 2017 18:33:02 drug via Digitalmars-d-learn wrote:
> My code fails and I guess the reason is I have a slice to data in the
> stack and it becomes garbage in some moment. So I need a way to check
> where data is placed. Is it right that it can be done in linux using
> `sbrk` so that if the addr of data is less than `sbrk(0)` returning then
> data is on the stack and on the heap in other case?

In theory, @safe is supposed to help with this such that any code that
sliced a static array would be @system or @trusted, which would seriously
narrow down the search space when something goes wrong with memory, but the
slicing of static arrays typically being treated as @safe is one of the
major, outstanding bugs for @safe. It looks like it's now caught when simply
returning a slice of a static array, but simply slicing a static array is
still considered @safe (even though taking the address of a local variable
does, and it's really the same thing).

So, if you try and use @safe throughout your code, you'll find _some_ of the
potential memory problems but not all of them. All of the work that Walter
has been doing with DIP 1000 should help though.

- Jonathan M Davis



Re: testing if data is allocated on the stack or heap

2017-10-18 Thread flamencofantasy via Digitalmars-d-learn
On Tuesday, 17 October 2017 at 23:59:19 UTC, Steven Schveighoffer 
wrote:

On 10/17/17 7:32 PM, flamencofantasy wrote:

On Tuesday, 17 October 2017 at 17:27:17 UTC, Biotronic wrote:

On Tuesday, 17 October 2017 at 15:33:02 UTC, drug wrote:

[...]


I have very little knowledge about sbrk, so here's my 
solution.


Tested on win32 and win64.

[...]


Try this;

unittest {
     int[5*1024] n;
     int* p = new int;

     assert(n.onStack);
     assert(!p.onStack);
}


The second is wrong. You are asserting that the storage of p is 
not on the stack, but it is.


What p *points at* is not on the stack.

So the correct call should be:

assert(!(*p).onStack);

or (IMO) less ugly: assert(!onStack(*p));

-Steve


you misunderstood, the code is from biotronic's post, i just made 
a static array of 5kb to point out how it fails, in just one way 
out of a dozen other possibilities.


Re: testing if data is allocated on the stack or heap

2017-10-17 Thread Steven Schveighoffer via Digitalmars-d-learn

On 10/17/17 7:32 PM, flamencofantasy wrote:

On Tuesday, 17 October 2017 at 17:27:17 UTC, Biotronic wrote:

On Tuesday, 17 October 2017 at 15:33:02 UTC, drug wrote:

[...]


I have very little knowledge about sbrk, so here's my solution.

Tested on win32 and win64.

[...]


Try this;

unittest {
     int[5*1024] n;
     int* p = new int;

     assert(n.onStack);
     assert(!p.onStack);
}


The second is wrong. You are asserting that the storage of p is not on 
the stack, but it is.


What p *points at* is not on the stack.

So the correct call should be:

assert(!(*p).onStack);

or (IMO) less ugly: assert(!onStack(*p));

-Steve


Re: testing if data is allocated on the stack or heap

2017-10-17 Thread flamencofantasy via Digitalmars-d-learn

On Tuesday, 17 October 2017 at 17:27:17 UTC, Biotronic wrote:

On Tuesday, 17 October 2017 at 15:33:02 UTC, drug wrote:

[...]


I have very little knowledge about sbrk, so here's my solution.

Tested on win32 and win64.

[...]


Try this;

unittest {
int[5*1024] n;
int* p = new int;

assert(n.onStack);
assert(!p.onStack);
}


Re: testing if data is allocated on the stack or heap

2017-10-17 Thread user1234 via Digitalmars-d-learn

On Tuesday, 17 October 2017 at 17:27:17 UTC, Biotronic wrote:

On Tuesday, 17 October 2017 at 15:33:02 UTC, drug wrote:

[...]


I have very little knowledge about sbrk, so here's my solution.

Tested on win32 and win64.

[...]


Nice solution. Is `stackStart` thread local on purpose?


Re: testing if data is allocated on the stack or heap

2017-10-17 Thread drug via Digitalmars-d-learn

17.10.2017 20:27, Biotronic пишет:

module stackCheck;

private size_t stackStart;
enum size_t pageSize = 0x1000;

static this() {
     import core.stdc.stdlib : alloca;
     stackStart = cast(size_t)alloca(size_t.sizeof) & ~(pageSize-1);
}

bool onStack(void* p) {
     size_t end = (cast(size_t) & ~(pageSize-1)) + pageSize;
     size_t pp = cast(size_t)p;

     if (end > stackStart) {
     return pp >= stackStart && pp <= end;
     } else {
     return pp <= stackStart && pp >= end;
     }
}

bool onStack(T)(ref T p) {
     return ().onStack;
}

unittest {
     int n;
     int* p = new int;

     assert(n.onStack);
     assert(!p.onStack);
}


Thanks! Your solution not only works but is portable also.


Re: testing if data is allocated on the stack or heap

2017-10-17 Thread Biotronic via Digitalmars-d-learn

On Tuesday, 17 October 2017 at 15:33:02 UTC, drug wrote:
My code fails and I guess the reason is I have a slice to data 
in the stack and it becomes garbage in some moment. So I need a 
way to check where data is placed. Is it right that it can be 
done in linux using `sbrk` so that if the addr of data is less 
than `sbrk(0)` returning then data is on the stack and on the 
heap in other case?


I have very little knowledge about sbrk, so here's my solution.

Tested on win32 and win64.

module stackCheck;

private size_t stackStart;
enum size_t pageSize = 0x1000;

static this() {
import core.stdc.stdlib : alloca;
stackStart = cast(size_t)alloca(size_t.sizeof) & 
~(pageSize-1);

}

bool onStack(void* p) {
size_t end = (cast(size_t) & ~(pageSize-1)) + pageSize;
size_t pp = cast(size_t)p;

if (end > stackStart) {
return pp >= stackStart && pp <= end;
} else {
return pp <= stackStart && pp >= end;
}
}

bool onStack(T)(ref T p) {
return ().onStack;
}

unittest {
int n;
int* p = new int;

assert(n.onStack);
assert(!p.onStack);
}

--
  Biotronic


testing if data is allocated on the stack or heap

2017-10-17 Thread drug via Digitalmars-d-learn
My code fails and I guess the reason is I have a slice to data in the 
stack and it becomes garbage in some moment. So I need a way to check 
where data is placed. Is it right that it can be done in linux using 
`sbrk` so that if the addr of data is less than `sbrk(0)` returning then 
data is on the stack and on the heap in other case?


Re: testing if data is allocated on the stack or heap

2017-10-17 Thread drug via Digitalmars-d-learn

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