aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBernd Edlinger <bernd.edlinger@hotmail.de>2016-06-10 12:22:21 +0000
committerBernd Edlinger <edlinger@gcc.gnu.org>2016-06-10 12:22:21 +0000
commitad551c07abd4d9227fad658d14f1fc68340db16e (patch)
treec24ec76f9b0472cc2b7d345004684724061c3501
parentfcea0bbbacd4f2ef7007338b3ec6edf72e9ba6a7 (diff)
downloadgcc-ad551c07abd4d9227fad658d14f1fc68340db16e.zip
gcc-ad551c07abd4d9227fad658d14f1fc68340db16e.tar.gz
gcc-ad551c07abd4d9227fad658d14f1fc68340db16e.tar.bz2
re PR inline-asm/68843 (ICE with "u" input constraint)
gcc: 2016-06-10 Bernd Edlinger <bernd.edlinger@hotmail.de> PR inline-asm/68843 * reg-stack.c (check_asm_stack_operands): Explicit input arguments must be grouped on top of stack. Don't force early clobber on ordinary reg outputs. testsuite: 2016-06-10 Bernd Edlinger <bernd.edlinger@hotmail.de> PR inline-asm/68843 * gcc.target/i386/pr68843-1.c: New test. * gcc.target/i386/pr68843-2.c: New test. From-SVN: r237303
-rw-r--r--gcc/ChangeLog7
-rw-r--r--gcc/reg-stack.c26
-rw-r--r--gcc/testsuite/ChangeLog6
-rw-r--r--gcc/testsuite/gcc.target/i386/pr68843-1.c12
-rw-r--r--gcc/testsuite/gcc.target/i386/pr68843-2.c22
5 files changed, 72 insertions, 1 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 580dbed..d9852c5 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,10 @@
+2016-06-10 Bernd Edlinger <bernd.edlinger@hotmail.de>
+
+ PR inline-asm/68843
+ * reg-stack.c (check_asm_stack_operands): Explicit input arguments
+ must be grouped on top of stack. Don't force early clobber
+ on ordinary reg outputs.
+
2016-06-10 Richard Biener <rguenther@suse.de>
* targhooks.c (default_builtin_vectorization_cost): Adjust
diff --git a/gcc/reg-stack.c b/gcc/reg-stack.c
index 89a7a11..c931349 100644
--- a/gcc/reg-stack.c
+++ b/gcc/reg-stack.c
@@ -97,6 +97,9 @@
All implicitly popped input regs must be closer to the top of
the reg-stack than any input that is not implicitly popped.
+ All explicitly referenced input operands may not "skip" a reg.
+ Otherwise we can have holes in the stack.
+
3. It is possible that if an input dies in an insn, reload might
use the input reg for an output reload. Consider this example:
@@ -461,6 +464,7 @@ check_asm_stack_operands (rtx_insn *insn)
char reg_used_as_output[FIRST_PSEUDO_REGISTER];
char implicitly_dies[FIRST_PSEUDO_REGISTER];
+ char explicitly_used[FIRST_PSEUDO_REGISTER];
rtx *clobber_reg = 0;
int n_inputs, n_outputs;
@@ -568,6 +572,7 @@ check_asm_stack_operands (rtx_insn *insn)
popped. */
memset (implicitly_dies, 0, sizeof (implicitly_dies));
+ memset (explicitly_used, 0, sizeof (explicitly_used));
for (i = n_outputs; i < n_outputs + n_inputs; i++)
if (STACK_REG_P (recog_data.operand[i]))
{
@@ -581,6 +586,8 @@ check_asm_stack_operands (rtx_insn *insn)
if (j < n_clobbers || op_alt[i].matches >= 0)
implicitly_dies[REGNO (recog_data.operand[i])] = 1;
+ else if (reg_class_size[(int) op_alt[i].cl] == 1)
+ explicitly_used[REGNO (recog_data.operand[i])] = 1;
}
/* Search for first non-popped reg. */
@@ -600,6 +607,23 @@ check_asm_stack_operands (rtx_insn *insn)
malformed_asm = 1;
}
+ /* Search for first not-explicitly used reg. */
+ for (i = FIRST_STACK_REG; i < LAST_STACK_REG + 1; i++)
+ if (! implicitly_dies[i] && ! explicitly_used[i])
+ break;
+
+ /* If there are any other explicitly used regs, that's an error. */
+ for (; i < LAST_STACK_REG + 1; i++)
+ if (explicitly_used[i])
+ break;
+
+ if (i != LAST_STACK_REG + 1)
+ {
+ error_for_asm (insn,
+ "explicitly used regs must be grouped at top of stack");
+ malformed_asm = 1;
+ }
+
/* Enforce rule #3: If any input operand uses the "f" constraint, all
output constraints must use the "&" earlyclobber.
@@ -607,7 +631,7 @@ check_asm_stack_operands (rtx_insn *insn)
record any earlyclobber. */
for (i = n_outputs; i < n_outputs + n_inputs; i++)
- if (op_alt[i].matches == -1)
+ if (STACK_REG_P (recog_data.operand[i]) && op_alt[i].matches == -1)
{
int j;
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 325de75..07c6389 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,9 @@
+2016-06-10 Bernd Edlinger <bernd.edlinger@hotmail.de>
+
+ PR inline-asm/68843
+ * gcc.target/i386/pr68843-1.c: New test.
+ * gcc.target/i386/pr68843-2.c: New test.
+
2016-06-10 Thomas Schwinge <thomas@codesourcery.com>
Cesar Philippidis <cesar@codesourcery.com>
diff --git a/gcc/testsuite/gcc.target/i386/pr68843-1.c b/gcc/testsuite/gcc.target/i386/pr68843-1.c
new file mode 100644
index 0000000..da0676a
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/pr68843-1.c
@@ -0,0 +1,12 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+
+double
+test ()
+{
+ double x = 1.0;
+ asm ("fld %1" /* { dg-error "explicitly used regs must be grouped at top of stack" } */
+ : "=&t" (x)
+ : "u" (x));
+ return x;
+}
diff --git a/gcc/testsuite/gcc.target/i386/pr68843-2.c b/gcc/testsuite/gcc.target/i386/pr68843-2.c
new file mode 100644
index 0000000..652a5d3
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/pr68843-2.c
@@ -0,0 +1,22 @@
+int
+__attribute__((noinline, noclone))
+test (double y)
+{
+ int a, b;
+ asm ("fistpl (%1)\n\t"
+ "movl (%1), %0"
+ : "=r" (a)
+ : "r" (&b), "t" (y)
+ : "st");
+ return a;
+}
+
+int
+main ()
+{
+ int t = -10;
+
+ if (test (t) != t)
+ __builtin_abort ();
+ return 0;
+}