Stack

How do we get to know the stack size required for a process?

Is there a utility that can do this job?

radha

“radha krishnan” <radha.nk@geind.ge.com> wrote in message
news:cbb46b$8uo$1@inn.qnx.com

How do we get to know the stack size required for a process?


Is there a utility that can do this job?

I have some C routines that can tell you how much stack was used. So you
first build the program with huge stack, let program run for a while. Then
upon terminating it call the routine to tell how much stack was used. Then
rebuild with “normal” stack size. I could post them if you’d like.
Actually I think I grab them from ftp.qnx.com/usr/free/qnx4/

Be aware that stack space is only allocated only when needed. Hence if a
program is build with a 1Meg stack it doesn’t consume 1M. Under QNX4 I
beleive the cost for unused stack is a few bytes per 4 k of stack that is
used to reserver virtual address.

radha

Mario Charest wrote:


“radha krishnan” <> radha.nk@geind.ge.com> > wrote in message
news:cbb46b$8uo$> 1@inn.qnx.com> …

How do we get to know the stack size required for a process?


Is there a utility that can do this job?

I have some C routines that can tell you how much stack was used. So you
first build the program with huge stack, let program run for a while. Then
upon terminating it call the routine to tell how much stack was used. Then
rebuild with “normal” stack size. I could post them if you’d like.
Actually I think I grab them from ftp.qnx.com/usr/free/qnx4/

Yes, i would like to use the software.

One more doubt,

when we allocate stack use -N option, how is it allocated for process and
handler which is attached to the process?
Will this routine be helpful to find the stacksize the handler needs?



Be aware that stack space is only allocated only when needed. Hence if a
program is build with a 1Meg stack it doesn’t consume 1M. Under QNX4 I
beleive the cost for unused stack is a few bytes per 4 k of stack that is
used to reserver virtual address.

radha

radha krishnan wrote:

One more doubt,

when we allocate stack use -N option, how is it allocated for process and
handler which is attached to the process?
Will this routine be helpful to find the stacksize the handler needs?

The physical memory pages for the stack are mapped in on demand (ie. on
fault) in the stack area. So if you build with a 64K stack, and only
use 16K, then only 16K of physical memory is used for backing store to
that stack.

I don’t know what ‘handler’ you’re refering to. But if your refering to
an ISR handler, the stack it is running on isn’t the processes stack -
it’s the kernels. There you have a very limited stack and should avoid
putting any large amount of automatic storage on it.


Cheers,
Adam

QNX Software Systems Ltd.
[ amallory@qnx.com ]

With a PC, I always felt limited by the software available.
On Unix, I am limited only by my knowledge.
–Peter J. Schoenster <pschon@baste.magibox.net>

Adam Mallory wrote:

The physical memory pages for the stack are mapped in on demand (ie. on
fault) in the stack area. So if you build with a 64K stack, and only
use 16K, then only 16K of physical memory is used for backing store to
that stack.

Is this true for QNX6, also?

Davide

Davide Ancri wrote:

Adam Mallory wrote:

The physical memory pages for the stack are mapped in on demand (ie.
on fault) in the stack area. So if you build with a 64K stack, and
only use 16K, then only 16K of physical memory is used for backing
store to that stack.


Is this true for QNX6, also?

Yes - in QNX6, it’s on a per thread basis (ie. each thread has a lazy
stack).

\

Cheers,
Adam

QNX Software Systems Ltd.
[ amallory@qnx.com ]

With a PC, I always felt limited by the software available.
On Unix, I am limited only by my knowledge.
–Peter J. Schoenster <pschon@baste.magibox.net>

Adam Mallory wrote:

The physical memory pages for the stack are mapped in on demand (ie.
on fault) in the stack area. So if you build with a 64K stack, and
only use 16K, then only 16K of physical memory is used for backing
store to that stack.

Is this true for QNX6, also?

Yes - in QNX6, it’s on a per thread basis (ie. each thread has a lazy
stack).

It seems like a strange real-time OS feature for me…

It means I cannot predict when a piece of code dealing with stack (a
simple function call, for example) will generate an exception, that
will be trapped by someone (procnto or microkernel?) to map some other
stack to my process/thread…

I suppose the microkernel is responsible for handling stack faults, so
the operation will be very very fast and will not trigger any kind of
rescheduling, but it remains an unpredictable event costing some
real-time.

Davide

Davide Ancri wrote:

It seems like a strange real-time OS feature for me…

From a real-time perspective, yes. You could just pre-touch your stack
in the main thread to avoid taking the hit at unknown times.

In QNX6.3, you can also specify the stack size and you can set the
preallocated amount for the main thread. Further threads can all have
their stacks allocated in a non lazy fashion.

It means I cannot predict when a piece of code dealing with stack (a
simple function call, for example) will generate an exception, that will
be trapped by someone (procnto or microkernel?) to map some other stack
to my process/thread…

I suppose the microkernel is responsible for handling stack faults, so
the operation will be very very fast and will not trigger any kind of
rescheduling, but it remains an unpredictable event costing some real-time.

It is fairly quick, but you can avoid it if need be.


Cheers,
Adam

QNX Software Systems Ltd.
[ amallory@qnx.com ]

With a PC, I always felt limited by the software available.
On Unix, I am limited only by my knowledge.
–Peter J. Schoenster <pschon@baste.magibox.net>

Adam Mallory wrote:

In QNX6.3, you can also specify the stack size and you can set the
preallocated amount for the main thread. Further threads can all have
their stacks allocated in a non lazy fashion.

Thanks a lot for the clear answer.

Davide

“radha krishnan” <radha.nk@geind.ge.com> wrote in message
news:cbbuk1$hp$1@inn.qnx.com

Mario Charest wrote:


“radha krishnan” <> radha.nk@geind.ge.com> > wrote in message
news:cbb46b$8uo$> 1@inn.qnx.com> …

How do we get to know the stack size required for a process?


Is there a utility that can do this job?

I have some C routines that can tell you how much stack was used. So
you
first build the program with huge stack, let program run for a while.
Then
upon terminating it call the routine to tell how much stack was used.
Then
rebuild with “normal” stack size. I could post them if you’d like.
Actually I think I grab them from ftp.qnx.com/usr/free/qnx4/

Yes, i would like to use the software.

#include <stdio.h>
#include <string.h>

#pragma off (check_stack)

#define A_LITTLE_XTRA_STACK_FOR_MEMSET 48

extern int _STACKLOW, _STACKTOP; // magic :wink:

// used to fill the currently unused portion with filler chars

//+

//+ Name: StackInit
//+ ---------------------------------------------------------------------------
//+ Descr: Prepare for mesureament of stack size
//+ ---------------------------------------------------------------------------
//+ Input: None
//+ ---------------------------------------------------------------------------
//+ Output: None
//+ ---------------------------------------------------------------------------
//+ Return: 0==:correct <=0:-errno >=0: Status
//+ ---------------------------------------------------------------------------
//+ Notes:
//+ ---------------------------------------------------------------------------
//+ Example:
//+ ---------------------------------------------------------------------------
//+ Safety: Thread: [ No] Signal Handler: [No ] Interrupt: [
No]
//+

unsigned char *_esp(void);

#pragma aux _esp = “mov eax,esp” __parm [] __modify __exact __nomemory
[eax];

void StackInit(void) {

unsigned char *stack_bottom, *stack_now;


stack_bottom = (unsigned char *) _STACKLOW;
stack_now = _esp();
memset( stack_bottom,
0x55,
(size_t)((int)stack_now - _STACKLOW - A_LITTLE_XTRA_STACK_FOR_MEMSET));

}

//+

//+ Name: StackUsage
//+ ---------------------------------------------------------------------------
//+ Descr: Return size of used stack
//+ ---------------------------------------------------------------------------
//+ Input: None
//+ ---------------------------------------------------------------------------
//+ Output: Size of used stack
//+ ---------------------------------------------------------------------------
//+ Return: 0==:correct <=0:-errno >=0: Status
//+ ---------------------------------------------------------------------------
//+ Notes: This function isn’t 100% accurate, its provide to get an idea
//+ of stack usage
//+ ---------------------------------------------------------------------------
//+ Example:
//+ ---------------------------------------------------------------------------
//+ Safety: Thread: [ No] Signal Handler: [No ] Interrupt: [
No]
//+

size_t StackUsage(void){

char *stack_bottom = (char near *) _STACKLOW;
size_t i;
size_t stack_size = ( size_t ) _STACKTOP - ( size_t ) _STACKLOW;

// look until it’s NOT an 0x55, if the stack as a value 0x55 in it
// it could be step over, but the risk are low :wink:

for (i=0; stack_bottom _== 0x55 && i < stack_size;i++)
;

return _STACKTOP - _STACKLOW - i;

}
\

_