This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH][AArch64] Add BIC-imm and ORR-imm SIMD pattern



Hi James

I have made the requested changes to the patch.


2017-09-27 Sudakshina Das  <sudi.das@arm.com>

	* config/aarch64/aarch64-protos.h (enum simd_immediate_check): New check type
	for aarch64_simd_valid_immediate.
	(aarch64_output_simd_mov_immediate): Update prototype.
	(aarch64_simd_valid_immediate): Update prototype.

	* config/aarch64/aarch64-simd.md (orr<mode>3): modified pattern to add
	support for ORR-immediate.
	(and<mode>3): modified pattern to add support for BIC-immediate.

	* config/aarch64/aarch64.c (aarch64_simd_valid_immediate): Function now checks
	for valid immediate for BIC and ORR based on new enum argument.
	(aarch64_output_simd_mov_immediate): Function now used to output BIC/ORR imm
	as well based on new enum argument.
 
	* config/aarch64/constraints.md (Do): New vector immediate constraint.
	(Db): Likewise.

2017-09-27 Sudakshina Das  <sudi.das@arm.com>

	* gcc.target/aarch64/bic_imm_1.c: New test.
	* gcc.target/aarch64/orr_imm_1.c: Likewise.


Thanks
Sudi

  
From: James Greenhalgh <james.greenhalgh@arm.com>
Sent: Tuesday, September 26, 2017 8:04:38 PM
To: Sudi Das
Cc: Richard Earnshaw; gcc-patches@gcc.gnu.org; nd; Marcus Shawcroft
Subject: Re: [PATCH][AArch64] Add BIC-imm and ORR-imm SIMD pattern
    
On Mon, Sep 25, 2017 at 11:13:57AM +0100, Sudi Das wrote:
> 
> Hi James
> 
> I put aarch64_output_simd_general_immediate looking at the similarities of
> the immediates for mov/mvni and orr/bic. The CHECK macro in
> aarch64_simd_valid_immediate both checks
> and converts the immediates in a manner that are needed for the instructions.
> 
> Having said that, I agree that maybe I could have refactored
> aarch64_output_simd_mov_immediate to do the work rather than creating a new
> functions to do similar things. I have done so in this patch.

Thanks, this looks much neater.

> I have also changed the names of the enum simd_immediate_check to be better
> indicative of what they are doing. 

Thanks, I'd tweak them to look more like the bitmasks you use them as, but
that is a small change for my personal preference.

> Lastly I have added more cases in the tests (according to all the possible
> CHECKs) and made them dg-do assemble (although I had to add --save-temps so
> that the scan-assembler would work). Do you think I should not put that
> option and rather create separate tests?

This is good - thanks.

I think clean up the enum definitions and this patch will be good.

> @@ -308,6 +308,16 @@ enum aarch64_parse_opt_result
>    AARCH64_PARSE_INVALID_ARG          /* Invalid arch, tune, cpu arg.  */
>  };
>  
> +/* Enum to distinguish which type of check is to be done in
> +   aarch64_simd_valid_immediate.  This is used as a bitmask where
> +   AARCH64_CHECK_MOV has both bits set.  Thus AARCH64_CHECK_MOV will
> +   perform all checks.  Adding new types would require changes accordingly.  */
> +enum simd_immediate_check {
> +  AARCH64_CHECK_ORR  = 1,    /* Perform immediate checks for ORR.  */
> +  AARCH64_CHECK_BIC  = 2,    /* Perform immediate checks for BIC.  */
> +  AARCH64_CHECK_MOV  = 3     /* Perform all checks (used for MOVI/MNVI).  */

These are used in bit-mask style, so how about:

  AARCH64_CHECK_ORR = 1 << 0,
  AARCH64_CHECK_BIC = 1 << 1,
  AARCH64_CHECK_MOV = AARCH64_CHECK_ORR | AARCH64_CHECK_BIC

Which is more self-documenting.

> @@ -13001,7 +13013,8 @@ aarch64_float_const_representable_p (rtx x)
>  char*
>  aarch64_output_simd_mov_immediate (rtx const_vector,
>                                   machine_mode mode,
> -                                unsigned width)
> +                                unsigned width,
> +                                enum simd_immediate_check which)

This function is sorely missing a comment explaining the parameters - it
would be very helpful if you could add one as part of this patch.

Thanks,
James

    
diff --git a/gcc/config/aarch64/aarch64-protos.h b/gcc/config/aarch64/aarch64-protos.h
index e67c2ed..5d7c5df 100644
--- a/gcc/config/aarch64/aarch64-protos.h
+++ b/gcc/config/aarch64/aarch64-protos.h
@@ -308,6 +308,16 @@ enum aarch64_parse_opt_result
   AARCH64_PARSE_INVALID_ARG		/* Invalid arch, tune, cpu arg.  */
 };
 
+/* Enum to distinguish which type of check is to be done in
+   aarch64_simd_valid_immediate.  This is used as a bitmask where
+   AARCH64_CHECK_MOV has both bits set.  Thus AARCH64_CHECK_MOV will
+   perform all checks.  Adding new types would require changes accordingly.  */
+enum simd_immediate_check {
+  AARCH64_CHECK_ORR  = 1 << 0,
+  AARCH64_CHECK_BIC  = 1 << 1,
+  AARCH64_CHECK_MOV  = AARCH64_CHECK_ORR | AARCH64_CHECK_BIC
+};
+
 extern struct tune_params aarch64_tune_params;
 
 HOST_WIDE_INT aarch64_initial_elimination_offset (unsigned, unsigned);
@@ -345,7 +355,8 @@ bool aarch64_mov_operand_p (rtx, machine_mode);
 rtx aarch64_reverse_mask (machine_mode);
 bool aarch64_offset_7bit_signed_scaled_p (machine_mode, HOST_WIDE_INT);
 char *aarch64_output_scalar_simd_mov_immediate (rtx, scalar_int_mode);
-char *aarch64_output_simd_mov_immediate (rtx, machine_mode, unsigned);
+char *aarch64_output_simd_mov_immediate (rtx, machine_mode, unsigned,
+			enum simd_immediate_check w = AARCH64_CHECK_MOV);
 bool aarch64_pad_reg_upward (machine_mode, const_tree, bool);
 bool aarch64_regno_ok_for_base_p (int, bool);
 bool aarch64_regno_ok_for_index_p (int, bool);
@@ -356,7 +367,8 @@ bool aarch64_simd_imm_zero_p (rtx, machine_mode);
 bool aarch64_simd_scalar_immediate_valid_for_move (rtx, scalar_int_mode);
 bool aarch64_simd_shift_imm_p (rtx, machine_mode, bool);
 bool aarch64_simd_valid_immediate (rtx, machine_mode, bool,
-				   struct simd_immediate_info *);
+			struct simd_immediate_info *,
+			enum simd_immediate_check w = AARCH64_CHECK_MOV);
 bool aarch64_split_dimode_const_store (rtx, rtx);
 bool aarch64_symbolic_address_p (rtx);
 bool aarch64_uimm12_shift (HOST_WIDE_INT);
diff --git a/gcc/config/aarch64/aarch64-simd.md b/gcc/config/aarch64/aarch64-simd.md
index 70e9339..0a7e5e8 100644
--- a/gcc/config/aarch64/aarch64-simd.md
+++ b/gcc/config/aarch64/aarch64-simd.md
@@ -558,21 +558,45 @@
   [(set_attr "type" "neon_fp_abd_<stype><q>")]
 )
 
+;; For AND (vector, register) and BIC (vector, immediate)
 (define_insn "and<mode>3"
-  [(set (match_operand:VDQ_I 0 "register_operand" "=w")
-        (and:VDQ_I (match_operand:VDQ_I 1 "register_operand" "w")
-		 (match_operand:VDQ_I 2 "register_operand" "w")))]
+  [(set (match_operand:VDQ_I 0 "register_operand" "=w,w")
+	(and:VDQ_I (match_operand:VDQ_I 1 "register_operand" "w,0")
+		 (match_operand:VDQ_I 2 "nonmemory_operand" "w,Db")))]
   "TARGET_SIMD"
-  "and\t%0.<Vbtype>, %1.<Vbtype>, %2.<Vbtype>"
+  {
+    switch (which_alternative)
+      {
+      case 0:
+	return "and\t%0.<Vbtype>, %1.<Vbtype>, %2.<Vbtype>";
+      case 1:
+	return aarch64_output_simd_mov_immediate (operands[2],
+	   <MODE>mode, GET_MODE_BITSIZE (<MODE>mode), AARCH64_CHECK_BIC);
+      default:
+	gcc_unreachable ();
+      }
+  }
   [(set_attr "type" "neon_logic<q>")]
 )
 
+;; For ORR (vector, register) and ORR (vector, immediate)
 (define_insn "ior<mode>3"
-  [(set (match_operand:VDQ_I 0 "register_operand" "=w")
-        (ior:VDQ_I (match_operand:VDQ_I 1 "register_operand" "w")
-		 (match_operand:VDQ_I 2 "register_operand" "w")))]
+  [(set (match_operand:VDQ_I 0 "register_operand" "=w,w")
+	(ior:VDQ_I (match_operand:VDQ_I 1 "register_operand" "w,0")
+		 (match_operand:VDQ_I 2 "nonmemory_operand" "w,Do")))]
   "TARGET_SIMD"
-  "orr\t%0.<Vbtype>, %1.<Vbtype>, %2.<Vbtype>"
+  {
+    switch (which_alternative)
+      {
+      case 0:
+	return "orr\t%0.<Vbtype>, %1.<Vbtype>, %2.<Vbtype>";
+      case 1:
+	return aarch64_output_simd_mov_immediate (operands[2],
+		<MODE>mode, GET_MODE_BITSIZE (<MODE>mode), AARCH64_CHECK_ORR);
+      default:
+	gcc_unreachable ();
+      }
+  }
   [(set_attr "type" "neon_logic<q>")]
 )
 
diff --git a/gcc/config/aarch64/aarch64.c b/gcc/config/aarch64/aarch64.c
index 5e26cb7..6a6b3d5 100644
--- a/gcc/config/aarch64/aarch64.c
+++ b/gcc/config/aarch64/aarch64.c
@@ -11471,7 +11471,8 @@ aarch64_vect_float_const_representable_p (rtx x)
 /* Return true for valid and false for invalid.  */
 bool
 aarch64_simd_valid_immediate (rtx op, machine_mode mode, bool inverse,
-			      struct simd_immediate_info *info)
+			      struct simd_immediate_info *info,
+			      enum simd_immediate_check which)
 {
 #define CHECK(STRIDE, ELSIZE, CLASS, TEST, SHIFT, NEG)	\
   matches = 1;						\
@@ -11539,54 +11540,65 @@ aarch64_simd_valid_immediate (rtx op, machine_mode mode, bool inverse,
 
   do
     {
-      CHECK (4, 32, 0, bytes[i] == bytes[0] && bytes[i + 1] == 0
-	     && bytes[i + 2] == 0 && bytes[i + 3] == 0, 0, 0);
+      if (which & AARCH64_CHECK_ORR)
+	{
+	  CHECK (4, 32, 0, bytes[i] == bytes[0] && bytes[i + 1] == 0
+		 && bytes[i + 2] == 0 && bytes[i + 3] == 0, 0, 0);
 
-      CHECK (4, 32, 1, bytes[i] == 0 && bytes[i + 1] == bytes[1]
-	     && bytes[i + 2] == 0 && bytes[i + 3] == 0, 8, 0);
+	  CHECK (4, 32, 1, bytes[i] == 0 && bytes[i + 1] == bytes[1]
+		 && bytes[i + 2] == 0 && bytes[i + 3] == 0, 8, 0);
 
-      CHECK (4, 32, 2, bytes[i] == 0 && bytes[i + 1] == 0
-	     && bytes[i + 2] == bytes[2] && bytes[i + 3] == 0, 16, 0);
+	  CHECK (4, 32, 2, bytes[i] == 0 && bytes[i + 1] == 0
+		 && bytes[i + 2] == bytes[2] && bytes[i + 3] == 0, 16, 0);
 
-      CHECK (4, 32, 3, bytes[i] == 0 && bytes[i + 1] == 0
-	     && bytes[i + 2] == 0 && bytes[i + 3] == bytes[3], 24, 0);
+	  CHECK (4, 32, 3, bytes[i] == 0 && bytes[i + 1] == 0
+		 && bytes[i + 2] == 0 && bytes[i + 3] == bytes[3], 24, 0);
 
-      CHECK (2, 16, 4, bytes[i] == bytes[0] && bytes[i + 1] == 0, 0, 0);
+	  CHECK (2, 16, 4, bytes[i] == bytes[0] && bytes[i + 1] == 0, 0, 0);
 
-      CHECK (2, 16, 5, bytes[i] == 0 && bytes[i + 1] == bytes[1], 8, 0);
+	  CHECK (2, 16, 5, bytes[i] == 0 && bytes[i + 1] == bytes[1], 8, 0);
+	}
 
-      CHECK (4, 32, 6, bytes[i] == bytes[0] && bytes[i + 1] == 0xff
-	     && bytes[i + 2] == 0xff && bytes[i + 3] == 0xff, 0, 1);
+      if (which & AARCH64_CHECK_BIC)
+	{
+	  CHECK (4, 32, 6, bytes[i] == bytes[0] && bytes[i + 1] == 0xff
+		 && bytes[i + 2] == 0xff && bytes[i + 3] == 0xff, 0, 1);
 
-      CHECK (4, 32, 7, bytes[i] == 0xff && bytes[i + 1] == bytes[1]
-	     && bytes[i + 2] == 0xff && bytes[i + 3] == 0xff, 8, 1);
+	  CHECK (4, 32, 7, bytes[i] == 0xff && bytes[i + 1] == bytes[1]
+		 && bytes[i + 2] == 0xff && bytes[i + 3] == 0xff, 8, 1);
 
-      CHECK (4, 32, 8, bytes[i] == 0xff && bytes[i + 1] == 0xff
-	     && bytes[i + 2] == bytes[2] && bytes[i + 3] == 0xff, 16, 1);
+	  CHECK (4, 32, 8, bytes[i] == 0xff && bytes[i + 1] == 0xff
+		 && bytes[i + 2] == bytes[2] && bytes[i + 3] == 0xff, 16, 1);
 
-      CHECK (4, 32, 9, bytes[i] == 0xff && bytes[i + 1] == 0xff
-	     && bytes[i + 2] == 0xff && bytes[i + 3] == bytes[3], 24, 1);
+	  CHECK (4, 32, 9, bytes[i] == 0xff && bytes[i + 1] == 0xff
+		 && bytes[i + 2] == 0xff && bytes[i + 3] == bytes[3], 24, 1);
 
-      CHECK (2, 16, 10, bytes[i] == bytes[0] && bytes[i + 1] == 0xff, 0, 1);
+	  CHECK (2, 16, 10, bytes[i] == bytes[0] && bytes[i + 1] == 0xff, 0, 1);
 
-      CHECK (2, 16, 11, bytes[i] == 0xff && bytes[i + 1] == bytes[1], 8, 1);
+	  CHECK (2, 16, 11, bytes[i] == 0xff && bytes[i + 1] == bytes[1], 8, 1);
+	}
 
-      CHECK (4, 32, 12, bytes[i] == 0xff && bytes[i + 1] == bytes[1]
-	     && bytes[i + 2] == 0 && bytes[i + 3] == 0, 8, 0);
+      /* Shifting ones / 8-bit / 64-bit variants only checked
+	 for 'ALL' (MOVI/MVNI).  */
+      if (which == AARCH64_CHECK_MOV)
+	{
+	  CHECK (4, 32, 12, bytes[i] == 0xff && bytes[i + 1] == bytes[1]
+		 && bytes[i + 2] == 0 && bytes[i + 3] == 0, 8, 0);
 
-      CHECK (4, 32, 13, bytes[i] == 0 && bytes[i + 1] == bytes[1]
-	     && bytes[i + 2] == 0xff && bytes[i + 3] == 0xff, 8, 1);
+	  CHECK (4, 32, 13, bytes[i] == 0 && bytes[i + 1] == bytes[1]
+		 && bytes[i + 2] == 0xff && bytes[i + 3] == 0xff, 8, 1);
 
-      CHECK (4, 32, 14, bytes[i] == 0xff && bytes[i + 1] == 0xff
-	     && bytes[i + 2] == bytes[2] && bytes[i + 3] == 0, 16, 0);
+	  CHECK (4, 32, 14, bytes[i] == 0xff && bytes[i + 1] == 0xff
+		 && bytes[i + 2] == bytes[2] && bytes[i + 3] == 0, 16, 0);
 
-      CHECK (4, 32, 15, bytes[i] == 0 && bytes[i + 1] == 0
-	     && bytes[i + 2] == bytes[2] && bytes[i + 3] == 0xff, 16, 1);
+	  CHECK (4, 32, 15, bytes[i] == 0 && bytes[i + 1] == 0
+		 && bytes[i + 2] == bytes[2] && bytes[i + 3] == 0xff, 16, 1);
 
-      CHECK (1, 8, 16, bytes[i] == bytes[0], 0, 0);
+	  CHECK (1, 8, 16, bytes[i] == bytes[0], 0, 0);
 
-      CHECK (1, 64, 17, (bytes[i] == 0 || bytes[i] == 0xff)
-	     && bytes[i] == bytes[(i + 8) % idx], 0, 0);
+	  CHECK (1, 64, 17, (bytes[i] == 0 || bytes[i] == 0xff)
+		 && bytes[i] == bytes[(i + 8) % idx], 0, 0);
+	}
     }
   while (0);
 
@@ -12998,10 +13010,14 @@ aarch64_float_const_representable_p (rtx x)
   return (exponent >= 0 && exponent <= 7);
 }
 
+/* Returns the string with the instruction for AdvSIMD MOVI, MVNI, ORR or BIC
+   immediate with a CONST_VECTOR of MODE and WIDTH.  WHICH selects whether to
+   output MOVI/MVNI, ORR or BIC immediate.  */
 char*
 aarch64_output_simd_mov_immediate (rtx const_vector,
 				   machine_mode mode,
-				   unsigned width)
+				   unsigned width,
+				   enum simd_immediate_check which)
 {
   bool is_valid;
   static char templ[40];
@@ -13013,9 +13029,11 @@ aarch64_output_simd_mov_immediate (rtx const_vector,
   struct simd_immediate_info info = { NULL_RTX, 0, 0, false, false };
 
   /* This will return true to show const_vector is legal for use as either
-     a AdvSIMD MOVI instruction (or, implicitly, MVNI) immediate.  It will
-     also update INFO to show how the immediate should be generated.  */
-  is_valid = aarch64_simd_valid_immediate (const_vector, mode, false, &info);
+     a AdvSIMD MOVI instruction (or, implicitly, MVNI), ORR or BIC immediate.
+     It will also update INFO to show how the immediate should be generated.
+     WHICH selects whether to check for MOVI/MVNI, ORR or BIC.  */
+  is_valid = aarch64_simd_valid_immediate (const_vector, mode, false,
+					   &info, which);
   gcc_assert (is_valid);
 
   element_char = sizetochar (info.element_width);
@@ -13046,20 +13064,37 @@ aarch64_output_simd_mov_immediate (rtx const_vector,
 	}
     }
 
-  mnemonic = info.mvn ? "mvni" : "movi";
-  shift_op = info.msl ? "msl" : "lsl";
-
   gcc_assert (CONST_INT_P (info.value));
-  if (lane_count == 1)
-    snprintf (templ, sizeof (templ), "%s\t%%d0, " HOST_WIDE_INT_PRINT_HEX,
-	      mnemonic, UINTVAL (info.value));
-  else if (info.shift)
-    snprintf (templ, sizeof (templ), "%s\t%%0.%d%c, " HOST_WIDE_INT_PRINT_HEX
-	      ", %s %d", mnemonic, lane_count, element_char,
-	      UINTVAL (info.value), shift_op, info.shift);
+
+  if (which == AARCH64_CHECK_MOV)
+    {
+      mnemonic = info.mvn ? "mvni" : "movi";
+      shift_op = info.msl ? "msl" : "lsl";
+      if (lane_count == 1)
+	snprintf (templ, sizeof (templ), "%s\t%%d0, " HOST_WIDE_INT_PRINT_HEX,
+		  mnemonic, UINTVAL (info.value));
+      else if (info.shift)
+	snprintf (templ, sizeof (templ), "%s\t%%0.%d%c, "
+		  HOST_WIDE_INT_PRINT_HEX ", %s %d", mnemonic, lane_count,
+		  element_char, UINTVAL (info.value), shift_op, info.shift);
+      else
+	snprintf (templ, sizeof (templ), "%s\t%%0.%d%c, "
+		  HOST_WIDE_INT_PRINT_HEX, mnemonic, lane_count,
+		  element_char, UINTVAL (info.value));
+    }
   else
-    snprintf (templ, sizeof (templ), "%s\t%%0.%d%c, " HOST_WIDE_INT_PRINT_HEX,
-	      mnemonic, lane_count, element_char, UINTVAL (info.value));
+    {
+      /* For AARCH64_CHECK_BIC and AARCH64_CHECK_ORR.  */
+      mnemonic = info.mvn ? "bic" : "orr";
+      if (info.shift)
+	snprintf (templ, sizeof (templ), "%s\t%%0.%d%c, #"
+		  HOST_WIDE_INT_PRINT_DEC ", %s #%d", mnemonic, lane_count,
+		  element_char, UINTVAL (info.value), "lsl", info.shift);
+      else
+	snprintf (templ, sizeof (templ), "%s\t%%0.%d%c, #"
+		  HOST_WIDE_INT_PRINT_DEC, mnemonic, lane_count,
+		  element_char, UINTVAL (info.value));
+    }
   return templ;
 }
 
diff --git a/gcc/config/aarch64/constraints.md b/gcc/config/aarch64/constraints.md
index 3649fb4..77c510c 100644
--- a/gcc/config/aarch64/constraints.md
+++ b/gcc/config/aarch64/constraints.md
@@ -190,6 +190,20 @@
   (and (match_code "const_double")
        (match_test "aarch64_can_const_movi_rtx_p (op, GET_MODE (op))")))
 
+(define_constraint "Do"
+  "@internal
+   A constraint that matches vector of immediates for orr."
+ (and (match_code "const_vector")
+      (match_test "aarch64_simd_valid_immediate (op, mode, false,
+						 NULL, AARCH64_CHECK_ORR)")))
+
+(define_constraint "Db"
+  "@internal
+   A constraint that matches vector of immediates for bic."
+ (and (match_code "const_vector")
+      (match_test "aarch64_simd_valid_immediate (op, mode, false,
+						 NULL, AARCH64_CHECK_BIC)")))
+
 (define_constraint "Dn"
   "@internal
  A constraint that matches vector of immediates."
diff --git a/gcc/testsuite/gcc.target/aarch64/bic_imm_1.c b/gcc/testsuite/gcc.target/aarch64/bic_imm_1.c
new file mode 100644
index 0000000..b14f009
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/bic_imm_1.c
@@ -0,0 +1,56 @@
+/* { dg-do assemble } */
+/* { dg-options "-O2 --save-temps -ftree-vectorize" } */
+
+/* Each function uses the correspoding 'CLASS' in
+   Marco CHECK (aarch64_simd_valid_immediate).  */
+
+void
+bic_6 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] &= ~(0xab);
+}
+
+void
+bic_7 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] &= ~(0xcd00);
+}
+
+void
+bic_8 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] &= ~(0xef0000);
+}
+
+void
+bic_9 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] &= ~(0x12000000);
+}
+
+void
+bic_10 (short *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] &= ~(0x34);
+}
+
+
+void
+bic_11 (short *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] &= ~(0x5600);
+}
+
+
+/* { dg-final { scan-assembler "bic\\tv\[0-9\]+.4s, #171" } } */
+/* { dg-final { scan-assembler "bic\\tv\[0-9\]+.4s, #205, lsl #8" } } */
+/* { dg-final { scan-assembler "bic\\tv\[0-9\]+.4s, #239, lsl #16" } } */
+/* { dg-final { scan-assembler "bic\\tv\[0-9\]+.4s, #18, lsl #24" } } */
+/* { dg-final { scan-assembler "bic\\tv\[0-9\]+.8h, #52" } } */
+/* { dg-final { scan-assembler "bic\\tv\[0-9\]+.8h, #86, lsl #8" } } */
diff --git a/gcc/testsuite/gcc.target/aarch64/orr_imm_1.c b/gcc/testsuite/gcc.target/aarch64/orr_imm_1.c
new file mode 100644
index 0000000..ff6f683
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/orr_imm_1.c
@@ -0,0 +1,54 @@
+/* { dg-do assemble } */
+/* { dg-options "-O2 --save-temps -ftree-vectorize" } */
+
+/* Each function uses the correspoding 'CLASS' in
+   Marco CHECK (aarch64_simd_valid_immediate).  */
+
+void
+orr_0 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] |= 0xab;
+}
+
+void
+orr_1 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] |= 0x0000cd00;
+}
+
+void
+orr_2 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] |= 0x00ef0000;
+}
+
+void
+orr_3 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] |= 0x12000000;
+}
+
+void
+orr_4 (short *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] |= 0x00340034;
+}
+
+void
+orr_5 (int *a)
+{
+  for (int i = 0; i < 1024; i++)
+    a[i] |= 0x56005600;
+}
+
+/* { dg-final { scan-assembler "orr\\tv\[0-9\]+.4s, #171" } } */
+/* { dg-final { scan-assembler "orr\\tv\[0-9\]+.4s, #205, lsl #8" } } */
+/* { dg-final { scan-assembler "orr\\tv\[0-9\]+.4s, #239, lsl #16" } } */
+/* { dg-final { scan-assembler "orr\\tv\[0-9\]+.4s, #18, lsl #24" } } */
+/* { dg-final { scan-assembler "orr\\tv\[0-9\]+.8h, #52" } } */
+/* { dg-final { scan-assembler "orr\\tv\[0-9\]+.8h, #86, lsl #8" } } */

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]