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]

mn10300 DI/DFmode may clobber CC without telling GCC


This patch fixes a problem in that the DImode and DFmode sequences may
use clr as part of loading a 64-bit constant into a pair of data
registers, but clr sets the CC to zero, however the insn attributes
didn't indicate that it might clobber CC.  This patch fixes this
problem.  I'm checking it in both mainline and 3.3.

Index: gcc/ChangeLog
from  Alexandre Oliva  <aoliva@redhat.com>

	* config/mn10300/mn10300.c (mn10300_wide_const_load_uses_clr): New
	function.
	* config/mn10300/mn10300-protos.h: Declare it.
	* config/mn10300/mn10300.md (movdi, movdf): Use it to compute
	attribute cc of instructions that may use clr.

Index: gcc/config/mn10300/mn10300-protos.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mn10300/mn10300-protos.h,v
retrieving revision 1.6
diff -u -p -r1.6 mn10300-protos.h
--- gcc/config/mn10300/mn10300-protos.h 28 Jan 2003 18:08:53 -0000 1.6
+++ gcc/config/mn10300/mn10300-protos.h 14 Feb 2003 21:34:36 -0000
@@ -1,5 +1,5 @@
 /* Definitions of target machine for GNU compiler. Matsushita MN10300 series
-   Copyright (C) 2000 Free Software Foundation, Inc.
+   Copyright (C) 2000, 2003 Free Software Foundation, Inc.
    Contributed by Jeff Law (law@cygnus.com).
 
 This file is part of GNU CC.
@@ -40,6 +40,8 @@ extern int symbolic_operand PARAMS ((rtx
 extern int call_address_operand PARAMS ((rtx, enum machine_mode));
 extern int impossible_plus_operand PARAMS ((rtx, enum machine_mode));
 extern int const_8bit_operand PARAMS ((rtx, enum machine_mode));
+
+extern bool mn10300_wide_const_load_uses_clr PARAMS ((rtx operands[2]));
 #endif /* RTX_CODE */
 
 #ifdef TREE_CODE
@@ -57,4 +59,3 @@ extern void expand_epilogue PARAMS ((voi
 extern int initial_offset PARAMS ((int, int));
 extern int can_use_return_insn PARAMS ((void));
 extern int mask_ok_for_mem_btst PARAMS ((int, int));
-
Index: gcc/config/mn10300/mn10300.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mn10300/mn10300.c,v
retrieving revision 1.49
diff -u -p -r1.49 mn10300.c
--- gcc/config/mn10300/mn10300.c 28 Jan 2003 18:08:53 -0000 1.49
+++ gcc/config/mn10300/mn10300.c 14 Feb 2003 21:34:36 -0000
@@ -1,5 +1,5 @@
 /* Subroutines for insn-output.c for Matsushita MN10300 series
-   Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002
+   Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003
    Free Software Foundation, Inc.
    Contributed by Jeff Law (law@cygnus.com).
 
@@ -1389,4 +1389,52 @@ mn10300_rtx_costs (x, code, outer_code, 
     default:
       return false;
     }
+}
+
+/* Check whether a constant used to initialize a DImode or DFmode can
+   use a clr instruction.  The code here must be kept in sync with
+   movdf and movdi.  */
+
+bool
+mn10300_wide_const_load_uses_clr (operands)
+     rtx operands[2];
+{
+  long val[2];
+
+  if (GET_CODE (operands[0]) != REG
+      || REGNO_REG_CLASS (REGNO (operands[0])) != DATA_REGS)
+    return false;
+
+  switch (GET_CODE (operands[1]))
+    {
+    case CONST_INT:
+      {
+	rtx low, high;
+	split_double (operands[1], &low, &high);
+	val[0] = INTVAL (low);
+	val[1] = INTVAL (high);
+      }
+      break;
+      
+    case CONST_DOUBLE:
+      if (GET_MODE (operands[1]) == DFmode)
+	{
+	  REAL_VALUE_TYPE rv;
+
+	  REAL_VALUE_FROM_CONST_DOUBLE (rv, operands[1]);
+	  REAL_VALUE_TO_TARGET_DOUBLE (rv, val);
+	}
+      else if (GET_MODE (operands[1]) == VOIDmode
+	       || GET_MODE (operands[1]) == DImode)
+	{
+	  val[0] = CONST_DOUBLE_LOW (operands[1]);
+	  val[1] = CONST_DOUBLE_HIGH (operands[1]);
+	}
+      break;
+      
+    default:
+      return false;
+    }
+
+  return val[0] == 0 || val[1] == 0;
 }
Index: gcc/config/mn10300/mn10300.md
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mn10300/mn10300.md,v
retrieving revision 1.44
diff -u -p -r1.44 mn10300.md
--- gcc/config/mn10300/mn10300.md 13 Dec 2002 23:07:47 -0000 1.44
+++ gcc/config/mn10300/mn10300.md 14 Feb 2003 21:34:38 -0000
@@ -1,5 +1,5 @@
 ;; GCC machine description for Matsushita MN10300
-;; Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002
+;; Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003
 ;; Free Software Foundation, Inc.
 ;; Contributed by Jeff Law (law@cygnus.com).
 
@@ -520,7 +520,26 @@
       abort ();
     }
 }"
-  [(set_attr "cc" "none,none,clobber,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit")])
+  [(set (attr "cc")
+	(cond
+	 [
+	 (lt (symbol_ref "which_alternative") (const_int 2)
+	     ) (const_string "none")
+	 (eq (symbol_ref "which_alternative") (const_int 2)
+	     ) (const_string "clobber")
+	 (eq (symbol_ref "which_alternative") (const_int 3)
+	     ) (if_then_else
+		(ne (symbol_ref "rtx_equal_p (operands[0], operands[1])")
+		    (const_int 0)) (const_string "clobber")
+		    (const_string "none_0hit"))
+	 (ior (eq (symbol_ref "which_alternative") (const_int 8))
+	      (eq (symbol_ref "which_alternative") (const_int 9))
+	      ) (if_then_else
+		 (ne (symbol_ref "mn10300_wide_const_load_uses_clr
+				  (operands)")
+		     (const_int 0)) (const_string "clobber")
+		     (const_string "none_0hit"))
+	 ] (const_string "none_0hit")))])
 
 (define_expand "movdf"
   [(set (match_operand:DF 0 "general_operand" "")
@@ -670,7 +689,26 @@
       abort ();
     }
 }"
-  [(set_attr "cc" "none,none,clobber,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit,none_0hit")])
+  [(set (attr "cc")
+	(cond
+	 [
+	 (lt (symbol_ref "which_alternative") (const_int 2)
+	     ) (const_string "none")
+	 (eq (symbol_ref "which_alternative") (const_int 2)
+	     ) (const_string "clobber")
+	 (eq (symbol_ref "which_alternative") (const_int 3)
+	     ) (if_then_else
+		(ne (symbol_ref "rtx_equal_p (operands[0], operands[1])")
+		    (const_int 0)) (const_string "clobber")
+		    (const_string "none_0hit"))
+	 (ior (eq (symbol_ref "which_alternative") (const_int 8))
+	      (eq (symbol_ref "which_alternative") (const_int 9))
+	      ) (if_then_else
+		 (ne (symbol_ref "mn10300_wide_const_load_uses_clr
+				  (operands)")
+		     (const_int 0)) (const_string "clobber")
+		     (const_string "none_0hit"))
+	 ] (const_string "none_0hit")))])
 
 
 
-- 
Alexandre Oliva   Enjoy Guarana', see http://www.ic.unicamp.br/~oliva/
Red Hat GCC Developer                 aoliva@{redhat.com, gcc.gnu.org}
CS PhD student at IC-Unicamp        oliva@{lsd.ic.unicamp.br, gnu.org}
Free Software Evangelist                Professional serial bug killer

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