diff mbox

[PowerPC] Fix unaligned Altivec load/stores in LE mode

Message ID 1374635951.3633.132.camel@gnopaine
State New
Headers show

Commit Message

Bill Schmidt July 24, 2013, 3:19 a.m. UTC
In order to use vperm for aligning loads and stores in little endian
mode, we need to reverse the order of the input operands and use lvsl
instead of lvsr.  This corrects 32 regressions in the test suite when
run in LE mode.

Bootstrapped and tested on powerpc64-unknown-linux-gnu in BE mode with
no new regressions.  Is this ok for trunk?

Patch by Anton Blanchard.

Thanks,
Bill


2013-07-23  Bill Schmidt  <wschmidt@vnet.linux.ibm.com>
	    Anton Blanchard <anton@au1.ibm.com>

	* vector.md (vec_realign_load_<mode>): Reorder input operands to
	vperm for little endian.
	* rs6000.c (rs6000_expand_builtin): Use lvsr instead of lvsl to
	create the control mask for a vperm for little endian.

Comments

David Edelsohn July 24, 2013, 12:49 p.m. UTC | #1
On Tue, Jul 23, 2013 at 11:19 PM, Bill Schmidt
<wschmidt@linux.vnet.ibm.com> wrote:
> In order to use vperm for aligning loads and stores in little endian
> mode, we need to reverse the order of the input operands and use lvsl
> instead of lvsr.  This corrects 32 regressions in the test suite when
> run in LE mode.
>
> Bootstrapped and tested on powerpc64-unknown-linux-gnu in BE mode with
> no new regressions.  Is this ok for trunk?
>
> Patch by Anton Blanchard.
>
> Thanks,
> Bill
>
>
> 2013-07-23  Bill Schmidt  <wschmidt@vnet.linux.ibm.com>
>             Anton Blanchard <anton@au1.ibm.com>
>
>         * vector.md (vec_realign_load_<mode>): Reorder input operands to
>         vperm for little endian.
>         * rs6000.c (rs6000_expand_builtin): Use lvsr instead of lvsl to
>         create the control mask for a vperm for little endian.

Okay.

Thanks, David
diff mbox

Patch

Index: gcc/config/rs6000/vector.md
===================================================================
--- gcc/config/rs6000/vector.md	(revision 201194)
+++ gcc/config/rs6000/vector.md	(working copy)
@@ -936,8 +936,12 @@ 
    (match_operand:V16QI 3 "vlogical_operand" "")]
   "VECTOR_MEM_ALTIVEC_OR_VSX_P (<MODE>mode)"
 {
-  emit_insn (gen_altivec_vperm_<mode> (operands[0], operands[1], operands[2],
-				       operands[3]));
+  if (BYTES_BIG_ENDIAN)
+    emit_insn (gen_altivec_vperm_<mode> (operands[0], operands[1],
+    	      				 operands[2], operands[3]));
+  else
+    emit_insn (gen_altivec_vperm_<mode> (operands[0], operands[2],
+    	      				 operands[1], operands[3]));
   DONE;
 })
 
Index: gcc/config/rs6000/rs6000.c
===================================================================
--- gcc/config/rs6000/rs6000.c	(revision 201195)
+++ gcc/config/rs6000/rs6000.c	(working copy)
@@ -12351,7 +12351,8 @@  rs6000_expand_builtin (tree exp, rtx target, rtx s
     case ALTIVEC_BUILTIN_MASK_FOR_LOAD:
     case ALTIVEC_BUILTIN_MASK_FOR_STORE:
       {
-	int icode = (int) CODE_FOR_altivec_lvsr;
+	int icode = (BYTES_BIG_ENDIAN ? (int) CODE_FOR_altivec_lvsr
+		     : (int) CODE_FOR_altivec_lvsl);
 	enum machine_mode tmode = insn_data[icode].operand[0].mode;
 	enum machine_mode mode = insn_data[icode].operand[1].mode;
 	tree arg;