[PATCH] middle end, s390: optimization for builtin isnormal

Wolfgang Gellerich gellerich@de.ibm.com
Tue Aug 7 13:47:00 GMT 2007


This patch introduces the optab framework for an insn implementing builtin
function isnormal, and it provides such an insn for s390 to exploit the s390
test data class instruction.

With best regards,

  Wolfgang Gellerich


---
Dr. Wolfgang Gellerich
IBM Deutschland Entwicklung GmbH
Schönaicher Strasse 220
71032 Böblingen, Germany
Tel. +49 / 7031 / 162598
gellerich@de.ibm.com

=======================

IBM Deutschland Entwicklung GmbH
Vorsitzender des Aufsichtsrats: Johann Weihen 
Geschäftsführung: Herbert Kircher 
Sitz der Gesellschaft: Böblingen
Registergericht: Amtsgericht Stuttgart, HRB 243294

----------------------------------------------------------------------------------

Changelog:

2007-06-07  Wolfgang Gellerich  <gellerich@de.ibm.com>

	* optabs.h: Added declaration for isnormal_optab.  
	* optabs.c: (init_optabs): Added initialization for isnormal_optab.
	* genoptinit.c (optabs): Added entry for isnormal insns.  
	* builtins.c (expand_builtin_interclass_mathfn): Added code to use the
	  isnormal insn.
	* config/s390/s390.h (S390_TDC_NORMALIZED): New constant.  
	* config/s390/s390.md (isnormal<mode>2): New expander.  

----------------------------------------------------------------------------------


Index: gcc/optabs.c
===================================================================
--- gcc/optabs.c	(Revision 127180)
+++ gcc/optabs.c	(Arbeitskopie)
@@ -5605,6 +5605,7 @@
   signbit_optab = init_optab (UNKNOWN);
 
   isinf_optab = init_optab (UNKNOWN);
+  isnormal_optab = init_optab (UNKNOWN);
 
   strlen_optab = init_optab (UNKNOWN);
   cbranch_optab = init_optab (UNKNOWN);
Index: gcc/optabs.h
===================================================================
--- gcc/optabs.h	(Revision 127180)
+++ gcc/optabs.h	(Arbeitskopie)
@@ -222,6 +222,8 @@
   OTI_signbit,
   /* Test for infinite value */
   OTI_isinf,
+  /* Test for normalized value */
+  OTI_isnormal,
 
   /* Compare insn; two operands.  */
   OTI_cmp,
@@ -411,6 +413,7 @@
 #define copysign_optab (optab_table[OTI_copysign])
 #define signbit_optab (optab_table[OTI_signbit])
 #define isinf_optab (optab_table[OTI_isinf])
+#define isnormal_optab (optab_table[OTI_isnormal])
 
 #define cmp_optab (optab_table[OTI_cmp])
 #define ucmp_optab (optab_table[OTI_ucmp])
Index: gcc/genopinit.c
===================================================================
--- gcc/genopinit.c	(Revision 127180)
+++ gcc/genopinit.c	(Arbeitskopie)
@@ -123,6 +123,7 @@
   "copysign_optab->handlers[$A].insn_code = CODE_FOR_$(copysign$F$a3$)",
   "signbit_optab->handlers[$A].insn_code = CODE_FOR_$(signbit$F$a2$)",
   "isinf_optab->handlers[$A].insn_code = CODE_FOR_$(isinf$a2$)",
+  "isnormal_optab->handlers[$A].insn_code = CODE_FOR_$(isnormal$a2$)",
   "sqrt_optab->handlers[$A].insn_code = CODE_FOR_$(sqrt$a2$)",
   "floor_optab->handlers[$A].insn_code = CODE_FOR_$(floor$a2$)",
   "lfloor_optab->handlers[$B][$A].insn_code = CODE_FOR_$(lfloor$F$a$I$b2$)",
Index: gcc/builtins.c
===================================================================
--- gcc/builtins.c	(Revision 127180)
+++ gcc/builtins.c	(Arbeitskopie)
@@ -2225,6 +2225,7 @@
     CASE_FLT_FN (BUILT_IN_ISINF):
       builtin_optab = isinf_optab; break;
     case BUILT_IN_ISNORMAL:
+      builtin_optab = isnormal_optab; break;
     case BUILT_IN_ISFINITE:
     CASE_FLT_FN (BUILT_IN_FINITE):
       /* These builtins have no optabs (yet).  */
Index: gcc/config/s390/s390.h
===================================================================
--- gcc/config/s390/s390.h	(Revision 127180)
+++ gcc/config/s390/s390.h	(Arbeitskopie)
@@ -165,6 +165,9 @@
 #define S390_TDC_INFINITY (S390_TDC_POSITIVE_INFINITY \
 			  | S390_TDC_NEGATIVE_INFINITY )
 
+#define S390_TDC_NORMALIZED (S390_TDC_POSITIVE_NORMALIZED_NUMBER \
+                          | S390_TDC_NEGATIVE_NORMALIZED_NUMBER)
+
 /* In libgcc2, determine target settings as compile-time constants.  */
 #ifdef IN_LIBGCC2
 #undef TARGET_64BIT
@@ -944,5 +947,4 @@
 #define DISP_IN_RANGE(d) \
   (TARGET_LONG_DISPLACEMENT? ((d) >= -524288 && (d) <= 524287) \
                            : ((d) >= 0 && (d) <= 4095))
-
 #endif
Index: gcc/config/s390/s390.md
===================================================================
--- gcc/config/s390/s390.md	(Revision 127180)
+++ gcc/config/s390/s390.md	(Arbeitskopie)
@@ -2331,6 +2331,18 @@
   operands[2] = GEN_INT (S390_TDC_INFINITY);
 })
 
+(define_expand "isnormal<mode>2"
+  [(set (reg:CCZ CC_REGNUM)
+        (unspec:CCZ [(match_operand:BFP 1 "register_operand" "f") 
+                     (match_dup 2)] 
+                     UNSPEC_TDC_INSN))
+   (set (match_operand:SI 0 "register_operand" "=d")
+        (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CCZ_TO_INT))]
+  "TARGET_HARD_FLOAT"
+{
+  operands[2] = GEN_INT (S390_TDC_NORMALIZED);
+})
+
 ; This insn is used to generate all variants of the Test Data Class
 ; instruction, namely tcxb, tcdb, and tceb.  The insn's first operand
 ; is the register to be tested and the second one is the bit mask



More information about the Gcc-patches mailing list