aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorIan Lance Taylor <iant@google.com>2010-11-05 23:45:32 +0000
committerIan Lance Taylor <ian@gcc.gnu.org>2010-11-05 23:45:32 +0000
commitc3928dde21846d4572238317390613c8bcb042b6 (patch)
tree9f086d2faa96f90607a0c59d97ffe86a12e067f3 /gcc
parent037de943dc054e19f7387c56668fbb6375bee268 (diff)
downloadgcc-c3928dde21846d4572238317390613c8bcb042b6.zip
gcc-c3928dde21846d4572238317390613c8bcb042b6.tar.gz
gcc-c3928dde21846d4572238317390613c8bcb042b6.tar.bz2
re PR target/46084 (gcc.dg/split-4.c failed with -mavx -m32)
gcc/: PR target/46084 * explow.c (allocate_dynamic_stack_space): If flag_split_stack, request enough additional space for alignment, and force alignment. testsuite/: * gcc.target/i386/pr46084.c: New test. From-SVN: r166383
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog7
-rw-r--r--gcc/explow.c13
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/gcc.target/i386/pr46084.c69
4 files changed, 92 insertions, 2 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 1678d05..34b3601 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,10 @@
+2010-11-05 Ian Lance Taylor <iant@google.com>
+
+ PR target/46084
+ * explow.c (allocate_dynamic_stack_space): If flag_split_stack,
+ request enough additional space for alignment, and force
+ alignment.
+
2010-11-05 Kai Tietz <kai.tietz@onevision.com>
* config/i386/i386.c (legitimate_pic_address_disp_p):
diff --git a/gcc/explow.c b/gcc/explow.c
index a83c6e8..1d809bc 100644
--- a/gcc/explow.c
+++ b/gcc/explow.c
@@ -1340,7 +1340,7 @@ allocate_dynamic_stack_space (rtx size, unsigned size_align,
least it doesn't cause a stack overflow. */
if (flag_split_stack)
{
- rtx available_label, space, func;
+ rtx available_label, ask, space, func;
available_label = NULL_RTX;
@@ -1355,10 +1355,19 @@ allocate_dynamic_stack_space (rtx size, unsigned size_align,
}
#endif
+ /* The __morestack_allocate_stack_space function will allocate
+ memory using malloc. We don't know that the alignment of the
+ memory returned by malloc will meet REQUIRED_ALIGN. Increase
+ SIZE to make sure we allocate enough space. */
+ ask = expand_binop (Pmode, add_optab, size,
+ GEN_INT (required_align / BITS_PER_UNIT - 1),
+ NULL_RTX, 1, OPTAB_LIB_WIDEN);
+ must_align = true;
+
func = init_one_libfunc ("__morestack_allocate_stack_space");
space = emit_library_call_value (func, target, LCT_NORMAL, Pmode,
- 1, size, Pmode);
+ 1, ask, Pmode);
if (available_label == NULL_RTX)
return space;
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index bace48a..b2642c1 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2010-11-05 Ian Lance Taylor <iant@google.com>
+
+ PR target/46084
+ * gcc.target/i386/pr46084.c: New test.
+
2010-11-05 Steve Ellcey <sje@cup.hp.com>
* lib/target-supports.exp (check_function_available): Use -fno-builtin.
diff --git a/gcc/testsuite/gcc.target/i386/pr46084.c b/gcc/testsuite/gcc.target/i386/pr46084.c
new file mode 100644
index 0000000..88bcd1c
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/pr46084.c
@@ -0,0 +1,69 @@
+/* This test needs to use setrlimit to set the stack size, so it can
+ only run on Unix. */
+/* { dg-do run { target *-*-linux* *-*-solaris* *-*-darwin* } } */
+/* { dg-require-effective-target avx } */
+/* { dg-require-effective-target split_stack } */
+/* { dg-options "-fsplit-stack -O2 -mavx" } */
+
+#include <stdlib.h>
+#include <string.h>
+#include <sys/types.h>
+#include <sys/resource.h>
+
+/* Use a noinline function to ensure that the buffer is not removed
+ from the stack. */
+static void use_buffer (char *buf, size_t) __attribute__ ((noinline));
+static void
+use_buffer (char *buf, size_t c)
+{
+ size_t i;
+
+ for (i = 0; i < c; ++i)
+ buf[i] = (char) i;
+}
+
+/* Each recursive call uses 10 * i bytes. We call it 1000 times,
+ using a total of 5,000,000 bytes. If -fsplit-stack is not working,
+ that will overflow our stack limit. */
+
+static void
+down1 (int i)
+{
+ char buf[10 * i];
+
+ if (i > 0)
+ {
+ use_buffer (buf, 10 * i);
+ down1 (i - 1);
+ }
+}
+
+/* Same thing, using alloca. */
+
+static void
+down2 (int i)
+{
+ char *buf = alloca (10 * i);
+
+ if (i > 0)
+ {
+ use_buffer (buf, 10 * i);
+ down2 (i - 1);
+ }
+}
+
+int
+main (void)
+{
+ struct rlimit r;
+
+ /* We set a stack limit because we are usually invoked via make, and
+ make sets the stack limit to be as large as possible. */
+ r.rlim_cur = 8192 * 1024;
+ r.rlim_max = 8192 * 1024;
+ if (setrlimit (RLIMIT_STACK, &r) != 0)
+ abort ();
+ down1 (1000);
+ down2 (1000);
+ return 0;
+}