else
pretend_args_size = crtl->args.pretend_args_size;
+ if (FRAME_GROWS_DOWNWARD)
+ size = IA64_STACK_ALIGN (size);
+
total_size = (spill_size + extra_spill_size + size + pretend_args_size
+ crtl->outgoing_args_size);
total_size = IA64_STACK_ALIGN (total_size);
HOST_WIDE_INT
ia64_initial_elimination_offset (int from, int to)
{
- HOST_WIDE_INT offset;
+ HOST_WIDE_INT offset, size = get_frame_size ();
- ia64_compute_frame_size (get_frame_size ());
+ ia64_compute_frame_size (size);
switch (from)
{
case FRAME_POINTER_REGNUM:
default:
gcc_unreachable ();
}
+ offset += FRAME_GROWS_DOWNWARD ? IA64_STACK_ALIGN (size) : 0;
break;
case ARG_POINTER_REGNUM:
/* Define this macro to nonzero if the addresses of local variable slots
are at negative offsets from the frame pointer. */
-#define FRAME_GROWS_DOWNWARD 0
+#define FRAME_GROWS_DOWNWARD (flag_stack_protect != 0)
/* Offset from the frame pointer to the first local variable slot to
be allocated. */
[(set_attr "itanium_class" "unknown")
(set_attr "predicable" "no")])
+;;
+;; Stack guard expanders
+
+(define_expand "stack_protect_set"
+ [(set (match_operand 0 "memory_operand" "")
+ (match_operand 1 "memory_operand" ""))]
+ ""
+{
+#ifdef TARGET_THREAD_SSP_OFFSET
+ rtx thread_pointer_rtx = gen_rtx_REG (Pmode, 13);
+ rtx canary = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, thread_pointer_rtx,
+ GEN_INT (TARGET_THREAD_SSP_OFFSET)));
+ MEM_VOLATILE_P (canary) = MEM_VOLATILE_P (operands[1]);
+ operands[1] = canary;
+#endif
+ emit_move_insn (operands[0], operands[1]);
+ DONE;
+})
+
+(define_expand "stack_protect_test"
+ [(match_operand 0 "memory_operand" "")
+ (match_operand 1 "memory_operand" "")
+ (match_operand 2 "" "")]
+ ""
+{
+#ifdef TARGET_THREAD_SSP_OFFSET
+ rtx thread_pointer_rtx = gen_rtx_REG (Pmode, 13);
+ rtx canary = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, thread_pointer_rtx,
+ GEN_INT (TARGET_THREAD_SSP_OFFSET)));
+ MEM_VOLATILE_P (canary) = MEM_VOLATILE_P (operands[1]);
+ operands[1] = canary;
+#endif
+ emit_cmp_and_jump_insns (operands[0], operands[1], EQ, NULL_RTX,
+ ptr_mode, 1, operands[2]);
+ DONE;
+})
+
;; Vector operations
(include "vect.md")
;; Atomic operations
#undef LINK_EH_SPEC
#define LINK_EH_SPEC ""
+#ifdef TARGET_LIBC_PROVIDES_SSP
+/* IA-64 glibc provides __stack_chk_guard in [r13-8]. */
+#define TARGET_THREAD_SSP_OFFSET -8
+#endif
+
/* Put all *tf routines in libgcc. */
#undef LIBGCC2_HAS_TF_MODE
#define LIBGCC2_HAS_TF_MODE 1