Open64 (mfef90, whirl2f, and IR tools)
TAG: version-openad; SVN changeset: 916
|
00001 /* 00002 00003 Copyright (C) 2000, 2001 Silicon Graphics, Inc. All Rights Reserved. 00004 00005 This program is free software; you can redistribute it and/or modify it 00006 under the terms of version 2 of the GNU General Public License as 00007 published by the Free Software Foundation. 00008 00009 This program is distributed in the hope that it would be useful, but 00010 WITHOUT ANY WARRANTY; without even the implied warranty of 00011 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 00012 00013 Further, this software is distributed without any warranty that it is 00014 free of the rightful claim of any third person regarding infringement 00015 or the like. Any license provided herein, whether implied or 00016 otherwise, applies only to this software file. Patent licenses, if 00017 any, provided herein do not apply to combinations of this program with 00018 other software, or any other product whatsoever. 00019 00020 You should have received a copy of the GNU General Public License along 00021 with this program; if not, write the Free Software Foundation, Inc., 59 00022 Temple Place - Suite 330, Boston MA 02111-1307, USA. 00023 00024 Contact information: Silicon Graphics, Inc., 1600 Amphitheatre Pky, 00025 Mountain View, CA 94043, or: 00026 00027 http://www.sgi.com 00028 00029 For further information regarding this notice, see: 00030 00031 http://oss.sgi.com/projects/GenInfo/NoticeExplan 00032 00033 */ 00034 00035 00036 /* Conversion from WHIRL opcode to CG opcode. */ 00037 00038 #ifdef USE_PCH 00039 #include "be_com_pch.h" 00040 #endif /* USE_PCH */ 00041 #pragma hdrstop 00042 #include "defs.h" 00043 #include "errors.h" 00044 #include "util.h" 00045 #include "topcode.h" 00046 #include "targ_isa_properties.h" 00047 #include "wn.h" 00048 #include "opcode.h" 00049 #include "config_targ.h" 00050 #include "config.h" 00051 #include "config_debug.h" 00052 #include "tracing.h" 00053 #include "opt_alias_interface.h" 00054 #include "opt_alias_mgr.h" 00055 #include "betarget.h" 00056 #include "w2op.h" 00057 00058 00059 /* only return machine_ops, TOP_UNDEFINED if not an exact correspondence */ 00060 TOP 00061 WHIRL_To_TOP (WN *wn) 00062 { 00063 OPCODE opcode = WN_opcode(wn); 00064 TOP top; 00065 00066 top = OPCODE_To_TOP (opcode); 00067 00068 /* For TAS WHIRL operators there is no direct translation. We 00069 * have to look at the kids to determine the corresponding TOP. 00070 */ 00071 if (top == TOP_UNDEFINED && OPCODE_operator(opcode) == OPR_TAS) { 00072 top = TAS_To_TOP (wn); 00073 } 00074 return top; 00075 } 00076 00077 00078 /* determines if the TOP can be speculatively executed taking into account 00079 * eagerness level 00080 */ 00081 BOOL TOP_Can_Be_Speculative (TOP opcode) 00082 { 00083 switch (Eager_Level) { 00084 case EAGER_NONE: 00085 00086 /* not allowed to speculate anything 00087 */ 00088 break; 00089 00090 case EAGER_SAFE: 00091 00092 /* Only exception-safe speculative ops are allowed 00093 */ 00094 if (TOP_is_ftrap(opcode) || TOP_is_itrap(opcode)) break; 00095 /*FALLTHROUGH*/ 00096 00097 case EAGER_ARITH: 00098 00099 /* Arithmetic exceptions allowed 00100 */ 00101 if (TOP_is_fdiv(opcode)) break; 00102 /*FALLTHROUGH*/ 00103 00104 case EAGER_DIVIDE: 00105 00106 /* Divide by zero exceptions allowed 00107 */ 00108 if (TOP_is_memtrap(opcode)) break; 00109 /*FALLTHROUGH*/ 00110 00111 case EAGER_MEMORY: 00112 00113 /* Memory exceptions allowed / All speculative ops allowed 00114 */ 00115 if (TOP_is_unsafe(opcode)) break; 00116 return TRUE; 00117 00118 default: 00119 DevWarn("unhandled eagerness level: %d", Eager_Level); 00120 break; 00121 } 00122 00123 return FALSE; 00124 } 00125 00126 00127 /* ==================================================================== 00128 * 00129 * BOOL OPCODE_Can_Be_Speculative(OPCODE opcode) 00130 * 00131 * Determine is the opcode can be executed speculatively, given that 00132 * its children are speculative 00133 * 00134 * Note: 00135 * TOP div (integer) does NOT trap, although -DEBUG:div_check (default) 00136 * inserts a trap to check divide by zero. So we have the strange case 00137 * that OPC_{I,U}{4,8}DIV does trap but the TOP div does not. 00138 * 00139 * ==================================================================== 00140 */ 00141 00142 BOOL OPCODE_Can_Be_Speculative(OPCODE opcode) 00143 { 00144 if (Eager_Level == EAGER_NONE) 00145 return FALSE; 00146 00147 switch(OPCODE_operator(opcode)) 00148 { 00149 case OPR_LDA: 00150 case OPR_CONST: 00151 case OPR_INTCONST: 00152 case OPR_IDNAME: 00153 case OPR_PREFETCH: 00154 case OPR_PREFETCHX: 00155 case OPR_ARRAY: 00156 return EAGER_SAFE <= Eager_Level; 00157 00158 case OPR_ILOAD: 00159 case OPR_ILOADX: 00160 case OPR_MLOAD: 00161 case OPR_LDID: 00162 return EAGER_MEMORY <= Eager_Level; 00163 00164 case OPR_CVT: 00165 case OPR_NEG: 00166 case OPR_ABS: 00167 case OPR_RND: 00168 case OPR_TRUNC: 00169 case OPR_CEIL: 00170 case OPR_FLOOR: 00171 case OPR_MADD: 00172 case OPR_MSUB: 00173 case OPR_NMADD: 00174 case OPR_NMSUB: 00175 if (MTYPE_is_float(OPCODE_rtype(opcode))) 00176 return EAGER_ARITH <= Eager_Level; 00177 return EAGER_SAFE <= Eager_Level; 00178 00179 case OPR_SQRT: 00180 case OPR_DIV: 00181 case OPR_RECIP: 00182 case OPR_RSQRT: 00183 case OPR_REM: 00184 case OPR_DIVREM: 00185 if (MTYPE_is_float(OPCODE_rtype(opcode)) || 00186 DEBUG_Div_Zero_Check) 00187 return EAGER_DIVIDE <= Eager_Level; 00188 return EAGER_SAFE <= Eager_Level; 00189 00190 case OPR_REALPART: 00191 case OPR_IMAGPART: 00192 case OPR_PAREN: 00193 case OPR_LOWPART: 00194 case OPR_HIGHPART: 00195 case OPR_MINMAX: 00196 case OPR_MINPART: 00197 case OPR_MAXPART: 00198 case OPR_COMPLEX: 00199 return EAGER_SAFE <= Eager_Level; 00200 00201 case OPR_BNOT: 00202 case OPR_LNOT: 00203 case OPR_ADD: 00204 case OPR_SUB: 00205 case OPR_MPY: 00206 case OPR_MOD: 00207 case OPR_MAX: 00208 case OPR_MIN: 00209 case OPR_TAS: 00210 case OPR_CVTL: 00211 case OPR_BAND: 00212 case OPR_BIOR: 00213 case OPR_BNOR: 00214 case OPR_BXOR: 00215 case OPR_LAND: 00216 case OPR_LIOR: 00217 case OPR_SHL: 00218 case OPR_ASHR: 00219 case OPR_LSHR: 00220 if (MTYPE_is_float(OPCODE_rtype(opcode))) 00221 return EAGER_DIVIDE <= Eager_Level; 00222 return EAGER_SAFE <= Eager_Level; 00223 00224 case OPR_CAND: 00225 case OPR_CIOR: 00226 case OPR_SELECT: 00227 case OPR_CSELECT: 00228 return EAGER_SAFE <= Eager_Level; 00229 00230 case OPR_EQ: 00231 case OPR_NE: 00232 case OPR_GT: 00233 case OPR_GE: 00234 case OPR_LT: 00235 case OPR_LE: 00236 return EAGER_SAFE <= Eager_Level; 00237 00238 case OPR_INTRINSIC_OP: 00239 return FALSE; 00240 } 00241 return FALSE; 00242 } 00243 00244 00245 /* ==================================================================== 00246 * 00247 * BOOL WN_Can_Be_Speculative (WN *wn, struct ALIAS_MANAGER *alias) 00248 * 00249 * Determine is the wn can be executed speculatively 00250 * This is a close approximation to be/cg/cgtarget.c: CGTAG_Can_Be_Speculative() 00251 * 00252 * 00253 * TODO: 00254 * handle classes of ILOADs 00255 * 00256 * ==================================================================== 00257 */ 00258 BOOL WN_Can_Be_Speculative (WN *wn, struct ALIAS_MANAGER *alias) 00259 { 00260 switch(WN_operator(wn)) 00261 { 00262 case OPR_CONST: 00263 case OPR_INTCONST: 00264 case OPR_LDA: 00265 return TRUE; 00266 00267 case OPR_LDID: 00268 if (WN_class(wn) == CLASS_PREG) 00269 return TRUE; 00270 00271 if (ST_is_constant(WN_st(wn))) 00272 return TRUE; 00273 00274 // fall thru 00275 00276 case OPR_ILOAD: 00277 case OPR_ILOADX: 00278 if (WN_Is_Volatile_Mem(wn)) 00279 return FALSE; 00280 00281 return FALSE; 00282 00283 case OPR_DIV: 00284 TYPE_ID rtype = WN_rtype(wn); 00285 if ((rtype == MTYPE_I4 || rtype == MTYPE_I8 || rtype == MTYPE_U4 00286 || rtype == MTYPE_U8) && WN_operator(WN_kid1(wn)) 00287 == OPR_INTCONST && WN_const_val(wn) != 0) 00288 return TRUE; 00289 00290 } 00291 return OPCODE_Can_Be_Speculative(WN_opcode(wn)); 00292 } 00293 00294 /* ==================================================================== 00295 * 00296 * BOOL WN_Expr_Can_Be_Speculative (WN *wn, struct ALIAS_MANAGER *alias) 00297 * 00298 * Determine if the whirl expression can be executed speculatively 00299 * It can only be speculative if the expression and all its children are speculative 00300 * 00301 * ==================================================================== 00302 */ 00303 BOOL WN_Expr_Can_Be_Speculative (WN *wn, struct ALIAS_MANAGER *alias) 00304 { 00305 INT16 i; 00306 00307 for(i=0; i<WN_kid_count(wn); i++) 00308 { 00309 if (WN_Expr_Can_Be_Speculative(WN_kid(wn,i), alias) == FALSE) 00310 return FALSE; 00311 } 00312 00313 return WN_Can_Be_Speculative(wn, alias); 00314 }