File nvl938159.patch of Package gcc43
2010-03-30 Andreas Krebbel <Andreas.Krebbel@de.ibm.com>
* config/s390/s390.c (s390_emit_prologue): Omit issuing a dynamic
stack check if the mask would be zero.
* gcc.target/s390/stackcheck1.c: New testcase.
Index: gcc/testsuite/gcc.target/s390/stackcheck1.c
===================================================================
--- gcc/testsuite/gcc.target/s390/stackcheck1.c (revision 0)
+++ gcc/testsuite/gcc.target/s390/stackcheck1.c (revision 157824)
@@ -0,0 +1,14 @@
+/* The automatically chosen stack guard value caused an ICE in that
+ case. */
+
+/* { dg-do compile } */
+/* { dg-options "-O2 -mstack-size=4096" } */
+
+extern void bar (char *);
+
+void
+foo ()
+{
+ char a[2500];
+ bar (a);
+}
Index: gcc/config/s390/s390.c
===================================================================
--- gcc/config/s390/s390.c (revision 157823)
+++ gcc/config/s390/s390.c (revision 157824)
@@ -7357,20 +7357,37 @@ s390_emit_prologue (void)
}
else
{
- HOST_WIDE_INT stack_check_mask = ((s390_stack_size - 1)
- & ~(stack_guard - 1));
- rtx t = gen_rtx_AND (Pmode, stack_pointer_rtx,
- GEN_INT (stack_check_mask));
- if (TARGET_64BIT)
- gen_cmpdi (t, const0_rtx);
- else
- gen_cmpsi (t, const0_rtx);
+ /* stack_guard has to be smaller than s390_stack_size.
+ Otherwise we would emit an AND with zero which would
+ not match the test under mask pattern. */
+ if (stack_guard >= s390_stack_size)
+ {
+ warning (0, "frame size of function %qs is "
+ HOST_WIDE_INT_PRINT_DEC
+ " bytes which is more than half the stack size. "
+ "The dynamic check would not be reliable. "
+ "No check emitted for this function.",
+ current_function_name(),
+ cfun_frame_layout.frame_size);
+ }
+ else
+ {
+ HOST_WIDE_INT stack_check_mask = ((s390_stack_size - 1)
+ & ~(stack_guard - 1));
+ rtx t = gen_rtx_AND (Pmode, stack_pointer_rtx,
+ GEN_INT (stack_check_mask));
+ if (TARGET_64BIT)
+ gen_cmpdi (t, const0_rtx);
+ else
+ gen_cmpsi (t, const0_rtx);
- emit_insn (gen_conditional_trap (gen_rtx_EQ (CCmode,
- gen_rtx_REG (CCmode,
- CC_REGNUM),
- const0_rtx),
- const0_rtx));
+ emit_insn (gen_conditional_trap (
+ gen_rtx_EQ (CCmode,
+ gen_rtx_REG (CCmode,
+ CC_REGNUM),
+ const0_rtx),
+ const0_rtx));
+ }
}
}