[RFC] Dynamically aligning the stack

Steve Ellcey sellcey@imgtec.com
Thu Mar 26 23:28:00 GMT 2015


I am looking at ways of dynamically realigning the runtime stack in GCC.
Currently it looks like x86 is the only architecture that supports this.

The issue that I am trying to address is MSA registers on MIPS.  The O32
MIPS ABI specifies an 8 byte aligned stack but MSA registers should be 16
byte aligned when spilled to memory.  I don't see anyway to do this unless
we can force the stack to be 16 byte aligned.

Richard Henderson created a way of aligning local variables with an
alignment greater than the maximum stack alignment by using alloca
and creating an aligned pointer in to that space but that doesn't help
when reload or LRA is spilling a register to memory.

My thought was to use alloca, not to create space, but to move the stack
pointer to an aligned address so that subsequent spills using the stack
pointer would be to aligned addresses.  As a test I created a simple gimple
pass that called __builtin_alloca at the beginning of each function just
to see if that was possible and it seemed to work fine.  This seemed to be
much cleaner than when I tried to modify the stack pointer in expand_prologue.
When I did it there I had issues with tests that use setjmp/longjmp and there
seems to be a lot of bookkeeping needed to track registers and offsets when
working at that level.  With this gimple pass that was all taken care of by
existing mechanisms.

Of course that test just did an alloca of 8 bytes, the actual code needs
to allocate a dynamic number of bytes depending on the current value of the
stack pointer.

	__builtin_alloca(stack_pointer MOD desired_alignment)

So my first question is: Is there way to access/refrence the stack pointer
in a gimple pass?  If so, how?

My second question is what do people think about this as a way to dymanically
align the stack?  It seems a lot simpler and more target independent than
what x86 is doing.

Steve Ellcey
sellcey@imgtec.com



A pass that inserts __builtin_alloca(8) at front of all routines:

unsigned int
pass_realign_stack::execute (function *fun)
{
  basic_block bb;
  gimple g;
  tree size;
  gimple_stmt_iterator gsi;
  bb = single_succ (ENTRY_BLOCK_PTR_FOR_FN (fun));
  gsi = gsi_start_bb (bb);
  size = build_int_cst (sizetype, 8);
  g = gimple_build_call (builtin_decl_explicit (BUILT_IN_ALLOCA), 1, size);
  gsi_insert_before (&gsi, g, GSI_NEW_STMT);
  return 0;
}



More information about the Gcc-patches mailing list