HPUX Stack Structure

  • Follow


Hi, friends:

I'm interested in how HP-UX organizes the stack for C programs.

My system is "HP-UX sd1 B.11.23 U ia64" and I wrote a simple program which
prints it:

int fun(int n)
{
        int i, a[5] = {5,5,5,5,5};

        if (n == 1)
                for (i = -50; i < 150; i++)
                        printf("%3d : %p = %x\n", i, &a[i], a[i]);
        else
                fun(n -1);
}

I call it from main with 5 as argument. It starts recursively calling
itself until reaching 1, when starts printing the array past its bounds. A
small part of the output is pasted here (note I've previously filled the
stack with 0xabcd to avoid garbage to be printed):

      ...

-13 : 7fffe38c = 0
-12 : 7fffe390 = 20000000
-11 : 7fffe394 = 7fffe358
-10 : 7fffe398 = 20000000
 -9 : 7fffe39c = 7e7e5c20
 -8 : 7fffe3a0 = 20000000
 -7 : 7fffe3a4 = 7e7e2580
 -6 : 7fffe3a8 = 0
 -5 : 7fffe3ac = 1a
 -4 : 7fffe3b0 = 1
 -3 : 7fffe3b4 = fffffffd
 -2 : 7fffe3b8 = abcd
 -1 : 7fffe3bc = abcd
  0 : 7fffe3c0 = 5
  1 : 7fffe3c4 = 5
  2 : 7fffe3c8 = 5
  3 : 7fffe3cc = 5
  4 : 7fffe3d0 = 5
  5 : 7fffe3d4 = abcd
  6 : 7fffe3d8 = abcd
  7 : 7fffe3dc = abcd
  8 : 7fffe3e0 = 2
  9 : 7fffe3e4 = abcd
 10 : 7fffe3e8 = abcd
 11 : 7fffe3ec = abcd
 12 : 7fffe3f0 = 5
 13 : 7fffe3f4 = 5
 14 : 7fffe3f8 = 5
 15 : 7fffe3fc = 5
 16 : 7fffe400 = 5
 17 : 7fffe404 = abcd
 18 : 7fffe408 = abcd
 19 : 7fffe40c = abcd
 20 : 7fffe410 = 3
 21 : 7fffe414 = abcd

      ...

But I was expecting to see return addresses, frame pointers and all that
stuff between "frames". I can't also see where "i" local variables are.

I couldn't find information about this in the Internet, only a litle
article for PA-RISC HP-UX (but mine is IA64).

Can somebody help me with this?

Thanks in advance!

-- 

Heriberto
0
Reply Heriberto 2/16/2007 5:05:09 PM

Heriberto Bens wrote:
> Hi, friends:
> 
> I'm interested in how HP-UX organizes the stack for C programs.
> 
> My system is "HP-UX sd1 B.11.23 U ia64" and I wrote a simple program which
> prints it:

The ia64 is rather important.. because it lets you know why you see
things the way you do. If you look at:
http://developer.intel.com/design/itanium/manuals/iiasdmanual.htm,
you'll see that ia64 uses a Register Stack Engine (RSE) model.
Register frames (such as when you branch to a new subroutine) get
pushed onto a stack consisting solely of such frames. Memory used
within a subroutine which isn't in registers is in a different
stack (tradtional stack, Data stack, whatever you want to think of
it as).

Presumably you can now guess why you see what you're seeing. You're
printing out your stack local variables, which aren't implemented
as registers by your compiler.. hence you're dumping the contents
of your data stack. Your RSE is elsewhere (and managed separately,
and quite frankly you *really* don't want to mess with it as a lot
of that management is done by the processor). When you see references
in HP-UX 11i v1.5 and higher documentation to the RSE stack, that's
what it is refering to (ref: maxrsessiz(5), etc.).

Don

> 
> int fun(int n)
> {
>         int i, a[5] = {5,5,5,5,5};
> 
>         if (n == 1)
>                 for (i = -50; i < 150; i++)
>                         printf("%3d : %p = %x\n", i, &a[i], a[i]);
>         else
>                 fun(n -1);
> }
> 
> I call it from main with 5 as argument. It starts recursively calling
> itself until reaching 1, when starts printing the array past its bounds. A
> small part of the output is pasted here (note I've previously filled the
> stack with 0xabcd to avoid garbage to be printed):
> 
>       ...
> 
> -13 : 7fffe38c = 0
> -12 : 7fffe390 = 20000000
> -11 : 7fffe394 = 7fffe358
> -10 : 7fffe398 = 20000000
>  -9 : 7fffe39c = 7e7e5c20
>  -8 : 7fffe3a0 = 20000000
>  -7 : 7fffe3a4 = 7e7e2580
>  -6 : 7fffe3a8 = 0
>  -5 : 7fffe3ac = 1a
>  -4 : 7fffe3b0 = 1
>  -3 : 7fffe3b4 = fffffffd
>  -2 : 7fffe3b8 = abcd
>  -1 : 7fffe3bc = abcd
>   0 : 7fffe3c0 = 5
>   1 : 7fffe3c4 = 5
>   2 : 7fffe3c8 = 5
>   3 : 7fffe3cc = 5
>   4 : 7fffe3d0 = 5
>   5 : 7fffe3d4 = abcd
>   6 : 7fffe3d8 = abcd
>   7 : 7fffe3dc = abcd
>   8 : 7fffe3e0 = 2
>   9 : 7fffe3e4 = abcd
>  10 : 7fffe3e8 = abcd
>  11 : 7fffe3ec = abcd
>  12 : 7fffe3f0 = 5
>  13 : 7fffe3f4 = 5
>  14 : 7fffe3f8 = 5
>  15 : 7fffe3fc = 5
>  16 : 7fffe400 = 5
>  17 : 7fffe404 = abcd
>  18 : 7fffe408 = abcd
>  19 : 7fffe40c = abcd
>  20 : 7fffe410 = 3
>  21 : 7fffe414 = abcd
> 
>       ...
> 
> But I was expecting to see return addresses, frame pointers and all that
> stuff between "frames". I can't also see where "i" local variables are.
> 
> I couldn't find information about this in the Internet, only a litle
> article for PA-RISC HP-UX (but mine is IA64).
> 
> Can somebody help me with this?
> 
> Thanks in advance!
> 
0
Reply Don 2/16/2007 5:43:57 PM


On Fri, 16 Feb 2007 17:43:57 +0000, Don Morris wrote:

> 
> The ia64 is rather important.. because it lets you know why you see
> things the way you do. If you look at:
> http://developer.intel.com/design/itanium/manuals/iiasdmanual.htm,
> you'll see that ia64 uses a Register Stack Engine (RSE) model.
> Register frames (such as when you branch to a new subroutine) get
> pushed onto a stack consisting solely of such frames. Memory used
> within a subroutine which isn't in registers is in a different
> stack (tradtional stack, Data stack, whatever you want to think of
> it as).
> 
> Presumably you can now guess why you see what you're seeing. You're
> printing out your stack local variables, which aren't implemented
> as registers by your compiler.. 

Thank you very much, now I understand it. My compiler (gcc), as you say,
doesn't implement my variables as registers, so they appear on the stack.
But.. is this what compilers usually do? Wouldn't it be better to put them
in registers to take advantage of the RSE model, in the same way as
register windows are used in SPARC?

Thanks again!

-- 

Heriberto
0
Reply Heriberto 2/17/2007 12:00:51 AM

Heriberto Bens <peekpoker@yahoo.com> writes:

> My compiler (gcc), as you say,
> doesn't implement my variables as registers, so they appear on the stack.

Try turning optimization on.

> But.. is this what compilers usually do? Wouldn't it be better to put them
> in registers to take advantage of the RSE model, in the same way as
> register windows are used in SPARC?

Gcc puts variables in memory on SPARC as well, unless you turn
optimization on. You'll notice that almost all open-source projects
compile with 'gcc -g -O2 ...' -- that way you get decent code,
that is still somewhat easy to debug.

Cheers,
-- 
In order to understand recursion you must first understand recursion.
Remove /-nsp/ for email.
0
Reply Paul 2/17/2007 4:57:38 AM

On Fri, 16 Feb 2007 20:57:38 -0800, Paul Pluzhnikov wrote:

> Heriberto Bens <peekpoker@yahoo.com> writes:
> 
>> My compiler (gcc), as you say,
>> doesn't implement my variables as registers, so they appear on the stack.
> 
> Try turning optimization on.

Yes, it works ;-)

Thanks!

-- 

Heriberto
0
Reply Heriberto 2/17/2007 3:32:27 PM

4 Replies
115 Views

(page loaded in 0.811 seconds)

Similiar Articles:













7/11/2012 11:37:41 PM


Reply: