diff options
author | Bernd Edlinger <bernd.edlinger@hotmail.de> | 2016-06-10 12:22:21 +0000 |
---|---|---|
committer | Bernd Edlinger <edlinger@gcc.gnu.org> | 2016-06-10 12:22:21 +0000 |
commit | ad551c07abd4d9227fad658d14f1fc68340db16e (patch) | |
tree | c24ec76f9b0472cc2b7d345004684724061c3501 | |
parent | fcea0bbbacd4f2ef7007338b3ec6edf72e9ba6a7 (diff) | |
download | gcc-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/ChangeLog | 7 | ||||
-rw-r--r-- | gcc/reg-stack.c | 26 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 6 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/i386/pr68843-1.c | 12 | ||||
-rw-r--r-- | gcc/testsuite/gcc.target/i386/pr68843-2.c | 22 |
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; +} |