Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 25 Feb 2009 20:46:17 GMT
From:      Oleksandr Tymoshenko <gonzo@FreeBSD.org>
To:        Perforce Change Reviews <perforce@FreeBSD.org>
Subject:   PERFORCE change 158286 for review
Message-ID:  <200902252046.n1PKkHM5026331@repoman.freebsd.org>

next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=158286

Change 158286 by gonzo@gonzo_figaro on 2009/02/25 20:46:02

	- Add AVR32 bits to GCC

Affected files ...

.. //depot/projects/avr32/src/contrib/gcc/config.gcc#2 edit
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/avr32-elf.h#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/avr32-modes.def#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/avr32-protos.h#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/avr32.c#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/avr32.h#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/avr32.md#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/avr32.opt#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/crti.asm#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/crtn.asm#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/fpcp.md#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/freebsd.h#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/lib1funcs.S#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/lib2funcs.S#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/linux-elf.h#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/predicates.md#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/simd.md#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/sync.md#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/t-avr32#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/t-elf#1 add
.. //depot/projects/avr32/src/contrib/gcc/config/avr32/uclinux-elf.h#1 add
.. //depot/projects/avr32/src/contrib/gcc/expmed.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/expr.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/flow.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/function.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/genemit.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/genflags.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/genoutput.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/ifcvt.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/longlong.h#2 edit
.. //depot/projects/avr32/src/contrib/gcc/optabs.h#2 edit
.. //depot/projects/avr32/src/contrib/gcc/regrename.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/reload.c#2 edit
.. //depot/projects/avr32/src/contrib/gcc/sched-deps.c#2 edit

Differences ...

==== //depot/projects/avr32/src/contrib/gcc/config.gcc#2 (text+ko) ====

@@ -782,6 +782,24 @@
 	tm_file="avr/avr.h dbxelf.h"
 	use_fixproto=yes
 	;;
+avr32*-*-linux*)
+    tm_file="dbxelf.h elfos.h linux.h avr32/linux-elf.h avr32/avr32.h "
+    tmake_file="t-linux avr32/t-avr32 avr32/t-elf"
+	extra_parts="crtbegin.o crtbeginS.o crtend.o crtendS.o"
+	extra_modes=avr32/avr32-modes.def
+	gnu_ld=yes
+	;;
+avr32*-*-uclinux*)
+	tm_file="dbxelf.h elfos.h linux.h avr32/linux-elf.h avr32/uclinux-elf.h avr32/avr32.h"
+	tmake_file="t-linux avr32/t-avr32 avr32/t-elf"
+	extra_modes=avr32/avr32-modes.def
+	gnu_ld=yes
+	;;
+avr32-*-*)
+    tm_file="dbxelf.h elfos.h avr32/avr32.h avr32/avr32-elf.h"
+    tmake_file="avr32/t-avr32 avr32/t-elf"
+	extra_modes=avr32/avr32-modes.def
+	;;
 bfin*-elf*)
 	tm_file="${tm_file} dbxelf.h elfos.h bfin/elf.h"
         tmake_file=bfin/t-bfin-elf
@@ -1682,6 +1700,9 @@
 pdp11-*-*)
 	use_fixproto=yes
 	;;
+avr-*-*)
+	use_fixproto=yes
+	;;
 # port not yet contributed
 #powerpc-*-openbsd*)
 #	tmake_file="${tmake_file} rs6000/t-fprules rs6000/t-fprules-fpbit "
@@ -2718,6 +2739,32 @@
 		fi
 		;;
 
+	avr32*-*-*)
+		supported_defaults="part arch"
+
+		case "$with_part" in
+		"" \
+		| "ap7000" | "ap7010" | "ap7020" | "uc3a0256" | "uc3a0512" | "uc3a1128" | "uc3a1256" | "uc3a1512" )
+			# OK
+			;;
+		*)
+			echo "Unknown part used in --with-part=$with_part" 1>&2
+			exit 1
+			;;
+		esac
+
+		case "$with_arch" in
+		"" \
+		| "ap" | "uc")
+			# OK
+			;;
+		*)
+			echo "Unknown arch used in --with-arch=$with_arch" 1>&2
+			exit 1
+			;;
+		esac
+                ;;
+
 	fr*-*-*linux*)
 		supported_defaults=cpu
 		case "$with_cpu" in

==== //depot/projects/avr32/src/contrib/gcc/expmed.c#2 (text+ko) ====

@@ -37,6 +37,7 @@
 #include "real.h"
 #include "recog.h"
 #include "langhooks.h"
+#include "target.h"
 
 static void store_fixed_bit_field (rtx, unsigned HOST_WIDE_INT,
 				   unsigned HOST_WIDE_INT,
@@ -455,9 +456,19 @@
 	  ? ((GET_MODE_SIZE (fieldmode) >= UNITS_PER_WORD
 	     || GET_MODE_SIZE (GET_MODE (op0)) == GET_MODE_SIZE (fieldmode))
 	     && byte_offset % GET_MODE_SIZE (fieldmode) == 0)
-	  : (! SLOW_UNALIGNED_ACCESS (fieldmode, MEM_ALIGN (op0))
-	     || (offset * BITS_PER_UNIT % bitsize == 0
-		 && MEM_ALIGN (op0) % GET_MODE_BITSIZE (fieldmode) == 0))))
+         : ( 
+
+             /* NB! Added for AVR32, and I think this should be true for
+                all targets not using narrow volatile bitfields. If the
+                bitfield is volatile then we need to perform an access
+                consistent with the container type. */
+             !(MEM_VOLATILE_P (op0) 
+               && GET_MODE_BITSIZE (GET_MODE (op0)) != bitsize
+               && bitsize < BITS_PER_WORD
+               && !targetm.narrow_volatile_bitfield ())
+             && (! SLOW_UNALIGNED_ACCESS (fieldmode, MEM_ALIGN (op0))
+                 || (offset * BITS_PER_UNIT % bitsize == 0
+                     && MEM_ALIGN (op0) % GET_MODE_BITSIZE (fieldmode) == 0)))))
     {
       if (MEM_P (op0))
 	op0 = adjust_address (op0, fieldmode, offset);
@@ -1257,6 +1268,13 @@
 	   && GET_MODE_SIZE (mode1) != 0
 	   && byte_offset % GET_MODE_SIZE (mode1) == 0)
 	  || (MEM_P (op0)
+             /* NB! Added for AVR32, and I think this should be true for
+                all targets not using narrow volatile bitfields. If the
+                bitfield is volatile then we need to perform an access
+                consistent with the container type. */
+              && !(MEM_VOLATILE_P (op0)
+                   && GET_MODE_BITSIZE (GET_MODE (op0)) != bitsize
+                   && !targetm.narrow_volatile_bitfield ())
 	      && (! SLOW_UNALIGNED_ACCESS (mode, MEM_ALIGN (op0))
 		  || (offset * BITS_PER_UNIT % bitsize == 0
 		      && MEM_ALIGN (op0) % bitsize == 0)))))

==== //depot/projects/avr32/src/contrib/gcc/expr.c#2 (text+ko) ====

@@ -3520,18 +3520,19 @@
     }
   else
     {
+      emit_move_insn (stack_pointer_rtx,
+		      expand_binop (Pmode,
 #ifdef STACK_GROWS_DOWNWARD
-      /* ??? This seems wrong if STACK_PUSH_CODE == POST_DEC.  */
-      dest_addr = gen_rtx_PLUS (Pmode, stack_pointer_rtx,
-				GEN_INT (-(HOST_WIDE_INT) rounded_size));
+				    sub_optab,
 #else
-      /* ??? This seems wrong if STACK_PUSH_CODE == POST_INC.  */
-      dest_addr = gen_rtx_PLUS (Pmode, stack_pointer_rtx,
-				GEN_INT (rounded_size));
+				    add_optab,
 #endif
-      dest_addr = gen_rtx_PRE_MODIFY (Pmode, stack_pointer_rtx, dest_addr);
+				    stack_pointer_rtx,
+				    GEN_INT (rounded_size),
+				    NULL_RTX, 0, OPTAB_LIB_WIDEN));
+      dest_addr = stack_pointer_rtx;
     }
-
+  
   dest = gen_rtx_MEM (mode, dest_addr);
 
   if (type != 0)
@@ -5510,7 +5511,21 @@
      is a bit field, we cannot use addressing to access it.
      Use bit-field techniques or SUBREG to store in it.  */
 
-  if (mode == VOIDmode
+  if (
+      /* NB! Added for AVR32, and I think this should be true for
+         all targets not using narrow volatile bitfields. If the
+         bitfield is volatile then we need to perform an access
+         consistent with the container type. */
+      (MEM_P (target) 
+       && MEM_VOLATILE_P (target) 
+       && ((GET_MODE (target) != BLKmode
+            && GET_MODE_BITSIZE (GET_MODE (target)) > bitsize )
+           /* If BLKmode, check if this is a record. Do not know 
+              if this is really necesarry though...*/
+           || (GET_MODE (target) == BLKmode
+               && TREE_CODE (type) == RECORD_TYPE))
+       && !targetm.narrow_volatile_bitfield ())
+      || mode == VOIDmode
       || (mode != BLKmode && ! direct_store[(int) mode]
 	  && GET_MODE_CLASS (mode) != MODE_COMPLEX_INT
 	  && GET_MODE_CLASS (mode) != MODE_COMPLEX_FLOAT)
@@ -7512,7 +7527,21 @@
 	   by doing the extract into an object as wide as the field
 	   (which we know to be the width of a basic mode), then
 	   storing into memory, and changing the mode to BLKmode.  */
-	if (mode1 == VOIDmode
+       if (      
+            /* NB! Added for AVR32, and I think this should be true for
+               all targets not using narrow volatile bitfields. If the
+               bitfield is volatile then we need to perform an access
+               consistent with the container type. */
+            (MEM_P (op0) 
+             && MEM_VOLATILE_P (op0) 
+             && ((GET_MODE (op0) != BLKmode
+                  && GET_MODE_BITSIZE (GET_MODE (op0)) > bitsize )
+                 /* If BLKmode, check if this is a record. Do not know 
+                    if this is really necesarry though...*/
+                 || (GET_MODE (op0) == BLKmode
+                     && TREE_CODE (type) == RECORD_TYPE))
+             && !targetm.narrow_volatile_bitfield ())
+            || mode1 == VOIDmode
 	    || REG_P (op0) || GET_CODE (op0) == SUBREG
 	    || (mode1 != BLKmode && ! direct_load[(int) mode1]
 		&& GET_MODE_CLASS (mode) != MODE_COMPLEX_INT

==== //depot/projects/avr32/src/contrib/gcc/flow.c#2 (text+ko) ====

@@ -3328,12 +3328,12 @@
   if (GET_CODE (x) == NOT)
     return XEXP (x, 0);
   if (COMPARISON_P (x)
-      && REG_P (XEXP (x, 0)))
+      /* && REG_P (XEXP (x, 0))*/)
     {
-      gcc_assert (XEXP (x, 1) == const0_rtx);
+      /*gcc_assert (XEXP (x, 1) == const0_rtx);*/
 
       return gen_rtx_fmt_ee (reversed_comparison_code (x, NULL),
-			     VOIDmode, XEXP (x, 0), const0_rtx);
+			     VOIDmode, XEXP (x, 0), XEXP (x, 0) /*const0_rtx*/);
     }
   return gen_rtx_NOT (0, x);
 }

==== //depot/projects/avr32/src/contrib/gcc/function.c#2 (text+ko) ====

@@ -2679,8 +2679,12 @@
     SET_DECL_RTL (parm, parmreg);
 
   /* Copy the value into the register.  */
-  if (data->nominal_mode != data->passed_mode
-      || promoted_nominal_mode != data->promoted_mode)
+  if ( (data->nominal_mode != data->passed_mode
+        /* Added for AVR32: If passed_mode is equal
+           to promoted nominal mode why should be convert?
+           The conversion should make no difference. */
+        && data->passed_mode != promoted_nominal_mode)
+       || promoted_nominal_mode != data->promoted_mode)
     {
       int save_tree_used;
 

==== //depot/projects/avr32/src/contrib/gcc/genemit.c#2 (text+ko) ====

@@ -122,6 +122,24 @@
 }
 
 static void
+gen_vararg_prologue(int operands)
+{
+  int i;
+
+  if (operands > 1)
+    {
+      for (i = 1; i < operands; i++)
+	printf("  rtx operand%d ATTRIBUTE_UNUSED;\n", i);
+
+      printf("  va_list args;\n\n");
+      printf("  va_start(args, operand0);\n");
+      for (i = 1; i < operands; i++)
+	printf("  operand%d = va_arg(args, rtx);\n", i);
+      printf("  va_end(args);\n\n");
+    }
+}
+
+static void
 print_code (RTX_CODE code)
 {
   const char *p1;
@@ -406,18 +424,16 @@
     fatal ("match_dup operand number has no match_operand");
 
   /* Output the function name and argument declarations.  */
-  printf ("rtx\ngen_%s (", XSTR (insn, 0));
+  printf ("rtx\ngen_%s ", XSTR (insn, 0));
+
   if (operands)
-    for (i = 0; i < operands; i++)
-      if (i)
-	printf (",\n\trtx operand%d ATTRIBUTE_UNUSED", i);
-      else
-	printf ("rtx operand%d ATTRIBUTE_UNUSED", i);
+    printf("(rtx operand0 ATTRIBUTE_UNUSED, ...)\n");
   else
-    printf ("void");
-  printf (")\n");
+    printf("(void)\n");
   printf ("{\n");
 
+  gen_vararg_prologue(operands);
+
   /* Output code to construct and return the rtl for the instruction body.  */
 
   if (XVECLEN (insn, 1) == 1)
@@ -457,16 +473,12 @@
   operands = max_operand_vec (expand, 1);
 
   /* Output the function name and argument declarations.  */
-  printf ("rtx\ngen_%s (", XSTR (expand, 0));
+  printf ("rtx\ngen_%s ", XSTR (expand, 0));
   if (operands)
-    for (i = 0; i < operands; i++)
-      if (i)
-	printf (",\n\trtx operand%d", i);
-      else
-	printf ("rtx operand%d", i);
+    printf("(rtx operand0 ATTRIBUTE_UNUSED, ...)\n");
   else
-    printf ("void");
-  printf (")\n");
+    printf("(void)\n");
+
   printf ("{\n");
 
   /* If we don't have any C code to write, only one insn is being written,
@@ -476,6 +488,8 @@
       && operands > max_dup_opno
       && XVECLEN (expand, 1) == 1)
     {
+      gen_vararg_prologue(operands);
+
       printf ("  return ");
       gen_exp (XVECEXP (expand, 1, 0), DEFINE_EXPAND, NULL);
       printf (";\n}\n\n");
@@ -489,6 +503,7 @@
   for (; i <= max_scratch_opno; i++)
     printf ("  rtx operand%d ATTRIBUTE_UNUSED;\n", i);
   printf ("  rtx _val = 0;\n");
+  gen_vararg_prologue(operands);
   printf ("  start_sequence ();\n");
 
   /* The fourth operand of DEFINE_EXPAND is some code to be executed

==== //depot/projects/avr32/src/contrib/gcc/genflags.c#2 (text+ko) ====

@@ -128,7 +128,6 @@
 gen_proto (rtx insn)
 {
   int num = num_operands (insn);
-  int i;
   const char *name = XSTR (insn, 0);
   int truth = maybe_eval_c_test (XSTR (insn, 2));
 
@@ -159,12 +158,7 @@
   if (num == 0)
     fputs ("void", stdout);
   else
-    {
-      for (i = 1; i < num; i++)
-	fputs ("rtx, ", stdout);
-
-      fputs ("rtx", stdout);
-    }
+    fputs("rtx, ...", stdout);
 
   puts (");");
 
@@ -174,12 +168,7 @@
     {
       printf ("static inline rtx\ngen_%s", name);
       if (num > 0)
-	{
-	  putchar ('(');
-	  for (i = 0; i < num-1; i++)
-	    printf ("rtx ARG_UNUSED (%c), ", 'a' + i);
-	  printf ("rtx ARG_UNUSED (%c))\n", 'a' + i);
-	}
+	puts("(rtx ARG_UNUSED(a), ...)");
       else
 	puts ("(void)");
       puts ("{\n  return 0;\n}");

==== //depot/projects/avr32/src/contrib/gcc/genoutput.c#2 (text+ko) ====

@@ -387,7 +387,7 @@
 	}
 
       if (d->name && d->name[0] != '*')
-	printf ("    (insn_gen_fn) gen_%s,\n", d->name);
+	printf ("    gen_%s,\n", d->name);
       else
 	printf ("    0,\n");
 

==== //depot/projects/avr32/src/contrib/gcc/ifcvt.c#2 (text+ko) ====

@@ -78,7 +78,7 @@
 static int num_updated_if_blocks;
 
 /* # of changes made which require life information to be updated.  */
-static int num_true_changes;
+int num_true_changes;
 
 /* Whether conditional execution changes were made.  */
 static int cond_exec_changed_p;
@@ -288,12 +288,15 @@
       if (must_be_last)
 	return FALSE;
 
-      if (modified_in_p (test, insn))
-	{
-	  if (!mod_ok)
-	    return FALSE;
-	  must_be_last = TRUE;
-	}
+#ifdef IFCVT_ALLOW_MODIFY_TEST_IN_INSN       
+      if ( !IFCVT_ALLOW_MODIFY_TEST_IN_INSN )
+#endif
+        if (modified_in_p (test, insn))
+          {
+            if (!mod_ok)
+              return FALSE;
+            must_be_last = TRUE;
+          }
 
       /* Now build the conditional form of the instruction.  */
       pattern = PATTERN (insn);
@@ -567,16 +570,19 @@
   /* Do any machine dependent final modifications.  */
   IFCVT_MODIFY_FINAL (ce_info);
 #endif
-
-  /* Conversion succeeded.  */
-  if (dump_file)
-    fprintf (dump_file, "%d insn%s converted to conditional execution.\n",
-	     n_insns, (n_insns == 1) ? " was" : "s were");
-
+  
   /* Merge the blocks!  */
-  merge_if_block (ce_info);
-  cond_exec_changed_p = TRUE;
-  return TRUE;
+  if ( reload_completed ){
+    /* Conversion succeeded.  */
+    if (dump_file)
+      fprintf (dump_file, "%d insn%s converted to conditional execution.\n",
+               n_insns, (n_insns == 1) ? " was" : "s were");
+    
+    merge_if_block (ce_info);
+    cond_exec_changed_p = TRUE;
+    return TRUE;
+  }
+  return FALSE;
 
  fail:
 #ifdef IFCVT_MODIFY_CANCEL
@@ -1051,7 +1057,11 @@
 	  != UNKNOWN))
     {
       rtx cond = if_info->cond;
-      enum rtx_code code = reversed_comparison_code (cond, if_info->jump);
+      /* This generates wrong code for AVR32. The cond code need not be reversed
+         since the addmodecc patterns add if the condition is NOT met. */
+      /*   enum rtx_code code = reversed_comparison_code (cond, if_info->jump);*/
+      enum rtx_code code = GET_CODE(cond);
+
 
       /* First try to use addcc pattern.  */
       if (general_operand (XEXP (cond, 0), VOIDmode)
@@ -2652,7 +2662,12 @@
       && cond_move_process_if_block (ce_info))
     return TRUE;
 
-  if (HAVE_conditional_execution && reload_completed)
+  if (HAVE_conditional_execution && 
+#ifdef IFCVT_COND_EXEC_BEFORE_RELOAD
+      (reload_completed || IFCVT_COND_EXEC_BEFORE_RELOAD))
+#else
+      reload_completed)
+#endif
     {
       /* If we have && and || tests, try to first handle combining the && and
          || tests into the conditional code, and if that fails, go back and
@@ -4037,6 +4052,15 @@
   cleanup_cfg (CLEANUP_EXPENSIVE
                | CLEANUP_UPDATE_LIFE
                | (flag_crossjumping ? CLEANUP_CROSSJUMP : 0));
+  
+  /* Hack for the AVR32 experimental ifcvt processing before reload.
+     The AVR32 specific ifcvt code needs to know when ifcvt after reload 
+     has begun. */
+#ifdef IFCVT_COND_EXEC_BEFORE_RELOAD
+  if ( IFCVT_COND_EXEC_BEFORE_RELOAD )
+    cfun->machine->ifcvt_after_reload = 1;
+#endif
+  
   if (flag_if_conversion2)
     if_convert (1);
   return 0;

==== //depot/projects/avr32/src/contrib/gcc/longlong.h#2 (text+ko) ====

@@ -227,6 +227,41 @@
 #define UDIV_TIME 100
 #endif /* __arm__ */
 
+#if defined (__avr32__) && W_TYPE_SIZE == 32
+#define add_ssaaaa(sh, sl, ah, al, bh, bl) \
+  __asm__ ("add\t%1, %4, %5\n\tadc\t%0, %2, %3"		\
+	   : "=r" ((USItype) (sh)),					\
+	     "=&r" ((USItype) (sl))					\
+	   : "r" ((USItype) (ah)),					\
+	     "r" ((USItype) (bh)),					\
+	     "r" ((USItype) (al)),					\
+	     "r" ((USItype) (bl)) __CLOBBER_CC)
+#define sub_ddmmss(sh, sl, ah, al, bh, bl) \
+  __asm__ ("sub\t%1, %4, %5\n\tsbc\t%0, %2, %3"		\
+	   : "=r" ((USItype) (sh)),					\
+	     "=&r" ((USItype) (sl))					\
+	   : "r" ((USItype) (ah)),					\
+	     "r" ((USItype) (bh)),					\
+	     "r" ((USItype) (al)),					\
+	     "r" ((USItype) (bl)) __CLOBBER_CC)
+
+#if !defined (__AVR32_UC__) || __AVR32_UC__ != 3
+#define __umulsidi3(a,b) ((UDItype)(a) * (UDItype)(b))
+
+#define umul_ppmm(w1, w0, u, v) \
+{									\
+  DWunion __w;								\
+  __w.ll = __umulsidi3 (u, v);						\
+  w1 = __w.s.high;							\
+  w0 = __w.s.low;							\
+}
+#endif
+
+#define count_leading_zeros(COUNT,X)	((COUNT) = __builtin_clz (X))
+#define count_trailing_zeros(COUNT,X)	((COUNT) = __builtin_ctz (X))
+#define COUNT_LEADING_ZEROS_0 32
+#endif
+
 #if defined (__hppa) && W_TYPE_SIZE == 32
 #define add_ssaaaa(sh, sl, ah, al, bh, bl) \
   __asm__ ("add %4,%5,%1\n\taddc %2,%3,%0"				\

==== //depot/projects/avr32/src/contrib/gcc/optabs.h#2 (text+ko) ====

@@ -432,7 +432,7 @@
 extern GTY(()) optab code_to_optab[NUM_RTX_CODE + 1];
 
 
-typedef rtx (*rtxfun) (rtx);
+typedef rtx (*rtxfun) (rtx, ...);
 
 /* Indexed by the rtx-code for a conditional (e.g. EQ, LT,...)
    gives the gen_function to make a branch to test that condition.  */

==== //depot/projects/avr32/src/contrib/gcc/regrename.c#2 (text+ko) ====

@@ -1593,6 +1593,9 @@
   bool changed = false;
   rtx insn;
 
+  rtx prev_pred_test;
+  int prev_pred_insn_skipped = 0;
+
   for (insn = BB_HEAD (bb); ; insn = NEXT_INSN (insn))
     {
       int n_ops, i, alt, predicated;
@@ -1631,7 +1634,60 @@
 	      || (predicated && recog_data.operand_type[i] == OP_OUT))
 	    recog_data.operand_type[i] = OP_INOUT;
 	}
+      
+
+      /* Added for targets (AVR32) which supports test operands to be modified
+         in cond_exec instruction. For these targets we cannot make a change to
+         the test operands if one of the test operands is an output operand This beacuse
+         changing the test operands might cause the need for inserting a new test
+         insns in the middle of a sequence of cond_exec insns and if the test operands
+         are modified these tests will fail.
+      */
+      
+      if ( IFCVT_ALLOW_MODIFY_TEST_IN_INSN
+           && predicated )
+        { 
+          int insn_skipped = 0;
+          rtx test = COND_EXEC_TEST (PATTERN (insn));
 
+          /* Check if the previous insn was a skipped predicated insn with the same
+             test as this predicated insns. If so we cannot do any modification to
+             this insn either since we cannot emit the test insn because the operands
+             are clobbered. */
+          if ( prev_pred_insn_skipped 
+               && (rtx_equal_p (test, prev_pred_test) 
+                   || rtx_equal_p (test, reversed_condition (prev_pred_test))) )
+            { 
+              insn_skipped = 1;
+            }
+          else
+            {
+              /* Check if the output operand is used in the test expression. */
+              for (i = 0; i < n_ops; ++i)
+                if ( recog_data.operand_type[i] == OP_INOUT 
+                     && reg_mentioned_p (recog_data.operand[i], test) )
+                  {
+                    insn_skipped = 1;
+                    break;
+                  }
+              
+            }
+          
+          prev_pred_test = test;
+          prev_pred_insn_skipped = insn_skipped;
+          if ( insn_skipped )
+            {
+              if (insn == BB_END (bb))
+                break;
+              else
+                continue;
+            }
+        } 
+      else 
+        {
+          prev_pred_insn_skipped = 0;
+        }
+      
       /* For each earlyclobber operand, zap the value data.  */
       for (i = 0; i < n_ops; i++)
 	if (recog_op_alt[i][alt].earlyclobber)

==== //depot/projects/avr32/src/contrib/gcc/reload.c#2 (text+ko) ====

@@ -4575,7 +4575,7 @@
 	      x = mem;
 	      i = find_reloads_address (GET_MODE (x), &x, XEXP (x, 0), &XEXP (x, 0),
 					opnum, type, ind_levels, insn);
-	      if (x != mem)
+         if (!rtx_equal_p (x, mem))
 		push_reg_equiv_alt_mem (regno, x);
 	      if (address_reloaded)
 		*address_reloaded = i;

==== //depot/projects/avr32/src/contrib/gcc/sched-deps.c#2 (text+ko) ====

@@ -650,7 +650,14 @@
 
   prev_nonnote = prev_nonnote_insn (insn);
   if (BLOCK_FOR_INSN (insn) == BLOCK_FOR_INSN (prev_nonnote)
-      && ! sched_insns_conditions_mutex_p (insn, prev_nonnote))
+      /* Modification for AVR32 by RP: Why is this here, this will
+         cause instruction to be without any dependencies which might
+         cause it to be moved anywhere. For the AVR32 we try to keep
+         a group of conditionals together even if they are mutual exclusive.
+      */
+      && (! sched_insns_conditions_mutex_p (insn, prev_nonnote)
+          || GET_CODE (PATTERN (insn)) == COND_EXEC )
+      )
     add_dependence (insn, prev_nonnote, REG_DEP_ANTI);
 }
 
@@ -1124,8 +1131,29 @@
 
   if (code == COND_EXEC)
     {
+#ifdef IFCVT_ALLOW_MODIFY_TEST_IN_INSN
+      if (IFCVT_ALLOW_MODIFY_TEST_IN_INSN)
+        {
+          /* Check if we have a group og conditional instructions with the same test. 
+             If so we must make sure that they are not scheduled apart in order to
+             avoid unnecesarry tests and if one of the registers in the test is modified
+             in the instruction this is needed to ensure correct code. */
+          if ( prev_nonnote_insn (insn)
+               && INSN_P (prev_nonnote_insn (insn))
+               && GET_CODE (PATTERN (prev_nonnote_insn (insn))) == COND_EXEC 
+               && rtx_equal_p (XEXP(COND_EXEC_TEST (PATTERN (prev_nonnote_insn (insn))), 0), XEXP (COND_EXEC_TEST (x), 0))
+               && rtx_equal_p (XEXP(COND_EXEC_TEST (PATTERN (prev_nonnote_insn (insn))), 1), XEXP (COND_EXEC_TEST (x), 1))
+               && ( GET_CODE (COND_EXEC_TEST (PATTERN (prev_nonnote_insn (insn)))) == GET_CODE (COND_EXEC_TEST (x))
+                    || GET_CODE (COND_EXEC_TEST (PATTERN (prev_nonnote_insn (insn)))) == reversed_comparison_code (COND_EXEC_TEST (x), insn)))
+            {
+              SCHED_GROUP_P (insn) = 1;
+              //CANT_MOVE (prev_nonnote_insn (insn)) = 1;
+            }
+        }
+#endif      
       sched_analyze_2 (deps, COND_EXEC_TEST (x), insn);
 
+
       /* ??? Should be recording conditions so we reduce the number of
 	 false dependencies.  */
       x = COND_EXEC_CODE (x);



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200902252046.n1PKkHM5026331>