public inbox for gcc-patches@gcc.gnu.org
 help / color / mirror / Atom feed
From: Claudiu Zissulescu <claziss@gmail.com>
To: gcc-patches@gcc.gnu.org
Cc: andrew.burgess@embecosm.com,	fbedard@synopsys.com,	claziss@synopsys.com
Subject: [PATCH 3/6] [ARC] Add BI/BIH instruction support.
Date: Wed, 10 Oct 2018 08:49:00 -0000	[thread overview]
Message-ID: <20181010080016.12317-4-claziss@gmail.com> (raw)
In-Reply-To: <20181010080016.12317-1-claziss@gmail.com>

Use BI/BIH instruction to implement casesi pattern. Only ARC V2.

gcc/
2018-03-21  Claudiu Zissulescu  <claziss@synopsys.com>

	* config/arc/arc.c (arc_override_options): Remove
	TARGET_COMPACT_CASESI.
	* config/arc/arc.h (ASM_OUTPUT_ADDR_DIFF_ELT): Update.
	(CASE_VECTOR_MODE): Likewise.
	(CASE_VECTOR_PC_RELATIVE): Likewise.
	(CASE_VECTOR_SHORTEN_MODE): Likewise.
	(CASE_VECTOR_SHORTEN_MODE1): Delete.
	(ADDR_VEC_ALIGN): Update.
	(ASM_OUTPUT_CASE_LABEL): Undefine.
	(ASM_OUTPUT_BEFORE_CASE_LABEL): Undefine.
	(TARGET_BI_BIH): Define.
	(DEFAULT_BRANCH_INDEX): Likewise.
	* config/arc/arc.md (casesi): Rework to accept BI/BIH
	instructions, remove compact_casesi use case.
	(casesi_compact_jump): Remove.
	(casesi_dispatch): New pattern.
	* config/arc/arc.opt: Add mbranch-index option. Deprecate
	compact_casesi option.
	* doc/invoke.texi: Document mbranch-index option.

gcc/testsuite
Claudiu Zissulescu  <claziss@synopsys.com>

	* gcc.target/arc/jumptable.c: New test.
---
 gcc/config/arc/arc.c                     |  19 --
 gcc/config/arc/arc.h                     | 106 ++++++-----
 gcc/config/arc/arc.md                    | 218 +++++++----------------
 gcc/config/arc/arc.opt                   |   6 +-
 gcc/doc/invoke.texi                      |   9 +-
 gcc/testsuite/gcc.target/arc/jumptable.c |  34 ++++
 6 files changed, 171 insertions(+), 221 deletions(-)
 create mode 100644 gcc/testsuite/gcc.target/arc/jumptable.c

diff --git a/gcc/config/arc/arc.c b/gcc/config/arc/arc.c
index 56f566795ff..18dd0de6af7 100644
--- a/gcc/config/arc/arc.c
+++ b/gcc/config/arc/arc.c
@@ -1291,33 +1291,14 @@ arc_override_options (void)
   if (arc_size_opt_level == 3)
     optimize_size = 1;
 
-  /* Compact casesi is not a valid option for ARCv2 family.  */
-  if (TARGET_V2)
-    {
-      if (TARGET_COMPACT_CASESI)
-	{
-	  warning (OPT_mcompact_casesi,
-		   "compact-casesi is not applicable to ARCv2");
-	  TARGET_COMPACT_CASESI = 0;
-	}
-    }
-  else if (optimize_size == 1
-	   && !global_options_set.x_TARGET_COMPACT_CASESI)
-    TARGET_COMPACT_CASESI = 1;
-
   if (flag_pic)
     target_flags |= MASK_NO_SDATA_SET;
 
   if (flag_no_common == 255)
     flag_no_common = !TARGET_NO_SDATA_SET;
 
-  /* TARGET_COMPACT_CASESI needs the "q" register class.  */
   if (TARGET_MIXED_CODE)
     TARGET_Q_CLASS = 1;
-  if (!TARGET_Q_CLASS)
-    TARGET_COMPACT_CASESI = 0;
-  if (TARGET_COMPACT_CASESI)
-    TARGET_CASE_VECTOR_PC_RELATIVE = 1;
 
   /* Check for small data option */
   if (!global_options_set.x_g_switch_value && !TARGET_NO_SDATA_SET)
diff --git a/gcc/config/arc/arc.h b/gcc/config/arc/arc.h
index dd78a6bbbd1..cb48b85d6e7 100644
--- a/gcc/config/arc/arc.h
+++ b/gcc/config/arc/arc.h
@@ -1264,25 +1264,39 @@ do {							\
 } while (0)
 
 /* This is how to output an element of a case-vector that is relative.  */
-#define ASM_OUTPUT_ADDR_DIFF_ELT(FILE, BODY, VALUE, REL) \
-do {							\
-  char label[30];					\
-  ASM_GENERATE_INTERNAL_LABEL (label, "L", VALUE);	\
-  switch (GET_MODE (BODY))				\
-    {							\
-    case E_QImode: fprintf (FILE, "\t.byte "); break;	\
-    case E_HImode: fprintf (FILE, "\t.hword "); break;	\
-    case E_SImode: fprintf (FILE, "\t.word "); break;	\
-    default: gcc_unreachable ();			\
-    }							\
-  assemble_name (FILE, label);				\
-  fprintf (FILE, "-");					\
-  ASM_GENERATE_INTERNAL_LABEL (label, "L", REL);	\
-  assemble_name (FILE, label);				\
-  if (TARGET_COMPACT_CASESI)				\
-    fprintf (FILE, " + %d", 4 + arc_get_unalign ());	\
-  fprintf(FILE, "\n");                                  \
-} while (0)
+#define ASM_OUTPUT_ADDR_DIFF_ELT(FILE, BODY, VALUE, REL)	\
+  do {								\
+    char label[30];						\
+    ASM_GENERATE_INTERNAL_LABEL (label, "L", VALUE);		\
+    if (!TARGET_BI_BIH)						\
+      {								\
+	switch (GET_MODE (BODY))				\
+	  {							\
+	  case E_QImode: fprintf (FILE, "\t.byte "); break;	\
+	  case E_HImode: fprintf (FILE, "\t.hword "); break;	\
+	  case E_SImode: fprintf (FILE, "\t.word "); break;	\
+	  default: gcc_unreachable ();				\
+	  }							\
+	assemble_name (FILE, label);				\
+	fprintf (FILE, "-");					\
+	ASM_GENERATE_INTERNAL_LABEL (label, "L", REL);		\
+	assemble_name (FILE, label);				\
+	fprintf(FILE, "\n");					\
+      } else {							\
+      switch (GET_MODE (BODY))					\
+	{							\
+	case E_SImode: fprintf (FILE, "\tb\t@"); break;		\
+	case E_HImode:						\
+	case E_QImode: fprintf (FILE, "\tb_s\t@"); break;	\
+	default: gcc_unreachable ();				\
+	}							\
+      assemble_name (FILE, label);				\
+      fprintf(FILE, "\n");					\
+    }								\
+  } while (0)
+
+/* Defined to also emit an .align in elfos.h.  We don't want that.  */
+#undef ASM_OUTPUT_CASE_LABEL
 
 /* ADDR_DIFF_VECs are in the text section and thus can affect the
    current alignment.  */
@@ -1380,36 +1394,34 @@ do { \
    for the index in the tablejump instruction.
    If we have pc relative case vectors, we start the case vector shortening
    with QImode.  */
-#define CASE_VECTOR_MODE \
-  ((optimize && (CASE_VECTOR_PC_RELATIVE || flag_pic)) ? QImode : Pmode)
+#define CASE_VECTOR_MODE						\
+  (TARGET_BI_BIH ? SImode						\
+   : (optimize && (CASE_VECTOR_PC_RELATIVE || flag_pic)) ? QImode : Pmode)
 
 /* Define as C expression which evaluates to nonzero if the tablejump
    instruction expects the table to contain offsets from the address of the
    table.
    Do not define this if the table should contain absolute addresses.  */
-#define CASE_VECTOR_PC_RELATIVE TARGET_CASE_VECTOR_PC_RELATIVE
-
-#define CASE_VECTOR_SHORTEN_MODE(MIN_OFFSET, MAX_OFFSET, BODY) \
-  CASE_VECTOR_SHORTEN_MODE_1 \
-    (MIN_OFFSET, TARGET_COMPACT_CASESI ? MAX_OFFSET + 6 : MAX_OFFSET, BODY)
-
-#define CASE_VECTOR_SHORTEN_MODE_1(MIN_OFFSET, MAX_OFFSET, BODY) \
-((MIN_OFFSET) >= 0 && (MAX_OFFSET) <= 255 \
- ? (ADDR_DIFF_VEC_FLAGS (BODY).offset_unsigned = 1, QImode) \
- : (MIN_OFFSET) >= -128 && (MAX_OFFSET) <= 127 \
- ? (ADDR_DIFF_VEC_FLAGS (BODY).offset_unsigned = 0, QImode) \
- : (MIN_OFFSET) >= 0 && (MAX_OFFSET) <= 65535 \
- ? (ADDR_DIFF_VEC_FLAGS (BODY).offset_unsigned = 1, HImode) \
- : (MIN_OFFSET) >= -32768 && (MAX_OFFSET) <= 32767 \
- ? (ADDR_DIFF_VEC_FLAGS (BODY).offset_unsigned = 0, HImode) \
- : SImode)
-
-#define ADDR_VEC_ALIGN(VEC_INSN) \
-  (exact_log2 (GET_MODE_SIZE (as_a <scalar_int_mode> \
-			      (GET_MODE (PATTERN (VEC_INSN))))))
-#undef ASM_OUTPUT_BEFORE_CASE_LABEL
-#define ASM_OUTPUT_BEFORE_CASE_LABEL(FILE, PREFIX, NUM, TABLE) \
-  ASM_OUTPUT_ALIGN ((FILE), ADDR_VEC_ALIGN (TABLE))
+#define CASE_VECTOR_PC_RELATIVE					\
+  (TARGET_CASE_VECTOR_PC_RELATIVE || TARGET_BI_BIH)
+
+#define CASE_VECTOR_SHORTEN_MODE(MIN_OFFSET, MAX_OFFSET, BODY)		\
+  (TARGET_BI_BIH ?						\
+   ((MIN_OFFSET) >= -512 && (MAX_OFFSET) <= 508 ? HImode : SImode)	\
+   : ((MIN_OFFSET) >= 0 && (MAX_OFFSET) <= 255				\
+      ? (ADDR_DIFF_VEC_FLAGS (BODY).offset_unsigned = 1, QImode)	\
+      : (MIN_OFFSET) >= -128 && (MAX_OFFSET) <= 127			\
+      ? (ADDR_DIFF_VEC_FLAGS (BODY).offset_unsigned = 0, QImode)	\
+      : (MIN_OFFSET) >= 0 && (MAX_OFFSET) <= 65535			\
+      ? (ADDR_DIFF_VEC_FLAGS (BODY).offset_unsigned = 1, HImode)	\
+      : (MIN_OFFSET) >= -32768 && (MAX_OFFSET) <= 32767			\
+      ? (ADDR_DIFF_VEC_FLAGS (BODY).offset_unsigned = 0, HImode)	\
+      : SImode))
+
+#define ADDR_VEC_ALIGN(VEC_INSN)					\
+  (TARGET_BI_BIH ? 0							\
+   : exact_log2 (GET_MODE_SIZE (as_a <scalar_int_mode>			\
+				(GET_MODE (PATTERN (VEC_INSN))))))
 
 #define INSN_LENGTH_ALIGNMENT(INSN)		  \
   ((JUMP_TABLE_DATA_P (INSN)			  \
@@ -1636,4 +1648,10 @@ enum
 #define TARGET_LRA arc_lra_p()
 #endif
 
+/* BI/BIH feature macro.  */
+#define TARGET_BI_BIH (TARGET_BRANCH_INDEX && TARGET_CODE_DENSITY)
+
+/* The default option for BI/BIH instructions.  */
+#define DEFAULT_BRANCH_INDEX 0
+
 #endif /* GCC_ARC_H */
diff --git a/gcc/config/arc/arc.md b/gcc/config/arc/arc.md
index 6ea67791627..1ed230fa5f0 100644
--- a/gcc/config/arc/arc.md
+++ b/gcc/config/arc/arc.md
@@ -3968,60 +3968,72 @@ archs4x, archs4xd, archs4xd_slow"
    (set_attr "cond" "canuse,canuse_limm,canuse,canuse,canuse")])
 
 ;; Implement a switch statement.
-
 (define_expand "casesi"
-  [(set (match_dup 5)
-	(minus:SI (match_operand:SI 0 "register_operand" "")
-		  (match_operand:SI 1 "nonmemory_operand" "")))
-   (set (reg:CC CC_REG)
-	(compare:CC (match_dup 5)
-		    (match_operand:SI 2 "nonmemory_operand" "")))
-   (set (pc)
-	(if_then_else (gtu (reg:CC CC_REG)
-			   (const_int 0))
-		      (label_ref (match_operand 4 "" ""))
-		      (pc)))
-   (set (match_dup 6)
-	(unspec:SI [(match_operand 3 "" "")
-		    (match_dup 5) (match_dup 7)] UNSPEC_ARC_CASESI))
-   (parallel [(set (pc) (match_dup 6)) (use (match_dup 7))])]
+  [(match_operand:SI 0 "register_operand" "")	; Index
+   (match_operand:SI 1 "const_int_operand" "")	; Lower bound
+   (match_operand:SI 2 "const_int_operand" "")	; Total range
+   (match_operand:SI 3 "" "")		; Table label
+   (match_operand:SI 4 "" "")]		; Out of range label
   ""
-  "
-{
-  rtx x;
-
-  operands[5] = gen_reg_rtx (SImode);
-  operands[6] = gen_reg_rtx (SImode);
-  operands[7] = operands[3];
-  emit_insn (gen_subsi3 (operands[5], operands[0], operands[1]));
-  emit_insn (gen_cmpsi_cc_insn_mixed (operands[5], operands[2]));
-  x = gen_rtx_GTU (VOIDmode, gen_rtx_REG (CCmode, CC_REG), const0_rtx);
-  x = gen_rtx_IF_THEN_ELSE (VOIDmode, x,
-			    gen_rtx_LABEL_REF (VOIDmode, operands[4]), pc_rtx);
-  emit_jump_insn (gen_rtx_SET (pc_rtx, x));
-  if (TARGET_COMPACT_CASESI)
-    {
-      emit_jump_insn (gen_casesi_compact_jump (operands[5], operands[7]));
-    }
-  else
-    {
+  {
+   if (operands[1] != const0_rtx)
+     {
+       rtx reg = gen_reg_rtx (SImode);
+       emit_insn (gen_subsi3 (reg, operands[0], operands[1]));
+       operands[0] = reg;
+      }
+   emit_jump_insn (gen_cbranchsi4 (gen_rtx_GTU (SImode, operands[0],
+							operands[2]),
+				   operands[0], operands[2], operands[4]));
+   if (TARGET_BI_BIH)
+     {
+      emit_jump_insn (gen_casesi_dispatch (operands[0], operands[3]));
+     }
+   else
+   {
+      rtx reg = gen_reg_rtx (SImode);
+      rtx lbl = operands[3];
       operands[3] = gen_rtx_LABEL_REF (VOIDmode, operands[3]);
-      if (flag_pic || !cse_not_expected)
+      if (flag_pic)
 	operands[3] = force_reg (Pmode, operands[3]);
-      emit_insn (gen_casesi_load (operands[6],
-				  operands[3], operands[5], operands[7]));
+      emit_insn (gen_casesi_load (reg,
+				  operands[3], operands[0], lbl));
       if (CASE_VECTOR_PC_RELATIVE || flag_pic)
-	emit_insn (gen_addsi3 (operands[6], operands[6], operands[3]));
-      emit_jump_insn (gen_casesi_jump (operands[6], operands[7]));
+	emit_insn (gen_addsi3 (reg, reg, operands[3]));
+      emit_jump_insn (gen_casesi_jump (reg, lbl));
+     }
+   DONE;
+  })
+
+(define_insn "casesi_dispatch"
+  [(set (pc)
+	(unspec:SI [(match_operand:SI 0 "register_operand" "r")
+		    (label_ref (match_operand 1 "" ""))]
+		   UNSPEC_ARC_CASESI))]
+  "TARGET_BI_BIH"
+  {
+   rtx diff_vec = PATTERN (next_nonnote_insn (as_a<rtx_insn *> (operands[1])));
+   gcc_assert (GET_CODE (diff_vec) == ADDR_DIFF_VEC);
+   switch (GET_MODE (diff_vec))
+   {
+    case E_SImode:
+     return \"bi\\t[%0]\";
+    case E_HImode:
+    case E_QImode:
+    return \"bih\\t[%0]\";
+    default: gcc_unreachable ();
     }
-  DONE;
-}")
+   }
+  [(set_attr "type" "brcc_no_delay_slot")
+   (set_attr "iscompact" "false")
+   (set_attr "length" "4")])
 
 (define_insn "casesi_load"
-  [(set (match_operand:SI 0 "register_operand"             "=Rcq,r,r")
-	(unspec:SI [(match_operand:SI 1 "nonmemory_operand" "Rcq,c,Cal")
-		    (match_operand:SI 2 "register_operand"  "Rcq,c,c")
-		    (label_ref (match_operand 3 "" ""))] UNSPEC_ARC_CASESI))]
+  [(set (match_operand:SI 0 "register_operand"             "=q,r,r")
+	(mem:SI (unspec:SI [(match_operand:SI 1 "nonmemory_operand" "q,r,Cal")
+			    (match_operand:SI 2 "register_operand"  "q,r,r")]
+			   UNSPEC_ARC_CASESI)))
+   (use (label_ref (match_operand 3 "" "")))]
   ""
   "*
 {
@@ -4037,15 +4049,15 @@ archs4x, archs4xd, archs4xd_slow"
   switch (GET_MODE (diff_vec))
     {
     case E_SImode:
-      return \"ld.as %0,[%1,%2]%&\";
+      return \"ld.as\\t%0,[%1,%2]%&\";
     case E_HImode:
       if (ADDR_DIFF_VEC_FLAGS (diff_vec).offset_unsigned)
-	return \"ld%_.as %0,[%1,%2]\";
-      return \"ld%_.x.as %0,[%1,%2]\";
+	return \"ld%_.as\\t%0,[%1,%2]\";
+      return \"ld%_.x.as\\t%0,[%1,%2]\";
     case E_QImode:
       if (ADDR_DIFF_VEC_FLAGS (diff_vec).offset_unsigned)
-	return \"ldb%? %0,[%1,%2]%&\";
-      return \"ldb.x %0,[%1,%2]\";
+	return \"ldb%?\\t%0,[%1,%2]%&\";
+      return \"ldb.x\\t%0,[%1,%2]\";
     default:
       gcc_unreachable ();
     }
@@ -4085,110 +4097,6 @@ archs4x, archs4xd, archs4xd_slow"
    (set_attr "iscompact" "false,maybe,false")
    (set_attr "cond" "canuse")])
 
-(define_insn "casesi_compact_jump"
-  [(set (pc)
-	(unspec:SI [(match_operand:SI 0 "register_operand" "c,q")]
-		   UNSPEC_ARC_CASESI))
-   (use (label_ref (match_operand 1 "" "")))
-   (clobber (match_scratch:SI 2 "=q,0"))]
-  "TARGET_COMPACT_CASESI"
-  "*
-{
-  rtx diff_vec = PATTERN (next_nonnote_insn (as_a<rtx_insn *> (operands[1])));
-  int unalign = arc_get_unalign ();
-  rtx xop[3];
-  const char *s;
-
-  xop[0] = operands[0];
-  xop[2] = operands[2];
-  gcc_assert (GET_CODE (diff_vec) == ADDR_DIFF_VEC);
-
-  switch (GET_MODE (diff_vec))
-    {
-    case E_SImode:
-      /* Max length can be 12 in this case, but this is OK because
-	 2 of these are for alignment, and are anticipated in the length
-	 of the ADDR_DIFF_VEC.  */
-      if (unalign && !satisfies_constraint_Rcq (xop[0]))
-	s = \"add2 %2,pcl,%0\n\tld_s %2,[%2,12]\";
-      else if (unalign)
-	s = \"add_s %2,%0,2\n\tld.as %2,[pcl,%2]\";
-      else
-	s = \"add %2,%0,2\n\tld.as %2,[pcl,%2]\";
-      arc_clear_unalign ();
-      break;
-    case E_HImode:
-      if (ADDR_DIFF_VEC_FLAGS (diff_vec).offset_unsigned)
-	{
-	  if (satisfies_constraint_Rcq (xop[0]))
-	    {
-	      s = \"add_s %2,%0,%1\n\tld%_.as %2,[pcl,%2]\";
-	      xop[1] = GEN_INT ((10 - unalign) / 2U);
-	    }
-	  else
-	    {
-	      s = \"add1 %2,pcl,%0\n\tld%__s %2,[%2,%1]\";
-	      xop[1] = GEN_INT (10 + unalign);
-	    }
-	}
-      else
-	{
-	  if (satisfies_constraint_Rcq (xop[0]))
-	    {
-	      s = \"add_s %2,%0,%1\n\tld%_.x.as %2,[pcl,%2]\";
-	      xop[1] = GEN_INT ((10 - unalign) / 2U);
-	    }
-	  else
-	    {
-	      s = \"add1 %2,pcl,%0\n\tld%__s.x %2,[%2,%1]\";
-	      xop[1] = GEN_INT (10 + unalign);
-	    }
-	}
-      arc_toggle_unalign ();
-      break;
-    case E_QImode:
-      if (ADDR_DIFF_VEC_FLAGS (diff_vec).offset_unsigned)
-	{
-	  if ((rtx_equal_p (xop[2], xop[0])
-	       || find_reg_note (insn, REG_DEAD, xop[0]))
-	      && satisfies_constraint_Rcq (xop[0]))
-	    {
-	      s = \"add_s %0,%0,pcl\n\tldb_s %2,[%0,%1]\";
-	      xop[1] = GEN_INT (8 + unalign);
-	    }
-	  else
-	    {
-	      s = \"add %2,%0,pcl\n\tldb_s %2,[%2,%1]\";
-	      xop[1] = GEN_INT (10 + unalign);
-	      arc_toggle_unalign ();
-	    }
-	}
-      else if ((rtx_equal_p (xop[0], xop[2])
-		|| find_reg_note (insn, REG_DEAD, xop[0]))
-	       && satisfies_constraint_Rcq (xop[0]))
-	{
-	  s = \"add_s %0,%0,%1\n\tldb.x %2,[pcl,%0]\";
-	  xop[1] = GEN_INT (10 - unalign);
-	  arc_toggle_unalign ();
-	}
-      else
-	{
-	  /* ??? Length is 12.  */
-	  s = \"add %2,%0,%1\n\tldb.x %2,[pcl,%2]\";
-	  xop[1] = GEN_INT (8 + unalign);
-	}
-      break;
-    default:
-      gcc_unreachable ();
-    }
-  output_asm_insn (s, xop);
-  return \"add_s %2,%2,pcl\n\tj_s%* [%2]\";
-}"
-  [(set_attr "length" "10")
-   (set_attr "type" "jump")
-   (set_attr "iscompact" "true")
-   (set_attr "cond" "nocond")])
-
 (define_expand "call"
   ;; operands[1] is stack_size_rtx
   ;; operands[2] is next_arg_register
diff --git a/gcc/config/arc/arc.opt b/gcc/config/arc/arc.opt
index ee06c063837..3e96b58375d 100644
--- a/gcc/config/arc/arc.opt
+++ b/gcc/config/arc/arc.opt
@@ -328,7 +328,7 @@ Target Var(TARGET_CASE_VECTOR_PC_RELATIVE)
 Use pc-relative switch case tables - this enables case table shortening.
 
 mcompact-casesi
-Target Var(TARGET_COMPACT_CASESI)
+Target Warn(%qs is deprecated)
 Enable compact casesi pattern.
 
 mq-class
@@ -528,3 +528,7 @@ Enum(arc_lpc) String(32) Value(32)
 mrf16
 Target Report Mask(RF16)
 Enable 16-entry register file.
+
+mbranch-index
+Target Report Var(TARGET_BRANCH_INDEX) Init(DEFAULT_BRANCH_INDEX)
+Enable use of BI/BIH instructions when available.
diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi
index 802cc642453..454587310c8 100644
--- a/gcc/doc/invoke.texi
+++ b/gcc/doc/invoke.texi
@@ -650,7 +650,7 @@ Objective-C and Objective-C++ Dialects}.
 -mmixed-code  -mq-class  -mRcq  -mRcw  -msize-level=@var{level} @gol
 -mtune=@var{cpu}  -mmultcost=@var{num} @gol
 -munalign-prob-threshold=@var{probability}  -mmpy-option=@var{multo} @gol
--mdiv-rem  -mcode-density  -mll64  -mfpu=@var{fpu} -mrf16}
+-mdiv-rem  -mcode-density  -mll64  -mfpu=@var{fpu} -mrf16 -mbranch-index}
 
 @emph{ARM Options}
 @gccoptlist{-mapcs-frame  -mno-apcs-frame @gol
@@ -15814,6 +15814,11 @@ This option instructs the compiler to generate code for a 16-entry
 register file.  This option defines the @code{__ARC_RF16__}
 preprocessor macro.
 
+@item -mbranch-index
+@opindex mbranch-index
+Enable use of @code{bi} or @code{bih} instructions to implement jump
+tables.
+
 @end table
 
 The following options are passed through to the assembler, and also
@@ -15985,7 +15990,7 @@ This is the default for @option{-Os}.
 @item -mcompact-casesi
 @opindex mcompact-casesi
 Enable compact @code{casesi} pattern.  This is the default for @option{-Os},
-and only available for ARCv1 cores.
+and only available for ARCv1 cores.  This option is deprecated.
 
 @item -mno-cond-exec
 @opindex mno-cond-exec
diff --git a/gcc/testsuite/gcc.target/arc/jumptable.c b/gcc/testsuite/gcc.target/arc/jumptable.c
new file mode 100644
index 00000000000..fbc58e33149
--- /dev/null
+++ b/gcc/testsuite/gcc.target/arc/jumptable.c
@@ -0,0 +1,34 @@
+/* { dg-do compile } */
+/* { dg-skip-if "" { arc700 || arc6xx } } */
+/* { dg-options "-O2 -mbranch-index -mcode-density" { target { arcem || archs } } } */
+
+extern void max( int,int);
+
+int switchCase(int value, int b)
+{
+  switch(value){
+  case 100:
+    value = b * value;
+    break;
+  case 101:
+    value = b << value;
+    break;
+  case 102:
+    value = b / value;
+    break;
+  case 103:
+    value = b >> value;
+    break;
+  case 104:
+    value = b + value;
+    break;
+  case 105:
+    value = b - value;
+    break;
+  }
+  max(value, b);
+  return 0;
+}
+
+/* { dg-final { scan-assembler-times "bih" 1 } } */
+/* { dg-final { scan-assembler-times "b_s" 8 } } */
-- 
2.17.1

  parent reply	other threads:[~2018-10-10  8:01 UTC|newest]

Thread overview: 25+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-10-10  8:01 [PATCH 0/6] ARC updates Claudiu Zissulescu
2018-10-10  8:01 ` [PATCH 6/6] [ARC] Handle store cacheline hazard Claudiu Zissulescu
2018-10-30 10:13   ` Andrew Burgess
2018-10-31  9:19     ` claziss
2018-10-31 13:43     ` claziss
2018-10-10  8:01 ` [PATCH 2/6] [ARC] Cleanup TLS implementation Claudiu Zissulescu
2018-10-11 10:13   ` Andrew Burgess
2018-10-31 13:11     ` claziss
2018-10-10  8:01 ` [PATCH 4/6] [ARC] Add peephole rules to combine store/loads into double store/loads Claudiu Zissulescu
2018-10-22 18:15   ` Andrew Burgess
2018-10-22 23:29     ` Bernhard Reutner-Fischer
2018-10-31  9:11       ` claziss
2018-11-12 11:33         ` claziss
2018-11-13 10:00         ` Andrew Burgess
2018-10-10  8:01 ` [PATCH 1/6] [ARC] Remove non standard funcions calls Claudiu Zissulescu
2018-10-11 10:14   ` Andrew Burgess
2018-10-31 12:40     ` claziss
2018-10-10  8:49 ` Claudiu Zissulescu [this message]
2018-10-16 23:19   ` [PATCH 3/6] [ARC] Add BI/BIH instruction support Andrew Burgess
2018-10-17 17:21     ` Claudiu Zissulescu
2018-10-31 12:59     ` claziss
2018-10-17  7:19   ` Sandra Loosemore
2018-10-31 12:31     ` claziss
2018-10-10  9:05 ` [PATCH 5/6] [ARC] Refurbish and improve prologue/epilogue functions Claudiu Zissulescu
2018-10-22 18:26   ` Andrew Burgess

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20181010080016.12317-4-claziss@gmail.com \
    --to=claziss@gmail.com \
    --cc=andrew.burgess@embecosm.com \
    --cc=claziss@synopsys.com \
    --cc=fbedard@synopsys.com \
    --cc=gcc-patches@gcc.gnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).