diff options
author | David Daney <ddaney@avtrex.com> | 2008-05-08 17:04:12 +0000 |
---|---|---|
committer | David Daney <daney@gcc.gnu.org> | 2008-05-08 17:04:12 +0000 |
commit | 977502ff8431f42bc84b71dd5814658439610c7b (patch) | |
tree | 53a03c6f31da3208a923be513b8bab95fd23f140 /gcc | |
parent | 627ab8616cc19a4bed7ca2d4273e3dc85aab39b4 (diff) | |
download | gcc-977502ff8431f42bc84b71dd5814658439610c7b.zip gcc-977502ff8431f42bc84b71dd5814658439610c7b.tar.gz gcc-977502ff8431f42bc84b71dd5814658439610c7b.tar.bz2 |
target-supports.exp (check_effective_target_sync_int_long): Add mips*-*-*.
2008-05-08 David Daney <ddaney@avtrex.com>
* lib/target-supports.exp (check_effective_target_sync_int_long): Add
mips*-*-*.
(check_effective_target_sync_char_short): Same.
2008-05-08 David Daney <ddaney@avtrex.com>
Richard Sandiford <rsandifo@nildram.co.uk>
* config/mips/mips.md (mips_expand_compare_and_swap_12): Handle
special case of constant zero operands.
* config/mips/mips.c (mips_expand_compare_and_swap_12): Zero extend
old and new values. Special case constant zero values.
* config/mips/mips.h (MIPS_COMPARE_AND_SWAP): Skip 'sync' if compare
fails.
(MIPS_COMPARE_AND_SWAP_12): Handle constant zero operands.
(MIPS_COMPARE_AND_SWAP_12_0): New macro.
Co-Authored-By: Richard Sandiford <rsandifo@nildram.co.uk>
From-SVN: r135088
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 12 | ||||
-rw-r--r-- | gcc/config/mips/mips.c | 32 | ||||
-rw-r--r-- | gcc/config/mips/mips.h | 19 | ||||
-rw-r--r-- | gcc/config/mips/mips.md | 19 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 6 | ||||
-rw-r--r-- | gcc/testsuite/lib/target-supports.exp | 6 |
6 files changed, 71 insertions, 23 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 7ac7cd2..ae8d7a9 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,15 @@ +2008-05-08 David Daney <ddaney@avtrex.com> + Richard Sandiford <rsandifo@nildram.co.uk> + + * config/mips/mips.md (mips_expand_compare_and_swap_12): Handle + special case of constant zero operands. + * config/mips/mips.c (mips_expand_compare_and_swap_12): Zero extend + old and new values. Special case constant zero values. + * config/mips/mips.h (MIPS_COMPARE_AND_SWAP): Skip 'sync' if compare + fails. + (MIPS_COMPARE_AND_SWAP_12): Handle constant zero operands. + (MIPS_COMPARE_AND_SWAP_12_0): New macro. + 2008-05-08 Paolo Bonzini <bonzini@gnu.org> PR target/36090 diff --git a/gcc/config/mips/mips.c b/gcc/config/mips/mips.c index de2e42a..2189533 100644 --- a/gcc/config/mips/mips.c +++ b/gcc/config/mips/mips.c @@ -5880,7 +5880,10 @@ void mips_expand_compare_and_swap_12 (rtx result, rtx mem, rtx oldval, rtx newval) { rtx orig_addr, memsi_addr, memsi, shift, shiftsi, unshifted_mask; - rtx mask, inverted_mask, oldvalsi, old_shifted, newvalsi, new_shifted, res; + rtx unshifted_mask_reg, mask, inverted_mask, res; + enum machine_mode mode; + + mode = GET_MODE (mem); /* Compute the address of the containing SImode value. */ orig_addr = force_reg (Pmode, XEXP (mem, 0)); @@ -5896,8 +5899,7 @@ mips_expand_compare_and_swap_12 (rtx result, rtx mem, rtx oldval, rtx newval) counting from the least significant byte. */ shift = mips_force_binary (Pmode, AND, orig_addr, GEN_INT (3)); if (TARGET_BIG_ENDIAN) - mips_emit_binary (XOR, shift, shift, - GEN_INT (GET_MODE (mem) == QImode ? 3 : 2)); + mips_emit_binary (XOR, shift, shift, GEN_INT (mode == QImode ? 3 : 2)); /* Multiply by eight to convert the shift value from bytes to bits. */ mips_emit_binary (ASHIFT, shift, shift, GEN_INT (3)); @@ -5907,9 +5909,9 @@ mips_expand_compare_and_swap_12 (rtx result, rtx mem, rtx oldval, rtx newval) shiftsi = force_reg (SImode, gen_lowpart (SImode, shift)); /* Set MASK to an inclusive mask of the QImode or HImode value. */ - unshifted_mask = GEN_INT (GET_MODE_MASK (GET_MODE (mem))); - unshifted_mask = force_reg (SImode, unshifted_mask); - mask = mips_force_binary (SImode, ASHIFT, unshifted_mask, shiftsi); + unshifted_mask = GEN_INT (GET_MODE_MASK (mode)); + unshifted_mask_reg = force_reg (SImode, unshifted_mask); + mask = mips_force_binary (SImode, ASHIFT, unshifted_mask_reg, shiftsi); /* Compute the equivalent exclusive mask. */ inverted_mask = gen_reg_rtx (SImode); @@ -5917,17 +5919,25 @@ mips_expand_compare_and_swap_12 (rtx result, rtx mem, rtx oldval, rtx newval) gen_rtx_NOT (SImode, mask))); /* Shift the old value into place. */ - oldvalsi = force_reg (SImode, gen_lowpart (SImode, oldval)); - old_shifted = mips_force_binary (SImode, ASHIFT, oldvalsi, shiftsi); + if (oldval != const0_rtx) + { + oldval = convert_modes (SImode, mode, oldval, true); + oldval = force_reg (SImode, oldval); + oldval = mips_force_binary (SImode, ASHIFT, oldval, shiftsi); + } /* Do the same for the new value. */ - newvalsi = force_reg (SImode, gen_lowpart (SImode, newval)); - new_shifted = mips_force_binary (SImode, ASHIFT, newvalsi, shiftsi); + if (newval != const0_rtx) + { + newval = convert_modes (SImode, mode, newval, true); + newval = force_reg (SImode, newval); + newval = mips_force_binary (SImode, ASHIFT, newval, shiftsi); + } /* Do the SImode atomic access. */ res = gen_reg_rtx (SImode); emit_insn (gen_compare_and_swap_12 (res, memsi, mask, inverted_mask, - old_shifted, new_shifted)); + oldval, newval)); /* Shift and convert the result. */ mips_emit_binary (AND, res, res, mask); diff --git a/gcc/config/mips/mips.h b/gcc/config/mips/mips.h index 1391c99..9f59f1a 100644 --- a/gcc/config/mips/mips.h +++ b/gcc/config/mips/mips.h @@ -2902,7 +2902,8 @@ while (0) "\tsc" SUFFIX "\t%@,%1\n" \ "\tbeq\t%@,%.,1b\n" \ "\tnop\n" \ - "2:\tsync%-%]%>%)" + "\tsync%-%]%>%)\n" \ + "2:\n" /* Return an asm string that atomically: @@ -2919,7 +2920,7 @@ while (0) "%(%<%[%|sync\n" \ "1:\tll\t%0,%1\n" \ "\tand\t%@,%0,%2\n" \ - "\tbne\t%@,%4,2f\n" \ + "\tbne\t%@,%z4,2f\n" \ "\tand\t%@,%0,%3\n" \ "\tor\t%@,%@,%5\n" \ "\tsc\t%@,%1\n" \ @@ -2928,6 +2929,20 @@ while (0) "\tsync%-%]%>%)\n" \ "2:\n" +/* Like MIPS_COMPARE_AND_SWAP_12, except %5 is a constant zero, + so the OR can be omitted. */ +#define MIPS_COMPARE_AND_SWAP_12_0 \ + "%(%<%[%|sync\n" \ + "1:\tll\t%0,%1\n" \ + "\tand\t%@,%0,%2\n" \ + "\tbne\t%@,%z4,2f\n" \ + "\tand\t%@,%0,%3\n" \ + "\tsc\t%@,%1\n" \ + "\tbeq\t%@,%.,1b\n" \ + "\tnop\n" \ + "\tsync%-%]%>%)\n" \ + "2:\n" + /* Return an asm string that atomically: - Sets memory reference %0 to %0 INSN %1. diff --git a/gcc/config/mips/mips.md b/gcc/config/mips/mips.md index 05adf22..a423529 100644 --- a/gcc/config/mips/mips.md +++ b/gcc/config/mips/mips.md @@ -4462,19 +4462,22 @@ ;; Helper insn for mips_expand_compare_and_swap_12. (define_insn "compare_and_swap_12" - [(set (match_operand:SI 0 "register_operand" "=&d") - (match_operand:SI 1 "memory_operand" "+R")) + [(set (match_operand:SI 0 "register_operand" "=&d,&d") + (match_operand:SI 1 "memory_operand" "+R,R")) (set (match_dup 1) - (unspec_volatile:SI [(match_operand:SI 2 "register_operand" "d") - (match_operand:SI 3 "register_operand" "d") - (match_operand:SI 4 "register_operand" "d") - (match_operand:SI 5 "register_operand" "d")] + (unspec_volatile:SI [(match_operand:SI 2 "register_operand" "d,d") + (match_operand:SI 3 "register_operand" "d,d") + (match_operand:SI 4 "reg_or_0_operand" "dJ,dJ") + (match_operand:SI 5 "reg_or_0_operand" "d,J")] UNSPEC_COMPARE_AND_SWAP_12))] "GENERATE_LL_SC" { - return MIPS_COMPARE_AND_SWAP_12; + if (which_alternative == 0) + return MIPS_COMPARE_AND_SWAP_12; + else + return MIPS_COMPARE_AND_SWAP_12_0; } - [(set_attr "length" "40")]) + [(set_attr "length" "40,36")]) (define_insn "sync_add<mode>" [(set (match_operand:GPR 0 "memory_operand" "+R,R") diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 3106bfb..ff5d2cc 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,9 @@ +2008-05-08 David Daney <ddaney@avtrex.com> + + * lib/target-supports.exp (check_effective_target_sync_int_long): Add + mips*-*-*. + (check_effective_target_sync_char_short): Same. + 2008-05-08 Kai Tietz <kai.tietz@onevision.com> * gcc.c-torture/compile/pr36172.c: Replace unsigned long by diff --git a/gcc/testsuite/lib/target-supports.exp b/gcc/testsuite/lib/target-supports.exp index de78c71..150a217 100644 --- a/gcc/testsuite/lib/target-supports.exp +++ b/gcc/testsuite/lib/target-supports.exp @@ -2052,7 +2052,8 @@ proc check_effective_target_sync_int_long { } { || [istarget s390*-*-*] || [istarget powerpc*-*-*] || [istarget sparc64-*-*] - || [istarget sparcv9-*-*] } { + || [istarget sparcv9-*-*] + || [istarget mips*-*-*] } { set et_sync_int_long_saved 1 } } @@ -2079,7 +2080,8 @@ proc check_effective_target_sync_char_short { } { || [istarget s390*-*-*] || [istarget powerpc*-*-*] || [istarget sparc64-*-*] - || [istarget sparcv9-*-*] } { + || [istarget sparcv9-*-*] + || [istarget mips*-*-*] } { set et_sync_char_short_saved 1 } } |