[ARM] PR58361 fix failure to conditionalize VFP instruction

Submitted by Richard Earnshaw on Sept. 10, 2013, 5:01 p.m.

Details

Message ID 522F5058.3030601@arm.com
State New
Headers show

Commit Message

Richard Earnshaw Sept. 10, 2013, 5:01 p.m.
PR target/58361 is a wrong code bug where we treat an instruction as
conditional but fail to put the conditional marker on the assembly.
Since the instruction can be correctly executed as a conditional
instruction, the fix is to enable that and to put out the condition code
accordingly.

The particular testcase doesn't trigger on 4.8 or trunk, but the bug is
still there so fixed on all three branches.  A slight variant of the
patch is needed for the release branches due to the changes that have
happened on trunk since the last release was made.  Both versions of the
patch are attached.

	PR target/58361
	* arm/vfp.md (combine_vcvt_f32_<FCVTI32typename>): Fix pattern to
	support conditional execution.
	(combine_vcvt_f64_<FCVTI32typename>): Likewise.

R.
--- vfp.md	(revision 202483)
+++ vfp.md	(local)
@@ -1146,18 +1146,18 @@ (define_insn "*cmpdf_trap_vfp"
    (set_attr "type" "fcmpd")]
 )
 
-;; Fixed point to floating point conversions. 
+;; Fixed point to floating point conversions.
 (define_code_iterator FCVT [unsigned_float float])
 (define_code_attr FCVTI32typename [(unsigned_float "u32") (float "s32")])
 
 (define_insn "*combine_vcvt_f32_<FCVTI32typename>"
   [(set (match_operand:SF 0 "s_register_operand" "=t")
 	(mult:SF (FCVT:SF (match_operand:SI 1 "s_register_operand" "0"))
-		 (match_operand 2 
+		 (match_operand 2
 			"const_double_vcvt_power_of_two_reciprocal" "Dt")))]
   "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP3 && !flag_rounding_math"
-  "vcvt.f32.<FCVTI32typename>\\t%0, %1, %v2"
- [(set_attr "predicable" "no")
+  "vcvt%?.f32.<FCVTI32typename>\\t%0, %1, %v2"
+ [(set_attr "predicable" "yes")
   (set_attr "type" "f_cvt")]
 )
 
@@ -1166,15 +1166,16 @@ (define_insn "*combine_vcvt_f32_<FCVTI32
 (define_insn "*combine_vcvt_f64_<FCVTI32typename>"
   [(set (match_operand:DF 0 "s_register_operand" "=x,x,w")
 	(mult:DF (FCVT:DF (match_operand:SI 1 "s_register_operand" "r,t,r"))
-		 (match_operand 2 
+		 (match_operand 2
 		     "const_double_vcvt_power_of_two_reciprocal" "Dt,Dt,Dt")))]
-  "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP3 && !flag_rounding_math 
+  "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP3 && !flag_rounding_math
   && !TARGET_VFP_SINGLE"
   "@
-  vmov.f32\\t%0, %1\;vcvt.f64.<FCVTI32typename>\\t%P0, %P0, %v2
-  vmov.f32\\t%0, %1\;vcvt.f64.<FCVTI32typename>\\t%P0, %P0, %v2
-  vmov.f64\\t%P0, %1, %1\;vcvt.f64.<FCVTI32typename>\\t%P0, %P0, %v2"
- [(set_attr "predicable" "no")
+  vmov%?.f32\\t%0, %1\;vcvt%?.f64.<FCVTI32typename>\\t%P0, %P0, %v2
+  vmov%?.f32\\t%0, %1\;vcvt%?.f64.<FCVTI32typename>\\t%P0, %P0, %v2
+  vmov%?.f64\\t%P0, %1, %1\;vcvt%?.f64.<FCVTI32typename>\\t%P0, %P0, %v2"
+ [(set_attr "predicable" "yes")
+  (set_attr "ce_count" "2")
   (set_attr "type" "f_cvt")
   (set_attr "length" "8")]
 )

Patch hide | download patch | download mbox

--- vfp.md	(revision 202355)
+++ vfp.md	(local)
@@ -1217,19 +1217,20 @@  (define_insn "*cmpdf_trap_vfp"
    (set_attr "type" "fcmpd")]
 )
 
-;; Fixed point to floating point conversions. 
+;; Fixed point to floating point conversions.
 (define_code_iterator FCVT [unsigned_float float])
 (define_code_attr FCVTI32typename [(unsigned_float "u32") (float "s32")])
 
 (define_insn "*combine_vcvt_f32_<FCVTI32typename>"
   [(set (match_operand:SF 0 "s_register_operand" "=t")
 	(mult:SF (FCVT:SF (match_operand:SI 1 "s_register_operand" "0"))
-		 (match_operand 2 
+		 (match_operand 2
 			"const_double_vcvt_power_of_two_reciprocal" "Dt")))]
   "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP3 && !flag_rounding_math"
-  "vcvt.f32.<FCVTI32typename>\\t%0, %1, %v2"
- [(set_attr "predicable" "no")
-  (set_attr "type" "f_cvti2f")]
+  "vcvt%?.f32.<FCVTI32typename>\\t%0, %1, %v2"
+  [(set_attr "predicable" "yes")
+   (set_attr "predicable_short_it" "no")
+   (set_attr "type" "f_cvti2f")]
 )
 
 ;; Not the ideal way of implementing this. Ideally we would be able to split
@@ -1237,17 +1238,19 @@  (define_insn "*combine_vcvt_f32_<FCVTI32
 (define_insn "*combine_vcvt_f64_<FCVTI32typename>"
   [(set (match_operand:DF 0 "s_register_operand" "=x,x,w")
 	(mult:DF (FCVT:DF (match_operand:SI 1 "s_register_operand" "r,t,r"))
-		 (match_operand 2 
+		 (match_operand 2
 		     "const_double_vcvt_power_of_two_reciprocal" "Dt,Dt,Dt")))]
-  "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP3 && !flag_rounding_math 
+  "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP3 && !flag_rounding_math
   && !TARGET_VFP_SINGLE"
   "@
-  vmov.f32\\t%0, %1\;vcvt.f64.<FCVTI32typename>\\t%P0, %P0, %v2
-  vmov.f32\\t%0, %1\;vcvt.f64.<FCVTI32typename>\\t%P0, %P0, %v2
-  vmov.f64\\t%P0, %1, %1\;vcvt.f64.<FCVTI32typename>\\t%P0, %P0, %v2"
- [(set_attr "predicable" "no")
-  (set_attr "type" "f_cvti2f")
-  (set_attr "length" "8")]
+  vmov%?.f32\\t%0, %1\;vcvt%?.f64.<FCVTI32typename>\\t%P0, %P0, %v2
+  vmov%?.f32\\t%0, %1\;vcvt%?.f64.<FCVTI32typename>\\t%P0, %P0, %v2
+  vmov%?.f64\\t%P0, %1, %1\;vcvt%?.f64.<FCVTI32typename>\\t%P0, %P0, %v2"
+  [(set_attr "predicable" "yes")
+   (set_attr "ce_count" "2")
+   (set_attr "predicable_short_it" "no")
+   (set_attr "type" "f_cvti2f")
+   (set_attr "length" "8")]
 )
 
 ;; Store multiple insn used in function prologue.