Subject: m68k uninitialized variable warnings (patch)
To: None <port-m68k@netbsd.org, tech-toolchain@netbsd.org>
From: Charles M. Hannum <abuse@spamalicious.com>
List: tech-toolchain
Date: 10/28/2003 18:51:09
--Boundary-00=_dqrn/Azu+T53XeS
Content-Type: text/plain;
  charset="us-ascii"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline

So the problem is thus:

* The {u,}mulsidi3 generate two parallel sets which modify the upper and lower 
halves of the target register.

* life_analysis() does not track subregister modifications -- if you don't 
modify the whole register with a single set, it considers the register 
unused.

The simple, if klugy, solution to this is to stick an explicit clobber in.  It 
seems to work.

While doing this, I noticed that constant folding was not happening for 
32x32->64 multiplies.  This is because the parallel set generated by 
{u,}mulsidi3 cannot be folded at all.  To solve this, I first expand to a 
normal multiply, and then use a define_insn_and_split to convert it to the 
parallel set after CSE and constant folding.

I've built a kernel and libc with these changes, and they seem to work.  The 
rest of my build hasn't finished yet.

--Boundary-00=_dqrn/Azu+T53XeS
Content-Type: text/x-diff;
  charset="us-ascii";
  name="m68k-diff"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
	filename="m68k-diff"

? m68k.md.new
Index: m68k.md
===================================================================
RCS file: /cvsroot/src/gnu/dist/gcc/gcc/config/m68k/m68k.md,v
retrieving revision 1.1.1.1
diff -u -r1.1.1.1 m68k.md
--- m68k.md	23 Jul 2003 02:41:50 -0000	1.1.1.1
+++ m68k.md	28 Oct 2003 18:34:14 -0000
@@ -3118,22 +3118,39 @@
 ;; We need a separate DEFINE_EXPAND for u?mulsidi3 to be able to use the
 ;; proper matching constraint.  This is because the matching is between
 ;; the high-numbered word of the DImode operand[0] and operand[1].
+;;
+;; Note: life_analysis() does not keep track of the individual halves of the
+;; DImode register.  To prevent spurious liveness before the u?mulsidi3 insn
+;; (which causes "uninitialized variable" warnings), we explicitly clobber
+;; the DImode register.
 (define_expand "umulsidi3"
-  [(parallel
-    [(set (subreg:SI (match_operand:DI 0 "register_operand" "") 4)
-	  (mult:SI (match_operand:SI 1 "register_operand" "")
-		   (match_operand:SI 2 "register_operand" "")))
+  [(set (match_operand:DI 0 "register_operand" "")
+	(mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
+		 (zero_extend:DI (match_operand:SI 2 "register_operand" ""))))]
+  "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
+  "")
+
+(define_insn_and_split "*umulsidi3_split"
+  [(set (match_operand:DI 0 "register_operand" "")
+	(mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
+		 (zero_extend:DI (match_operand:SI 2 "register_operand" ""))))]
+  "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
+  "#"
+  "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
+  [(clobber (match_dup 0))
+   (parallel
+    [(set (subreg:SI (match_dup 0) 4)
+	  (mult:SI (match_dup 1) (match_dup 2)))
      (set (subreg:SI (match_dup 0) 0)
 	  (truncate:SI (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
 					     (zero_extend:DI (match_dup 2)))
 				    (const_int 32))))])]
-  "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
   "")
 
 (define_insn ""
   [(set (match_operand:SI 0 "register_operand" "=d")
 	(mult:SI (match_operand:SI 1 "register_operand" "%0")
-		  (match_operand:SI 2 "nonimmediate_operand" "dm")))
+		 (match_operand:SI 2 "nonimmediate_operand" "dm")))
    (set (match_operand:SI 3 "register_operand" "=d")
 	(truncate:SI (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
 					   (zero_extend:DI (match_dup 2)))
@@ -3158,15 +3175,27 @@
   "mulu%.l %2,%3:%0")
 
 (define_expand "mulsidi3"
-  [(parallel
-    [(set (subreg:SI (match_operand:DI 0 "register_operand" "") 4)
-	  (mult:SI (match_operand:SI 1 "register_operand" "")
-		   (match_operand:SI 2 "register_operand" "")))
+  [(set (match_operand:DI 0 "register_operand" "")
+	(mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
+		 (sign_extend:DI (match_operand:SI 2 "register_operand" ""))))]
+  "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
+  "")
+
+(define_insn_and_split "*mulsidi3_split"
+  [(set (match_operand:DI 0 "register_operand" "")
+	(mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
+		 (sign_extend:DI (match_operand:SI 2 "register_operand" ""))))]
+  "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
+  "#"
+  "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
+  [(clobber (match_dup 0))
+   (parallel
+    [(set (subreg:SI (match_dup 0) 4)
+	  (mult:SI (match_dup 1) (match_dup 2)))
      (set (subreg:SI (match_dup 0) 0)
 	  (truncate:SI (lshiftrt:DI (mult:DI (sign_extend:DI (match_dup 1))
 					     (sign_extend:DI (match_dup 2)))
 				    (const_int 32))))])]
-  "TARGET_68020 && !TARGET_68060 && !TARGET_5200"
   "")
 
 (define_insn ""

--Boundary-00=_dqrn/Azu+T53XeS--