00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042 #include "defs.h"
00043 #include "erglob.h"
00044 #include "ercg.h"
00045 #include "tracing.h"
00046 #include "config.h"
00047 #include "config_targ_opt.h"
00048 #include "tn.h"
00049 #include "cg_flags.h"
00050 #include "op.h"
00051 #include "cgexp.h"
00052 #include "cgexp_internals.h"
00053
00054 extern OPS New_OPs;
00055 extern OP * Last_Processed_OP;
00056 extern INT total_bb_insts;
00057 extern BB * Cur_BB;
00058
00059 extern INT64 Get_TN_Value(TN * tn);
00060 extern TN * Get_64Bit_High_TN(TN * low, TYPE_ID type, OPS * ops);
00061 extern void Process_New_OPs(void);
00062
00063 void
00064 Initialize_Branch_Variants(void)
00065 {
00066
00067 }
00068
00069 BOOL
00070 Cond_Is_64Bit(VARIANT cond)
00071 {
00072 const int COND_OP[] = {
00073 V_BR_I8EQ0, V_BR_I8NE0, V_BR_I8GT0, V_BR_I8GE0, V_BR_I8LT0, V_BR_I8LE0,
00074 V_BR_I8EQ, V_BR_I8NE, V_BR_I8GT, V_BR_I8GE, V_BR_I8LT, V_BR_I8LE,
00075 V_BR_U8EQ0, V_BR_U8NE0, V_BR_U8GT0, V_BR_U8GE0, V_BR_U8LT0, V_BR_U8LE0,
00076 V_BR_U8EQ, V_BR_U8NE, V_BR_U8GT, V_BR_U8GE, V_BR_U8LT, V_BR_U8LE};
00077
00078 for (int i = 0; i < sizeof(COND_OP) / sizeof(COND_OP[0]); i++) {
00079 if (cond == COND_OP[i]) return TRUE;
00080 }
00081
00082 return FALSE;
00083 }
00084
00085 BOOL
00086 Cond_Is_Unsigned(VARIANT cond)
00087 {
00088 const int UNSIGNED_COND_OP[] = {
00089 V_BR_U4EQ0, V_BR_U4NE0, V_BR_U4GT0, V_BR_U4GE0, V_BR_U4LT0, V_BR_U4LE0,
00090 V_BR_U4EQ, V_BR_U4NE, V_BR_U4GT, V_BR_U4GE, V_BR_U4LT, V_BR_U4LE,
00091 V_BR_U8EQ0, V_BR_U8NE0, V_BR_U8GT0, V_BR_U8GE0, V_BR_U8LT0, V_BR_U8LE0,
00092 V_BR_U8EQ, V_BR_U8NE, V_BR_U8GT, V_BR_U8GE, V_BR_U8LT, V_BR_U8LE
00093 };
00094
00095 const int SIGNED_COND_OP[] = {
00096 V_BR_I4EQ0, V_BR_I4NE0, V_BR_I4GT0, V_BR_I4GE0, V_BR_I4LT0, V_BR_I4LE0,
00097 V_BR_I4EQ, V_BR_I4NE, V_BR_I4GT, V_BR_I4GE, V_BR_I4LT, V_BR_I4LE,
00098 V_BR_I8EQ0, V_BR_I8NE0, V_BR_I8GT0, V_BR_I8GE0, V_BR_I8LT0, V_BR_I8LE0,
00099 V_BR_I8EQ, V_BR_I8NE, V_BR_I8GT, V_BR_I8GE, V_BR_I8LT, V_BR_I8LE
00100 };
00101
00102 for (int i = 0; i < sizeof(UNSIGNED_COND_OP) / sizeof(UNSIGNED_COND_OP[0]); i++) {
00103 if (cond == UNSIGNED_COND_OP[i]) return TRUE;
00104 }
00105
00106 for (int i = 0; i < sizeof(SIGNED_COND_OP) / sizeof(SIGNED_COND_OP[0]); i++) {
00107 if (cond == SIGNED_COND_OP[i]) return FALSE;
00108 }
00109
00110 FmtAssert(FALSE, ("Cond_Is_Unsigned: Branch cond NYI"));
00111 return FALSE;
00112 }
00113
00114 void
00115 Expand_64Bit_Branch(TN* targ, TN* src1, TN* src2, VARIANT variant, OPS *ops)
00116 {
00117 TN * src1_low = src1;
00118 TN * src1_high = Get_TN_Pair(src1);
00119 TN * src2_low = src2;
00120 TN * src2_high = Get_TN_Pair(src2);
00121
00122 if (TN_has_value(src1)) {
00123 Expand_64Bit_Branch(targ, src2, src1, Invert_BR_Variant(variant), ops);
00124 return;
00125 }
00126
00127 VARIANT cond = V_br_condition(variant);
00128
00129 if (src1_high == NULL) {
00130 src1_high = Get_64Bit_High_TN(src1_low, Cond_Is_Unsigned(cond) ?
00131 MTYPE_U8 : MTYPE_I8, ops);
00132 }
00133
00134 if (TN_is_register(src2) && (src2_high == NULL)) {
00135 src2_high = Get_64Bit_High_TN(src2_low, Cond_Is_Unsigned(cond) ?
00136 MTYPE_U8 : MTYPE_I8, ops);
00137 } else if (TN_has_value(src2)) {
00138 INT64 val = Get_TN_Value(src2);
00139 INT32 val_high = (val >> 32);
00140 UINT32 val_low = val & 0XFFFFFFFF;
00141 src2_high = Gen_Literal_TN(val_high, 4);
00142 src2_low = Gen_Literal_TN(val_low, 4);
00143 }
00144
00145 FmtAssert((src2_high != NULL) && (src1_high != NULL), ("Expand_64Bit_Branch src2_high/src1_high is NULL"));
00146
00147 if (cond == V_BR_I8EQ || cond == V_BR_U8EQ) {
00148 BB* bb_entry = Cur_BB;
00149 BB* bb_cmp_low = Gen_And_Append_BB(bb_entry);
00150 BB* bb_exit = Gen_And_Append_BB(bb_cmp_low);
00151
00152 LABEL_IDX label_bb_exit = Gen_Label_For_BB(bb_exit);
00153 BB_branch_wn(bb_entry) = WN_Create(OPC_TRUEBR,1);
00154 WN_kid0(BB_branch_wn(bb_entry)) = NULL;
00155 WN_label_number(BB_branch_wn(bb_entry)) = label_bb_exit;
00156
00157 Expand_Branch(Gen_Label_TN(label_bb_exit, 0), src1_high, src2_high,
00158 cond == V_BR_I8EQ ? V_BR_I4NE : V_BR_U4NE, ops);
00159
00160 if( ops != &New_OPs )
00161 OPS_Append_Ops(&New_OPs, ops);
00162
00163 Process_New_OPs();
00164 BB_Append_Ops(bb_entry, &New_OPs);
00165 OPS_Init(&New_OPs);
00166 OPS_Init(ops);
00167
00168 BB_branch_wn(bb_cmp_low) = WN_Create(OPC_TRUEBR,1);
00169 WN_kid0(BB_branch_wn(bb_cmp_low)) = NULL;
00170 WN_label_number(BB_branch_wn(bb_cmp_low)) = TN_label(targ);
00171
00172 OPS* bb_cmp_low_ops = &New_OPs;
00173
00174 Expand_Branch(targ, src1_low, src2_low, V_BR_U4EQ, bb_cmp_low_ops);
00175
00176 total_bb_insts = 0;
00177 Last_Processed_OP = NULL;
00178 Process_New_OPs();
00179 BB_Append_Ops(bb_cmp_low, bb_cmp_low_ops);
00180 OPS_Init(bb_cmp_low_ops);
00181
00182 total_bb_insts = 0;
00183 Last_Processed_OP = NULL;
00184 Process_New_OPs();
00185 OPS_Init(&New_OPs);
00186
00187 Cur_BB = bb_exit;
00188 return;
00189 }
00190 if (cond == V_BR_I8NE || cond == V_BR_U8NE) {
00191 BB* bb_entry = Cur_BB;
00192 BB* bb_cmp_low = Gen_And_Append_BB(bb_entry);
00193 BB* bb_exit = Gen_And_Append_BB(bb_cmp_low);
00194 LABEL_IDX label_bb_exit = Gen_Label_For_BB(bb_exit);
00195
00196 BB_branch_wn(bb_entry) = WN_Create(OPC_TRUEBR,1);
00197 WN_kid0(BB_branch_wn(bb_entry)) = NULL;
00198 WN_label_number(BB_branch_wn(bb_entry)) = TN_label(targ);
00199
00200 Expand_Branch(targ, src1_high, src2_high,
00201 cond == V_BR_I8NE ? V_BR_I4NE : V_BR_U4NE, ops);
00202
00203 if( ops != &New_OPs )
00204 OPS_Append_Ops(&New_OPs, ops);
00205
00206 Process_New_OPs();
00207 BB_Append_Ops(bb_entry, &New_OPs);
00208 OPS_Init(&New_OPs);
00209 OPS_Init(ops);
00210
00211 BB_branch_wn(bb_cmp_low) = WN_Create(OPC_TRUEBR,1);
00212 WN_kid0(BB_branch_wn(bb_cmp_low)) = NULL;
00213 WN_label_number(BB_branch_wn(bb_cmp_low)) = TN_label(targ);
00214
00215 OPS* bb_cmp_low_ops = &New_OPs;
00216
00217 Expand_Branch(targ, src1_low, src2_low, V_BR_U4NE, bb_cmp_low_ops);
00218
00219 total_bb_insts = 0;
00220 Last_Processed_OP = NULL;
00221 Process_New_OPs();
00222 BB_Append_Ops(bb_cmp_low, bb_cmp_low_ops);
00223 OPS_Init(bb_cmp_low_ops);
00224
00225 total_bb_insts = 0;
00226 Last_Processed_OP = NULL;
00227 Process_New_OPs();
00228 OPS_Init(&New_OPs);
00229
00230 Cur_BB = bb_exit;
00231 return;
00232 }
00233
00234 VARIANT br1_cond, br2_cond, br3_cond;
00235 switch (cond) {
00236 case V_BR_I8GT:
00237 br1_cond = V_BR_I4GT;
00238 br2_cond = V_BR_I4LT;
00239 br3_cond = V_BR_U4GT;
00240 break;
00241 case V_BR_U8GT:
00242 br1_cond = V_BR_U4GT;
00243 br2_cond = V_BR_U4LT;
00244 br3_cond = V_BR_U4GT;
00245 break;
00246 case V_BR_I8GE:
00247 br1_cond = V_BR_I4GT;
00248 br2_cond = V_BR_I4LT;
00249 br3_cond = V_BR_U4GE;
00250 break;
00251 case V_BR_U8GE:
00252 br1_cond = V_BR_U4GT;
00253 br2_cond = V_BR_U4LT;
00254 br3_cond = V_BR_U4GE;
00255 break;
00256 case V_BR_I8LE:
00257 br1_cond = V_BR_I4LT;
00258 br2_cond = V_BR_I4GT;
00259 br3_cond = V_BR_U4LE;
00260 break;
00261 case V_BR_U8LE:
00262 br1_cond = V_BR_U4LT;
00263 br2_cond = V_BR_U4GT;
00264 br3_cond = V_BR_U4LE;
00265 break;
00266 case V_BR_I8LT:
00267 br1_cond = V_BR_I4LT;
00268 br2_cond = V_BR_I4GT;
00269 br3_cond = V_BR_U4LT;
00270 break;
00271 case V_BR_U8LT:
00272 br1_cond = V_BR_U4LT;
00273 br2_cond = V_BR_U4GT;
00274 br3_cond = V_BR_U4LT;
00275 break;
00276 default:
00277 FmtAssert(FALSE, ("unknown condition in Expand_64Bit_Branch"));
00278 }
00279
00280 BB* bb_entry = Cur_BB;
00281 BB* bb_cmp_high = Gen_And_Append_BB(bb_entry);
00282 BB* bb_cmp_low = Gen_And_Append_BB(bb_cmp_high);
00283 BB* bb_exit = Gen_And_Append_BB(bb_cmp_low);
00284 LABEL_IDX label_bb_exit = Gen_Label_For_BB(bb_exit);
00285
00286 BB_branch_wn(bb_entry) = WN_Create(OPC_TRUEBR,1);
00287 WN_kid0(BB_branch_wn(bb_entry)) = NULL;
00288 WN_label_number(BB_branch_wn(bb_entry)) = TN_label(targ);
00289
00290 Expand_Branch(targ, src1_high, src2_high, br1_cond, ops);
00291
00292 if( ops != &New_OPs )
00293 OPS_Append_Ops(&New_OPs, ops);
00294
00295 Process_New_OPs();
00296 BB_Append_Ops(bb_entry, &New_OPs);
00297 OPS_Init(&New_OPs);
00298 OPS_Init(ops);
00299
00300 BB_branch_wn(bb_cmp_high) = WN_Create(OPC_TRUEBR,1);
00301 WN_kid0(BB_branch_wn(bb_cmp_high)) = NULL;
00302 WN_label_number(BB_branch_wn(bb_cmp_high)) = label_bb_exit;
00303
00304 OPS* bb_cmp_high_ops = &New_OPs;
00305 Expand_Branch(Gen_Label_TN(label_bb_exit, 0), src1_high, src2_high, br2_cond, bb_cmp_high_ops);
00306
00307 total_bb_insts = 0;
00308 Last_Processed_OP = NULL;
00309 Process_New_OPs();
00310 BB_Append_Ops(bb_cmp_high, bb_cmp_high_ops);
00311 OPS_Init(bb_cmp_high_ops);
00312
00313 BB_branch_wn(bb_cmp_low) = WN_Create(OPC_TRUEBR,1);
00314 WN_kid0(BB_branch_wn(bb_cmp_low)) = NULL;
00315 WN_label_number(BB_branch_wn(bb_cmp_low)) = TN_label(targ);
00316
00317 OPS* bb_cmp_low_ops = &New_OPs;
00318
00319 Expand_Branch(targ, src1_low, src2_low, br3_cond, bb_cmp_low_ops);
00320
00321 total_bb_insts = 0;
00322 Last_Processed_OP = NULL;
00323 Process_New_OPs();
00324 BB_Append_Ops(bb_cmp_low, bb_cmp_low_ops);
00325 OPS_Init(bb_cmp_low_ops);
00326
00327 total_bb_insts = 0;
00328 Last_Processed_OP = NULL;
00329 Process_New_OPs();
00330 OPS_Init(&New_OPs);
00331
00332 Cur_BB = bb_exit;
00333 }
00334
00335
00336
00337
00338 TOP
00339 Pick_Compare_TOP (VARIANT *variant, TN **src1, TN **src2, OPS *ops)
00340 {
00341 TOP cmp = TOP_UNDEFINED;
00342 TOP cmp_i = TOP_UNDEFINED;
00343 int val;
00344
00345 if (*src1 != NULL && TN_has_value(*src1)) {
00346
00347 TN *tmp = *src1;
00348 *src1 = *src2;
00349 *src2 = tmp;
00350 *variant = Invert_BR_Variant(*variant);
00351 }
00352
00353 if (*src2 != NULL && TN_is_zero(*src2)) {
00354 switch (*variant) {
00355 case V_BR_U8LT:
00356 case V_BR_U4LT:
00357 *variant = V_BR_NEVER; break;
00358 case V_BR_U8GE:
00359 case V_BR_U4GE:
00360 *variant = V_BR_ALWAYS; break;
00361
00362 case V_BR_U4LE:
00363 *variant = V_BR_U4EQ; break;
00364
00365 case V_BR_U8LE:
00366 *variant = V_BR_U8EQ; break;
00367 }
00368 }
00369
00370
00371 switch (*variant) {
00372 case V_BR_I8EQ:
00373 case V_BR_U8EQ:
00374 case V_BR_I8NE:
00375 case V_BR_U8NE:
00376 case V_BR_I4EQ:
00377 case V_BR_U4EQ:
00378 case V_BR_I4NE:
00379 case V_BR_U4NE:
00380 break;
00381
00382 case V_BR_I8LT:
00383 case V_BR_I4LT:
00384 cmp_i = TOP_slti; cmp = TOP_slt;
00385 break;
00386 case V_BR_U8LT:
00387 case V_BR_U4LT:
00388 cmp_i = TOP_sltiu; cmp = TOP_sltu;
00389 break;
00390
00391 case V_BR_I8GE:
00392 case V_BR_I4GE:
00393 cmp_i = TOP_slti; cmp = TOP_slt;
00394 break;
00395 case V_BR_U8GE:
00396 case V_BR_U4GE:
00397 cmp_i = TOP_sltiu; cmp = TOP_sltu;
00398 break;
00399
00400 case V_BR_I8GT:
00401 case V_BR_I4GT:
00402 if (TN_has_value(*src2)) {
00403 val = TN_value(*src2);
00404 *src2 = Gen_Literal_TN(val+1, TN_size(*src2));
00405 cmp_i = TOP_slti; cmp = TOP_slt;
00406 *variant = (*variant == V_BR_I8GT) ? V_BR_I8GE : V_BR_I4GE;
00407 }
00408 else {
00409 TN *tmp = *src1;
00410 *src1 = *src2;
00411 *src2 = tmp;
00412 *variant = Invert_BR_Variant(*variant);
00413 cmp_i = TOP_slti; cmp = TOP_slt;
00414 }
00415 break;
00416 case V_BR_U8GT:
00417 case V_BR_U4GT:
00418 if (TN_has_value(*src2)) {
00419 val = TN_value(*src2);
00420 if (val == -1) {
00421 *variant = V_BR_NEVER;
00422 break;
00423 }
00424 *src2 = Gen_Literal_TN(val+1, TN_size(*src2));
00425 cmp_i = TOP_sltiu; cmp = TOP_sltu;
00426 *variant = (*variant == V_BR_U8GT) ? V_BR_U8GE : V_BR_U4GE;
00427 }
00428 else {
00429 TN *tmp = *src1;
00430 *src1 = *src2;
00431 *src2 = tmp;
00432 *variant = Invert_BR_Variant(*variant);
00433 cmp_i = TOP_sltiu; cmp = TOP_sltu;
00434 }
00435 break;
00436
00437 case V_BR_I8LE:
00438 case V_BR_I4LE:
00439 if (TN_has_value(*src2)) {
00440 val = TN_value(*src2);
00441 *src2 = Gen_Literal_TN(val+1, TN_size(*src2));
00442 cmp_i = TOP_slti; cmp = TOP_slt;
00443 *variant = (*variant == V_BR_I8LE) ? V_BR_I8LT : V_BR_I4LT;
00444 }
00445 else {
00446 TN *tmp = *src1;
00447 *src1 = *src2;
00448 *src2 = tmp;
00449 *variant = Invert_BR_Variant(*variant);
00450 cmp_i = TOP_slti; cmp = TOP_slt;
00451 }
00452 break;
00453 case V_BR_U8LE:
00454 case V_BR_U4LE:
00455 if (TN_has_value(*src2)) {
00456 val = TN_value(*src2);
00457 if (val == -1) {
00458 *variant = V_BR_ALWAYS;
00459 break;
00460 }
00461 *src2 = Gen_Literal_TN(val+1, TN_size(*src2));
00462 cmp_i = TOP_sltiu; cmp = TOP_sltu;
00463 *variant = (*variant == V_BR_U8LE) ? V_BR_U8LT : V_BR_U4LT;
00464 }
00465 else {
00466 TN *tmp = *src1;
00467 *src1 = *src2;
00468 *src2 = tmp;
00469 *variant = Invert_BR_Variant(*variant);
00470 cmp_i = TOP_sltiu; cmp = TOP_sltu;
00471 }
00472 break;
00473
00474 case V_BR_FEQ: cmp = TOP_c_eq_s; break;
00475 case V_BR_DEQ: cmp = TOP_c_eq_d; break;
00476 #if defined(TARG_SL)
00477 case V_BR_FLT: cmp = TOP_c_olt_s; break;
00478 #else
00479 case V_BR_FLT: cmp = TOP_c_lt_s; break;
00480 #endif
00481 case V_BR_DLT: cmp = TOP_c_lt_d; break;
00482 #if defined(TARG_SL)
00483 case V_BR_FLE: cmp = TOP_c_ole_s; break;
00484 #else
00485 case V_BR_FLE: cmp = TOP_c_le_s; break;
00486 #endif
00487 case V_BR_DLE: cmp = TOP_c_le_d; break;
00488 case V_BR_FNE: cmp = TOP_c_neq_s; break;
00489 case V_BR_DNE: cmp = TOP_c_neq_d; break;
00490 case V_BR_FGT:
00491 {
00492 TN *tmp = *src1;
00493 *src1 = *src2;
00494 *src2 = tmp;
00495 *variant = Invert_BR_Variant(*variant);
00496 #if defined(TARG_SL)
00497 cmp = TOP_c_olt_s;
00498 #else
00499 cmp = TOP_c_lt_s;
00500 #endif
00501 break;
00502 }
00503 case V_BR_DGT:
00504 {
00505 TN *tmp = *src1;
00506 *src1 = *src2;
00507 *src2 = tmp;
00508 *variant = Invert_BR_Variant(*variant);
00509 cmp = TOP_c_lt_d;
00510 break;
00511 }
00512 case V_BR_FGE:
00513 {
00514 TN *tmp = *src1;
00515 *src1 = *src2;
00516 *src2 = tmp;
00517 *variant = Invert_BR_Variant(*variant);
00518 #if defined(TARG_SL)
00519 cmp = TOP_c_ole_s; break;
00520 #else
00521 cmp = TOP_c_le_s; break;
00522 #endif
00523 }
00524 case V_BR_DGE:
00525 {
00526 TN *tmp = *src1;
00527 *src1 = *src2;
00528 *src2 = tmp;
00529 *variant = Invert_BR_Variant(*variant);
00530 cmp = TOP_c_le_d; break;
00531 }
00532 default: ;
00533 }
00534
00535
00536
00537
00538 if (*src2 == NULL)
00539 return TOP_UNDEFINED;
00540
00541
00542 if (TN_has_value(*src2)) {
00543 if (cmp_i != TOP_UNDEFINED &&
00544 ISA_LC_Value_In_Class(TN_value(*src2), LC_simm16))
00545 cmp = cmp_i;
00546 else
00547 *src2 = Expand_Immediate_Into_Register(*src2, TN_size(*src1) == 8, ops);
00548 }
00549
00550 return cmp;
00551 }
00552
00553 void
00554 Expand_Branch ( TN *targ, TN *src1, TN *src2, VARIANT variant, OPS *ops)
00555 {
00556 TOP cmp;
00557 BOOL false_br = V_false_br(variant);
00558 VARIANT cond = V_br_condition(variant);
00559
00560
00561 if ( Trace_Exp2 ) {
00562 fprintf ( TFile, "<cgexp> Translating %s branch:\n",
00563 (false_br ? "false" : "true") );
00564 }
00565
00566 FmtAssert( cond <= V_BR_LAST, ("unexpected variant in Expand_Branch"));
00567 FmtAssert( cond != V_BR_NONE, ("BR_NONE variant in Expand_Branch"));
00568
00569 if (Cond_Is_64Bit(cond) && Get_TN_Pair(src1) != NULL) {
00570 Expand_64Bit_Branch(targ, src1, src2, variant, ops);
00571 return;
00572 }
00573
00574 cmp = Pick_Compare_TOP (&cond, &src1, &src2, ops);
00575
00576 if ( Trace_Exp2 && cond != variant) {
00577 fprintf ( TFile, "<cgexp> transformed branch cond = %lld\n", cond);
00578 }
00579
00580 switch (cond) {
00581 case V_BR_ALWAYS:
00582 case V_BR_NEVER:
00583 Is_True(cmp == TOP_UNDEFINED,
00584 ("unexpected compare op for %s", BR_Variant_Name(cond)));
00585 if ((cond == V_BR_ALWAYS) ^ false_br) {
00586
00587 Build_OP (TOP_j, targ, ops);
00588 }
00589 break;
00590 case V_BR_PEQ:
00591 case V_BR_PNE:
00592 case V_BR_P_TRUE:
00593 FmtAssert(FALSE, ("unimplemented branch variant in Expand_Branch"));
00594 break;
00595 default:
00596 {
00597 TOP top;
00598
00599 TN *tmp;
00600 if (cmp != TOP_UNDEFINED) {
00601 if (TOP_is_flop(cmp)) {
00602 TN *fcc_tmp = Gen_Register_TN(ISA_REGISTER_CLASS_fcc, 1);
00603
00604 if (cmp == TOP_c_neq_s || cmp == TOP_c_neq_d) {
00605 Build_OP ((cmp == TOP_c_neq_d)?TOP_c_eq_d:TOP_c_eq_s,
00606 fcc_tmp, src1, src2, ops);
00607 Build_OP (false_br?TOP_bc1t:TOP_bc1f, fcc_tmp, targ, ops);
00608 } else {
00609 Build_OP (cmp, fcc_tmp, src1, src2, ops);
00610 Build_OP (false_br?TOP_bc1f:TOP_bc1t, fcc_tmp, targ, ops);
00611 }
00612 }
00613 else {
00614 if (TN_is_constant(src2) &&
00615 TN_has_value(src2) &&
00616 (TN_value(src2) == 0)) {
00617 if (cond == V_BR_I8LT || cond == V_BR_U8LT ||
00618 cond == V_BR_I4LT || cond == V_BR_U4LT)
00619 top = TOP_bltz;
00620 else top = TOP_bgez;
00621 Build_OP (top, src1, targ, ops);
00622 } else {
00623 tmp = Build_TN_Of_Mtype (MTYPE_I4);
00624 Build_OP (cmp, tmp, src1, src2, ops);
00625 if (cond == V_BR_I8LT || cond == V_BR_U8LT ||
00626 cond == V_BR_I4LT || cond == V_BR_U4LT)
00627 top = TOP_bne;
00628 else top = TOP_beq;
00629 Build_OP (top, tmp, Zero_TN, targ, ops);
00630 }
00631 }
00632 }
00633 else {
00634 switch (cond) {
00635 case V_BR_I8GE: top = TOP_bgez; break;
00636 case V_BR_I8GT: top = TOP_bgtz; break;
00637 case V_BR_I8LE: top = TOP_blez; break;
00638 case V_BR_I8LT: top = TOP_bltz; break;
00639 case V_BR_I8EQ: top = TOP_beq; break;
00640 case V_BR_U8EQ: top = TOP_beq; break;
00641 case V_BR_I8NE: top = TOP_bne; break;
00642 case V_BR_U8NE: top = TOP_bne; break;
00643 case V_BR_I4GE: top = TOP_bgez; break;
00644 case V_BR_I4GT: top = TOP_bgtz; break;
00645 case V_BR_I4LE: top = TOP_blez; break;
00646 case V_BR_I4LT: top = TOP_bltz; break;
00647 case V_BR_I4EQ: top = TOP_beq; break;
00648 case V_BR_U4EQ: top = TOP_beq; break;
00649 case V_BR_I4NE: top = TOP_bne; break;
00650 case V_BR_U4NE: top = TOP_bne; break;
00651 default:
00652 FmtAssert(FALSE, ("unimplemented branch variant in Expand_Branch"));
00653 }
00654 if (top == TOP_bne || top == TOP_beq)
00655 Build_OP(top, src1, TN_is_zero(src2) ? Zero_TN : src2, targ, ops);
00656 else Build_OP(top, src1, targ, ops);
00657 }
00658 }
00659 break;
00660 }
00661 }
00662
00663 void Exp_Indirect_Branch (TN *targ_reg, OPS *ops)
00664 {
00665 #if defined(TARG_SL)
00666 Build_OP(TOP_mvtc, JA_TN, targ_reg, ops);
00667 Build_OP(TOP_jr, JA_TN, ops);
00668 #else
00669 Build_OP(TOP_jr, targ_reg, ops);
00670 #endif
00671 }
00672
00673 #if defined(TARG_SL) && defined(TARG_SL2)
00674 void Exp_Local_Jump(BB * bb, INT64 offset, OPS * ops)
00675 {
00676 if(Gen_PIC_Shared) {
00677 ST *st = Gen_ST_For_BB(bb);
00678 TN *tn = Gen_Register_TN(ISA_REGISTER_CLASS_integer, Pointer_Size);
00679 Exp_Lda(MTYPE_U4, tn, st, offset, OPERATOR_UNKNOWN, ops);
00680 Build_OP(TOP_jr, tn, ops);
00681 } else {
00682
00683
00684 LABEL_IDX lab = Gen_Label_For_BB(bb);
00685 TN *lab_tn = Gen_Label_TN(lab, offset);
00686 Build_OP(TOP_j, lab_tn, ops);
00687 }
00688
00689 }
00690 #else
00691 void Exp_Local_Jump(BB *bb, INT64 offset, OPS *ops)
00692 {
00693 FmtAssert(FALSE, ("NYI: Exp_Local_Jump"));
00694 }
00695 #endif
00696
00697 void Exp_Return (TN *return_address, OPS *ops)
00698 {
00699 #if defined(TARG_SL)
00700 Build_OP(TOP_ret,return_address, ops);
00701 #else
00702 Build_OP(TOP_jr, return_address, ops);
00703 #endif
00704 }
00705
00706 void Exp_Call (OPERATOR opr, TN *return_address, TN *target, OPS *ops)
00707 {
00708 TOP top;
00709 switch (opr) {
00710 case OPR_CALL:
00711 top = TOP_jal;
00712 break;
00713 case OPR_ICALL:
00714 #if 0
00715 if ( ! Get_Trace (TP_CGEXP, 256)) {
00716
00717 OPCODE opc = OPCODE_make_op (OPR_LDID, Pointer_Mtype, Pointer_Mtype);
00718 TN *tmp1 = Build_TN_Of_Mtype (Pointer_Mtype);
00719 Expand_Load (opc, GP_TN, target, Gen_Literal_TN(8, 4), V_NONE, ops);
00720 Expand_Load (opc, tmp1, target, Gen_Literal_TN(0, 4), V_NONE, ops);
00721 target = tmp1;
00722 }
00723 #endif
00724
00725 case OPR_PICCALL:
00726 top = TOP_jalr;
00727 #if defined(TARG_SL)
00728 Build_OP(TOP_mvtc, JA_TN, target, ops);
00729 Build_OP (top, return_address, JA_TN, ops);
00730 return;
00731 #endif
00732 break;
00733 default:
00734 FmtAssert(FALSE, ("unexpected opr in Exp_Call"));
00735
00736 }
00737 Build_OP (top, return_address, target, ops);
00738 }