public inbox for gcc-patches@gcc.gnu.org
 help / color / mirror / Atom feed
* [PATCH] Introduce MODE_SIZE mode attribute
@ 2014-01-03  8:48 Jakub Jelinek
  2014-01-03  9:23 ` Uros Bizjak
  2014-01-03 15:39 ` Joseph S. Myers
  0 siblings, 2 replies; 8+ messages in thread
From: Jakub Jelinek @ 2014-01-03  8:48 UTC (permalink / raw)
  To: Uros Bizjak, Richard Henderson, Kirill Yukhin; +Cc: gcc-patches

Hi!

I've noticed that especially with the AVX512F introduction we use
GET_MODE_SIZE (<MODE>mode) quite heavily in the i386 *.md files, and
the problem with that is GET_MODE_SIZE isn't a compile time constant,
needs to read mode_size array (non-const) at runtime.

This patch attempts to decrease the enormous .text/.rodata growth from AVX512F
introduction a little bit and improve generated code, by making
GET_MODE_SIZE (<MODE>mode) compile time constants, thus all the
GET_MODE_SIZE (<MODE>mode) == 64 and similar tests can fold into
false/true.  The patch saves ~ 110KB of .text (both x86_64 and i686)
and ~ 50KB of .rodata (x86_64) or ~ 27KB of .rodata (i686).

The disadvantage is that the mode attribute duplicates insn-modes.c,
but I guess the listed modes aren't going to change their sizes ever
on this target, and if some mode isn't listed and used in some mode
iterator, one would get syntax errors from insn-*.[ch] and so it wouldn't be
hard to add it.

Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk?

2014-01-03  Jakub Jelinek  <jakub@redhat.com>

	* config/i386/i386.md (MODE_SIZE): New mode attribute.
	(push splitter): Use <P:MODE_SIZE> instead of
	GET_MODE_SIZE (<P:MODE>mode).
	(lea splitter): Use <MODE_SIZE> instead of GET_MODE_SIZE (<MODE>mode).
	(mov -1, reg peephole2): Likewise.
	* config/i386/sse.md (*mov<mode>_internal,
	<sse>_storeu<ssemodesuffix><avxsizesuffix>,
	<sse2_avx_avx512f>_storedqu<mode>, <sse>_andnot<mode>3,
	*<code><mode>3, *andnot<mode>3<mask_name>,
	<mask_codefor><code><mode>3<mask_name>): Likewise.
	* config/i386/subst.md (mask_mode512bit_condition,
	sd_mask_mode512bit_condition): Likewise.

--- gcc/config/i386/i386.md.jj	2013-12-27 19:24:33.000000000 +0100
+++ gcc/config/i386/i386.md	2014-01-02 20:08:16.911851795 +0100
@@ -914,6 +914,20 @@ (define_mode_iterator SWIM248 [(HI "TARG
 (define_mode_iterator DWI [(DI "!TARGET_64BIT")
 			   (TI "TARGET_64BIT")])
 
+;; GET_MODE_SIZE for selected modes.  As GET_MODE_SIZE is not
+;; compile time constant, it is faster to use <MODE_SIZE> than
+;; GET_MODE_SIZE (<MODE>mode).  For XFmode which depends on
+;; command line options just use GET_MODE_SIZE macro.
+(define_mode_attr MODE_SIZE [(QI "1") (HI "2") (SI "4") (DI "8") (TI "16")
+			     (SF "4") (DF "8") (XF "GET_MODE_SIZE (XFmode)")
+			     (V16QI "16") (V32QI "32") (V64QI "64")
+			     (V8HI "16") (V16HI "32") (V32HI "64")
+			     (V4SI "16") (V8SI "32") (V16SI "64")
+			     (V2DI "16") (V4DI "32") (V8DI "64")
+			     (V1TI "16") (V2TI "32") (V4TI "64")
+			     (V2DF "16") (V4DF "32") (V8DF "64")
+			     (V4SF "16") (V8SF "32") (V16SF "64")])
+
 ;; Double word integer modes as mode attribute.
 (define_mode_attr DWI [(QI "HI") (HI "SI") (SI "DI") (DI "TI")])
 (define_mode_attr dwi [(QI "hi") (HI "si") (SI "di") (DI "ti")])
@@ -2734,7 +2748,7 @@ (define_split
   "reload_completed"
   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
    (set (mem:SF (reg:P SP_REG)) (match_dup 1))]
-  "operands[2] = GEN_INT (-GET_MODE_SIZE (<P:MODE>mode));")
+  "operands[2] = GEN_INT (-<P:MODE_SIZE>);")
 
 (define_split
   [(set (match_operand:SF 0 "push_operand")
@@ -5770,7 +5784,7 @@ (define_split
   enum machine_mode mode = <MODE>mode;
   rtx pat;
 
-  if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
+  if (<MODE_SIZE> < GET_MODE_SIZE (SImode))
     { 
       mode = SImode; 
       operands[0] = gen_lowpart (mode, operands[0]);
@@ -17403,7 +17417,7 @@ (define_peephole2
   [(parallel [(set (match_dup 0) (const_int -1))
 	      (clobber (reg:CC FLAGS_REG))])]
 {
-  if (GET_MODE_SIZE (<MODE>mode) < GET_MODE_SIZE (SImode))
+  if (<MODE_SIZE> < GET_MODE_SIZE (SImode))
     operands[0] = gen_lowpart (SImode, operands[0]);
 })
 
--- gcc/config/i386/sse.md.jj	2014-01-01 00:52:56.000000000 +0100
+++ gcc/config/i386/sse.md	2014-01-02 20:11:49.723916127 +0100
@@ -669,7 +669,7 @@ (define_insn "*mov<mode>_internal"
       /* There is no evex-encoded vmov* for sizes smaller than 64-bytes
 	 in avx512f, so we need to use workarounds, to access sse registers
 	 16-31, which are evex-only.  */
-      if (TARGET_AVX512F && GET_MODE_SIZE (<MODE>mode) < 64
+      if (TARGET_AVX512F && <MODE_SIZE> < 64
 	  && ((REG_P (operands[0])
 	       && EXT_REX_SSE_REGNO_P (REGNO (operands[0])))
 	      || (REG_P (operands[1])
@@ -677,18 +677,18 @@ (define_insn "*mov<mode>_internal"
 	{
 	  if (memory_operand (operands[0], <MODE>mode))
 	    {
-	      if (GET_MODE_SIZE (<MODE>mode) == 32)
+	      if (<MODE_SIZE> == 32)
 		return "vextract<shuffletype>64x4\t{$0x0, %g1, %0|%0, %g1, 0x0}";
-	      else if (GET_MODE_SIZE (<MODE>mode) == 16)
+	      else if (<MODE_SIZE> == 16)
 		return "vextract<shuffletype>32x4\t{$0x0, %g1, %0|%0, %g1, 0x0}";
 	      else
 		gcc_unreachable ();
 	    }
 	  else if (memory_operand (operands[1], <MODE>mode))
 	    {
-	      if (GET_MODE_SIZE (<MODE>mode) == 32)
+	      if (<MODE_SIZE> == 32)
 		return "vbroadcast<shuffletype>64x4\t{%1, %g0|%g0, %1}";
-	      else if (GET_MODE_SIZE (<MODE>mode) == 16)
+	      else if (<MODE_SIZE> == 16)
 		return "vbroadcast<shuffletype>32x4\t{%1, %g0|%g0, %1}";
 	      else
 		gcc_unreachable ();
@@ -759,7 +759,7 @@ (define_insn "*mov<mode>_internal"
    (set (attr "mode")
 	(cond [(match_test "TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL")
 		 (const_string "<ssePSmode>")
-	       (and (match_test "GET_MODE_SIZE (<MODE>mode) == 16")
+	       (and (match_test "<MODE_SIZE> == 16")
 		    (and (eq_attr "alternative" "2")
 			 (match_test "TARGET_SSE_TYPELESS_STORES")))
 		 (const_string "<ssePSmode>")
@@ -998,7 +998,7 @@ (define_insn "<sse>_storeu<ssemodesuffix
    (set_attr "ssememalign" "8")
    (set_attr "prefix" "maybe_vex")
    (set (attr "mode")
-        (cond [(and (match_test "GET_MODE_SIZE (<MODE>mode) == 16")
+	(cond [(and (match_test "<MODE_SIZE> == 16")
                     (ior (match_test "TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL")
                          (match_test "TARGET_SSE_TYPELESS_STORES")))
 		 (const_string "<ssePSmode>")
@@ -1127,7 +1127,7 @@ (define_insn "<sse2_avx_avx512f>_storedq
      (const_string "1")))
    (set_attr "prefix" "maybe_vex")
    (set (attr "mode")
-	(cond [(and (match_test "GET_MODE_SIZE (<MODE>mode) == 16")
+	(cond [(and (match_test "<MODE_SIZE> == 16")
 		    (ior (match_test "TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL")
 			 (match_test "TARGET_SSE_TYPELESS_STORES")))
 		 (const_string "<ssePSmode>")
@@ -2363,7 +2363,7 @@ (define_insn "<sse>_andnot<mode>3"
     }
 
   /* There is no vandnp[sd].  Use vpandnq.  */
-  if (GET_MODE_SIZE (<MODE>mode) == 64)
+  if (<MODE_SIZE> == 64)
     {
       suffix = "q";
       ops = "vpandn%s\t{%%2, %%1, %%0|%%0, %%1, %%2}";
@@ -2435,7 +2435,7 @@ (define_insn "*<code><mode>3"
     }
 
   /* There is no v<logic>p[sd].  Use vp<logic>q.  */
-  if (GET_MODE_SIZE (<MODE>mode) == 64)
+  if (<MODE_SIZE> == 64)
     {
       suffix = "q";
       ops = "vp<logic>%s\t{%%2, %%1, %%0|%%0, %%1, %%2}";
@@ -8940,7 +8940,7 @@ (define_insn "*andnot<mode>3<mask_name>"
 		 (const_string "<sseinsnmode>")
 	       (match_test "TARGET_AVX")
 		 (if_then_else
-		   (match_test "GET_MODE_SIZE (<MODE>mode) > 16")
+		   (match_test "<MODE_SIZE> > 16")
 		   (const_string "V8SF")
 		   (const_string "<sseinsnmode>"))
 	       (ior (not (match_test "TARGET_SSE2"))
@@ -9032,7 +9032,7 @@ (define_insn "<mask_codefor><code><mode>
 		 (const_string "<sseinsnmode>")
 	       (match_test "TARGET_AVX")
 		 (if_then_else
-		   (match_test "GET_MODE_SIZE (<MODE>mode) > 16")
+		   (match_test "<MODE_SIZE> > 16")
 		   (const_string "V8SF")
 		   (const_string "<sseinsnmode>"))
 	       (ior (not (match_test "TARGET_SSE2"))
--- gcc/config/i386/subst.md.jj	2014-01-01 00:45:15.000000000 +0100
+++ gcc/config/i386/subst.md	2014-01-02 20:12:17.285791572 +0100
@@ -51,7 +51,7 @@ (define_subst_attr "mask_operand11" "mas
 (define_subst_attr "mask_operand18" "mask" "" "%{%19%}%N18")
 (define_subst_attr "mask_operand19" "mask" "" "%{%20%}%N19")
 (define_subst_attr "mask_codefor" "mask" "*" "")
-(define_subst_attr "mask_mode512bit_condition" "mask" "1" "(GET_MODE_SIZE (<MODE>mode) == 64)")
+(define_subst_attr "mask_mode512bit_condition" "mask" "1" "(<MODE_SIZE> == 64)")
 (define_subst_attr "store_mask_constraint" "mask" "vm" "v")
 (define_subst_attr "store_mask_predicate" "mask" "nonimmediate_operand" "register_operand")
 (define_subst_attr "mask_prefix" "mask" "vex" "evex")
@@ -85,7 +85,7 @@ (define_subst_attr "sd_maskz_name" "sd"
 (define_subst_attr "sd_mask_op4" "sd" "" "%{%5%}%N4")
 (define_subst_attr "sd_mask_op5" "sd" "" "%{%6%}%N5")
 (define_subst_attr "sd_mask_codefor" "sd" "*" "")
-(define_subst_attr "sd_mask_mode512bit_condition" "sd" "1" "(GET_MODE_SIZE (<MODE>mode) == 64)")
+(define_subst_attr "sd_mask_mode512bit_condition" "sd" "1" "(<MODE_SIZE> == 64)")
 
 (define_subst "sd"
  [(set (match_operand:SUBST_V 0)

	Jakub

^ permalink raw reply	[flat|nested] 8+ messages in thread

end of thread, other threads:[~2014-04-18 15:00 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2014-01-03  8:48 [PATCH] Introduce MODE_SIZE mode attribute Jakub Jelinek
2014-01-03  9:23 ` Uros Bizjak
2014-01-03 15:39 ` Joseph S. Myers
2014-01-03 23:38   ` Jakub Jelinek
2014-01-04  2:27     ` Andrew Pinski
2014-01-04  2:30       ` Andrew Pinski
2014-01-06 15:21     ` Jakub Jelinek
2014-04-18 15:20       ` H.J. Lu

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).