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
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057 #include <ctype.h>
00058
00059 #include "defs.h"
00060 #include "util.h"
00061 #include "config.h"
00062 #include "config_targ_opt.h"
00063 #include "erglob.h"
00064 #include "tracing.h"
00065 #include "data_layout.h"
00066 #include "const.h"
00067 #include "wn.h"
00068 #include "import.h"
00069 #include "opt_alias_interface.h"
00070 #include "opt_alias_mgr.h"
00071 #include "cgir.h"
00072 #include "cg.h"
00073 #include "void_list.h"
00074 #include "cg_dep_graph.h"
00075 #include "cg_spill.h"
00076 #include "cg_vector.h"
00077 #include "whirl2ops.h"
00078 #include "ti_errors.h"
00079 #include "ti_latency.h"
00080 #include "w2op.h"
00081 #include "cgexp.h"
00082 #include "cg_loop_recur.h"
00083 #include "targ_proc_properties.h"
00084 #include "ti_bundle.h"
00085 #include "hb_sched.h"
00086 #include "hb_hazards.h"
00087 #include "bb.h"
00088 #include "op.h"
00089 #include "op_list.h"
00090 #include "cg_grouping.h"
00091 #include "calls.h"
00092 #include "cgtarget.h"
00093 #include "calls.h"
00094
00095 UINT32 CGTARG_branch_taken_penalty;
00096 BOOL CGTARG_branch_taken_penalty_overridden = FALSE;
00097
00098 TOP CGTARG_Invert_Table[TOP_count+1];
00099 TOP CGTARG_Immed_To_Reg_Table[TOP_count+1];
00100
00101 OPCODE CGTARG_Assoc_Base_Opr_Table[TOP_count];
00102 mTOP CGTARG_Assoc_Base_Top_Table[TOP_count];
00103 mTOP CGTARG_Assoc_Base_Fnc_Table[TOP_count];
00104
00105 mTOP CGTARG_Inter_RegClass_Copy_Table[ISA_REGISTER_CLASS_MAX+1][ISA_REGISTER_CLASS_MAX+1][2];
00106
00107
00108 BOOL Trace_TD = FALSE;
00109 BOOL Trace_Eager = FALSE;
00110 extern BOOL Trace_Call_Exp;
00111
00112
00113 UINT32 CGTARG_Mem_Ref_Bytes(const OP *memop)
00114
00115
00116
00117
00118
00119 {
00120 FmtAssert(OP_load(memop) || OP_store(memop), ("not a load or store"));
00121
00122 TOP topcode = OP_code(memop);
00123
00124 Is_True(topcode < TOP_count, ("unexpected topcode %d\n", topcode));
00125
00126 if (topcode < TOP_count)
00127 {
00128 switch (topcode)
00129 {
00130 case TOP_lb:
00131 case TOP_lbu:
00132 case TOP_sb:
00133 return 1;
00134
00135 case TOP_lh:
00136 case TOP_lhu:
00137 case TOP_sh:
00138 return 2;
00139
00140 #ifdef TARG_SL
00141 case TOP_ldw16:
00142 case TOP_stw16:
00143 case TOP_push16:
00144 case TOP_pop16:
00145 return 4;
00146
00147 case TOP_ldub16_rs:
00148 return 1;
00149 case TOP_lduh16_rs:
00150 return 2;
00151 case TOP_c3_dmac_a:
00152 case TOP_c3_dmacn_a:
00153 case TOP_c3_dmula_a:
00154 case TOP_c3_dmulan_a:
00155 case TOP_c3_ffe:
00156 case TOP_c3_fftld:
00157 case TOP_c3_ld:
00158 case TOP_c3_fftst:
00159 case TOP_c3_st:
00160 case TOP_c3_mac_a:
00161 case TOP_c3_macn_a:
00162 case TOP_c3_mac_ar:
00163 case TOP_c3_macn_ar:
00164 case TOP_c3_mula_a:
00165 case TOP_c3_mula_ar:
00166 case TOP_c3_saadd_a:
00167 case TOP_c3_sasub_a:
00168 case TOP_c3_saaddh_a:
00169 case TOP_c3_sasubh_a:
00170 case TOP_c3_sadda_a:
00171 case TOP_c3_samulh_a:
00172 return 4;
00173 #endif
00174
00175 #ifdef TARG_SL2
00176
00177 case TOP_c2_ld_v_b_u:
00178 case TOP_c2_ld_v_b:
00179 case TOP_c2_ldi_v_b_u:
00180 case TOP_c2_ldi_v_b:
00181 return 16;
00182
00183 case TOP_c2_ld_v_h:
00184 case TOP_c2_ldi_v_h:
00185 return 32;
00186
00187 case TOP_c2_ld_v_w:
00188 case TOP_c2_ldi_v_w:
00189 return 64;
00190
00191 case TOP_c2_ld_v_sw:
00192 case TOP_c2_ld_v_m_b_u:
00193 case TOP_c2_ld_v_m_b:
00194 case TOP_c2_ld_v_m_h:
00195 case TOP_c2_ld_v_m_w:
00196 case TOP_c2_ldi_v_m_b_u:
00197 case TOP_c2_ldi_v_m_b:
00198 case TOP_c2_ldi_v_m_h:
00199 case TOP_c2_ldi_v_m_w:
00200 return 32768;
00201
00202
00203 case TOP_c2_ld_s_h_u_p:
00204 case TOP_c2_ld_s_h_u:
00205 case TOP_c2_ld_s_h_p:
00206 case TOP_c2_ld_s_h:
00207 case TOP_c2_ldi_s_h_u:
00208 case TOP_c2_ldi_s_h:
00209 return 2;
00210
00211 case TOP_c2_ld_s_w_p:
00212 case TOP_c2_ld_s_w:
00213 case TOP_c2_ldi_s_w:
00214 return 4;
00215
00216
00217 case TOP_c2_ld_v2g_b_u:
00218 case TOP_c2_ld_v2g_b:
00219 case TOP_c2_ldi_v2g_b_u:
00220 case TOP_c2_ldi_v2g_b:
00221 return 1;
00222
00223 case TOP_c2_ld_v2g_h_u:
00224 case TOP_c2_ld_v2g_h:
00225 case TOP_c2_ldi_v2g_h_u:
00226 case TOP_c2_ldi_v2g_h:
00227 return 17;
00228
00229 case TOP_c2_ld_v2g_w:
00230 case TOP_c2_ldi_v2g_w:
00231 return 49;
00232
00233
00234 case TOP_c2_ldi_c:
00235 return 4;
00236
00237
00238 case TOP_c2_st_v_b:
00239 case TOP_c2_sti_v_b:
00240 return 16;
00241
00242 case TOP_c2_st_v_h:
00243 case TOP_c2_sti_v_h:
00244 return 32;
00245
00246 case TOP_c2_st_v_w:
00247 case TOP_c2_sti_v_w:
00248 return 64;
00249
00250 case TOP_c2_st_v_m_b:
00251 case TOP_c2_st_v_m_h:
00252 case TOP_c2_st_v_m_w:
00253 case TOP_c2_sti_v_m_b:
00254 case TOP_c2_sti_v_m_h:
00255 case TOP_c2_sti_v_m_w:
00256 return 32768;
00257
00258
00259 case TOP_c2_st_s_h:
00260 case TOP_c2_st_s_h_p:
00261 case TOP_c2_sti_s_h:
00262 return 2;
00263
00264 case TOP_c2_st_s_w:
00265 case TOP_c2_st_s_w_p:
00266 case TOP_c2_sti_s_w:
00267 return 4;
00268
00269 case TOP_c2_sti_c:
00270 return 4;
00271
00272
00273
00274 case TOP_c2_st_g2v_b:
00275 case TOP_c2_sti_g2v_b:
00276 return 1;
00277 case TOP_c2_st_g2v_h:
00278 case TOP_c2_sti_g2v_h:
00279 return 17;
00280 case TOP_c2_st_g2v_w:
00281 case TOP_c2_sti_g2v_w:
00282 return 49;
00283
00284 #endif
00285 case TOP_lw:
00286 case TOP_ll:
00287 case TOP_lwu:
00288 case TOP_lwc1:
00289 case TOP_lwxc1:
00290 case TOP_sw:
00291 case TOP_sc:
00292 case TOP_swc1:
00293 case TOP_swxc1:
00294 return 4;
00295
00296 case TOP_ld:
00297 case TOP_lld:
00298 case TOP_ldc1:
00299 case TOP_ldxc1:
00300 case TOP_sd:
00301 case TOP_scd:
00302 case TOP_sdc1:
00303 case TOP_sdxc1:
00304 return 8;
00305 }
00306 }
00307
00308 return 0;
00309 }
00310
00311
00312
00313
00314
00315
00316
00317
00318
00319 BOOL
00320 CGTARG_Is_OP_Speculative(OP *op)
00321 {
00322 if (!OP_load(op)) return FALSE;
00323
00324
00325 if (CGTARG_Is_OP_Advanced_Load(op) || CGTARG_Is_OP_Speculative_Load(op))
00326 return TRUE;
00327
00328 return FALSE;
00329 }
00330
00331
00332
00333
00334
00335
00336
00337
00338
00339 void CGTARG_Perform_THR_Code_Generation (OP *load_op, OP *chk_load,
00340 THR_TYPE type)
00341 {
00342 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
00343 }
00344
00345
00346
00347
00348
00349
00350
00351
00352
00353 INT CGTARG_ARC_Sched_Latency(
00354 ARC *arc
00355 )
00356 {
00357 if ( ARC_kind(arc) == CG_DEP_PREBR &&
00358 PROC_has_same_cycle_branch_shadow() )
00359 return 0;
00360 else
00361 return ARC_latency(arc);
00362 }
00363
00364
00365
00366
00367
00368
00369
00370
00371
00372
00373 BOOL
00374 CGTARG_Bundle_Slot_Available(TI_BUNDLE *bundle,
00375 OP *op,
00376 INT slot,
00377 ISA_EXEC_UNIT_PROPERTY *prop,
00378 BOOL stop_bit_reqd,
00379 const CG_GROUPING *grouping)
00380 {
00381 return FALSE;
00382 }
00383
00384
00385
00386
00387
00388
00389
00390
00391
00392 BOOL
00393 CGTARG_Bundle_Stop_Bit_Available(TI_BUNDLE *bundle, INT slot)
00394 {
00395
00396 if (TI_BUNDLE_stop_bit(bundle, slot)) return TRUE;
00397
00398 return TI_BUNDLE_Stop_Bit_Available(bundle, slot);
00399 }
00400
00401
00402
00403
00404
00405
00406
00407
00408
00409 void
00410 CGTARG_Handle_Bundle_Hazard (OP *op,
00411 TI_BUNDLE *bundle,
00412 VECTOR *bundle_vector,
00413 BOOL can_fill,
00414 INT slot_pos,
00415 INT max_pos,
00416 BOOL stop_bit_reqd,
00417 ISA_EXEC_UNIT_PROPERTY prop)
00418 {
00419 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
00420 }
00421
00422
00423
00424
00425
00426
00427
00428
00429
00430 void
00431 CGTARG_Handle_Errata_Hazard (OP *op, INT erratnum, INT ops_to_check)
00432 {
00433 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
00434 }
00435
00436
00437
00438
00439
00440
00441
00442
00443
00444
00445
00446
00447
00448
00449 static void
00450 Reduce_Fraction(INT frac[2])
00451 {
00452 INT i;
00453 static const INT primes[] = {2, 3, 5, 7, 11, 13};
00454 INT n = frac[0];
00455 INT d = frac[1];
00456 INT p = d;
00457
00458 if (d < -1 || d > 1) {
00459 for (i = sizeof(primes) / sizeof(primes[0]); ; p = primes[--i]) {
00460 while (n % p == 0 && d % p == 0) {
00461 n = n / p;
00462 d = d / p;
00463 }
00464 if (i == 0) break;
00465 }
00466 }
00467
00468 frac[0] = n;
00469 frac[1] = d;
00470 }
00471
00472
00473
00474
00475
00476
00477
00478
00479
00480
00481
00482
00483
00484
00485
00486
00487
00488
00489
00490 static void
00491 Harmonic_Mean(
00492 INT mean[2],
00493 INT a,
00494 const INT a_rate[2],
00495 INT b,
00496 const INT b_rate[2]
00497 ) {
00498 if (a == 0) {
00499 mean[0] = b_rate[0];
00500 mean[1] = b_rate[1];
00501 } else if (b == 0) {
00502 mean[0] = a_rate[0];
00503 mean[1] = a_rate[1];
00504 } else {
00505 mean[1] = (a * a_rate[1] * b_rate[0])
00506 + (b * b_rate[1] * a_rate[0]);
00507 mean[0] = (a + b) * a_rate[0] * b_rate[0];
00508 Reduce_Fraction(mean);
00509 }
00510 }
00511
00512
00513
00514
00515
00516
00517
00518
00519
00520
00521 void CGTARG_Peak_Rate( PEAK_RATE_CLASS prc, PRC_INFO *info, INT ratio[2] )
00522 {
00523 ratio[0] = 1;
00524 ratio[1] = 1;
00525
00526 switch (prc) {
00527 case PRC_INST:
00528 ratio[0] = 4;
00529 break;
00530 case PRC_MADD:
00531 case PRC_MEMREF:
00532 ratio[0] = 2;
00533 break;
00534 case PRC_FLOP:
00535 case PRC_FADD:
00536 case PRC_FMUL:
00537 ratio[0] = 2;
00538 break;
00539 case PRC_IOP:
00540 ratio[0] = 2;
00541 break;
00542 default:
00543 ratio[0] = 2;
00544 break;
00545 }
00546 }
00547
00548
00549
00550
00551
00552
00553
00554
00555
00556
00557 #define Plural(i) ((i) != 1 ? "s" : "")
00558
00559
00560
00561
00562
00563
00564
00565
00566
00567
00568
00569
00570 static INT
00571 Percent_Of_Peak(INT numer, INT denom, INT peak[2])
00572 {
00573 if (numer == 0) return 0;
00574 return (numer * peak[1] * 100) / ((denom * peak[0]) + peak[1] - 1);
00575 }
00576
00577
00578
00579
00580
00581
00582
00583
00584
00585
00586 void
00587 CGTARG_Print_PRC_INFO(
00588 FILE *file,
00589 PRC_INFO *info,
00590 INT32 ii,
00591 const char *prefix,
00592 const char *suffix
00593 )
00594 {
00595 char *s;
00596 INT madds_per_cycle[2];
00597 INT memrefs_per_cycle[2];
00598 INT flops_per_cycle[2];
00599 INT fadds_per_cycle[2];
00600 INT fmuls_per_cycle[2];
00601 INT iops_per_cycle[2];
00602 INT insts_per_cycle[2];
00603 INT insts = info->refs[PRC_INST];
00604 INT memrefs = info->refs[PRC_MEMREF];
00605 INT flops = info->refs[PRC_FLOP];
00606 INT madds = info->refs[PRC_MADD];
00607 INT fadds = info->refs[PRC_FADD];
00608 INT fmuls = info->refs[PRC_FMUL];
00609 INT iops = info->refs[PRC_IOP];
00610
00611 CGTARG_Peak_Rate(PRC_INST, info, insts_per_cycle);
00612 CGTARG_Peak_Rate(PRC_MEMREF, info, memrefs_per_cycle);
00613 CGTARG_Peak_Rate(PRC_FLOP, info, flops_per_cycle);
00614 CGTARG_Peak_Rate(PRC_MADD, info, madds_per_cycle);
00615 CGTARG_Peak_Rate(PRC_FADD, info, fadds_per_cycle);
00616 CGTARG_Peak_Rate(PRC_FMUL, info, fmuls_per_cycle);
00617 CGTARG_Peak_Rate(PRC_IOP, info, iops_per_cycle);
00618
00619 if (flops != 0) {
00620 BOOL unbalanced_fpu = FALSE;
00621
00622 if ( madds_per_cycle[0] != 0 ) {
00623 fprintf(file,"%s%5d flop%1s (%3d%% of peak) (madds count as 2)%s"
00624 "%s%5d flop%1s (%3d%% of peak) (madds count as 1)%s"
00625 "%s%5d madd%1s (%3d%% of peak)%s",
00626 prefix,
00627 flops + madds,
00628 Plural(flops + madds),
00629 Percent_Of_Peak(flops + madds, ii * 2, madds_per_cycle),
00630 suffix,
00631 prefix,
00632 flops,
00633 Plural(flops),
00634 Percent_Of_Peak(flops, ii, flops_per_cycle),
00635 suffix,
00636 prefix,
00637 madds,
00638 Plural(madds),
00639 Percent_Of_Peak(madds, ii, madds_per_cycle),
00640 suffix);
00641 }
00642 else {
00643 fprintf(file,"%s%5d flop%1s (%3d%% of peak)%s",
00644 prefix,
00645 flops,
00646 Plural(flops),
00647 Percent_Of_Peak(flops, ii, flops_per_cycle),
00648 suffix);
00649 }
00650
00651 if ( unbalanced_fpu ) {
00652 INT fmuls2_per_cycle[2];
00653 INT fadds2_per_cycle[2];
00654 INT fadds2 = fadds + madds;
00655 INT fmuls2 = fmuls + madds;
00656
00657 Harmonic_Mean(fmuls2_per_cycle,
00658 fmuls, fmuls_per_cycle,
00659 madds, madds_per_cycle);
00660 Harmonic_Mean(fadds2_per_cycle,
00661 fadds, fadds_per_cycle,
00662 madds, madds_per_cycle);
00663
00664 fprintf(file,"%s%5d fmul%1s (%3d%% of peak)%s%s",
00665 prefix,
00666 fmuls2,
00667 Plural(fmuls2),
00668 Percent_Of_Peak(fmuls2, ii, fmuls2_per_cycle),
00669 madds_per_cycle[0] ? " (madds count as 1)" : "",
00670 suffix);
00671 fprintf(file,"%s%5d fadd%1s (%3d%% of peak)%s%s",
00672 prefix,
00673 fadds2,
00674 Plural(fadds2),
00675 Percent_Of_Peak(fadds2, ii, fadds2_per_cycle),
00676 madds_per_cycle[0] ? " (madds count as 1)" : "",
00677 suffix);
00678 }
00679 }
00680
00681 s = "";
00682 if (FALSE) {
00683 iops += memrefs;
00684 s = " (mem refs included)";
00685 }
00686
00687 fprintf(file,"%s%5d mem ref%1s (%3d%% of peak)%s"
00688 "%s%5d integer op%1s (%3d%% of peak)%s%s"
00689 "%s%5d instruction%1s (%3d%% of peak)%s",
00690 prefix,
00691 memrefs,
00692 Plural(memrefs),
00693 Percent_Of_Peak(memrefs, ii, memrefs_per_cycle),
00694 suffix,
00695 prefix,
00696 iops,
00697 Plural(iops),
00698 Percent_Of_Peak(iops, ii, iops_per_cycle),
00699 s,
00700 suffix,
00701 prefix,
00702 insts,
00703 Plural(insts),
00704 Percent_Of_Peak(insts, ii, insts_per_cycle),
00705 suffix);
00706 }
00707
00708
00709
00710
00711
00712
00713
00714
00715
00716
00717
00718 void
00719 CGTARG_Compute_PRC_INFO(
00720 BB *bb,
00721 PRC_INFO *info
00722 )
00723 {
00724 OP *op;
00725
00726 bzero (info, sizeof (PRC_INFO));
00727
00728 for ( op = BB_first_op(bb); op != NULL; op = OP_next(op) ) {
00729 INT num_insts = OP_Real_Ops (op);
00730
00731 if (num_insts == 0) continue;
00732
00733 info->refs[PRC_INST] += num_insts;
00734
00735 if ( OP_flop(op) ) {
00736 BOOL is_single = (OP_result_size(op,0) == 32);
00737
00738 ++info->refs[PRC_FLOP];
00739 info->refs[PRC_FLOP_S] += is_single;
00740 if (OP_madd(op)) {
00741 ++info->refs[PRC_MADD];
00742 info->refs[PRC_MADD_S] += is_single;
00743 }
00744 else if (OP_fadd(op) || OP_fsub(op)) {
00745 ++info->refs[PRC_FADD];
00746 info->refs[PRC_FADD_S] += is_single;
00747 }
00748 else if (OP_fmul(op)) {
00749 ++info->refs[PRC_FMUL];
00750 info->refs[PRC_FMUL_S] += is_single;
00751 }
00752 }
00753 else if (OP_memory(op))
00754 ++info->refs[PRC_MEMREF];
00755 else {
00756 INT k;
00757
00758
00759
00760
00761
00762 if (OP_has_result(op) && TN_is_float(OP_result(op,0))) goto not_iop;
00763
00764 for (k = 0; k < OP_opnds(op); k++) {
00765 if (TN_is_float(OP_opnd(op,k))) goto not_iop;
00766 }
00767
00768 info->refs[PRC_IOP] += num_insts;
00769
00770 not_iop:
00771 ;
00772 }
00773 }
00774 }
00775
00776
00777
00778
00779
00780
00781
00782
00783
00784
00785 void
00786 CGTARG_Branch_Info ( const OP *op,
00787 INT *tfirst,
00788 INT *tcount )
00789 {
00790 INT i;
00791 TN *tn;
00792
00793
00794 *tfirst = -1;
00795 *tcount = 0;
00796
00797
00798 for ( i = 0; ; i++ ) {
00799 if ( i >= OP_opnds(op) ) return;
00800 tn = OP_opnd(op,i);
00801 if ( tn != NULL && TN_is_label(tn) ) break;
00802 }
00803 *tfirst = i;
00804
00805
00806 *tcount = 1;
00807 for ( i++; i < OP_opnds(op); i++ ) {
00808 tn = OP_opnd(op,i);
00809 if ( tn == NULL || ! TN_is_label(tn) ) return;
00810 (*tcount)++;
00811 }
00812 return;
00813 }
00814
00815
00816
00817
00818
00819
00820
00821
00822
00823
00824 BOOL
00825 CGTARG_Can_Be_Speculative( OP *op )
00826 {
00827 WN *wn;
00828
00829
00830 if (Eager_Level == EAGER_NONE) return FALSE;
00831
00832
00833 if (OP_volatile(op)) return FALSE;
00834
00835 if (TOP_Can_Be_Speculative(OP_code(op))) return TRUE;
00836
00837 if (!OP_load(op)) return FALSE;
00838
00839
00840
00841
00842
00843
00844
00845
00846
00847
00848
00849 if (OP_no_alias(op)) goto scalar_load;
00850
00851
00852
00853
00854
00855 if (TN_is_symbol(OP_opnd(op, 1)) &&
00856 !ST_is_weak_symbol(TN_var(OP_opnd(op, 1)))) goto scalar_load;
00857
00858
00859
00860
00861
00862 if (
00863 ( (wn = Get_WN_From_Memory_OP(op))
00864 && Alias_Manager->Safe_to_speculate(wn))) goto scalar_load;
00865
00866
00867
00868
00869 if (CGTARG_Is_OP_Speculative(op)) goto scalar_load;
00870
00871
00872
00873
00874 return FALSE;
00875
00876
00877
00878
00879 scalar_load:
00880 return TRUE;
00881 }
00882
00883
00884
00885
00886
00887
00888
00889
00890
00891 BOOL
00892 CGTARG_Is_OP_Speculative_Load( OP *memop )
00893 {
00894 return FALSE;
00895 }
00896
00897
00898
00899
00900
00901
00902
00903
00904
00905 BOOL
00906 CGTARG_Is_OP_Advanced_Load( OP *memop )
00907 {
00908 return FALSE;
00909 }
00910
00911
00912
00913
00914
00915
00916
00917
00918
00919 BOOL
00920 CGTARG_Is_OP_Check_Load( OP *memop )
00921 {
00922 return FALSE;
00923 }
00924
00925
00926
00927
00928
00929
00930
00931
00932
00933
00934 BOOL
00935 CGTARG_OP_Defs_TN( OP *op, TN *tn )
00936 {
00937 return FALSE;
00938 }
00939
00940 BOOL
00941 CGTARG_OP_Refs_TN( OP *op, TN *tn )
00942 {
00943 return FALSE;
00944 }
00945
00946
00947
00948
00949
00950
00951
00952
00953
00954 static MEM_POOL interference_pool;
00955 static VOID_LIST** writing;
00956
00957 static BOOL is_loop;
00958 static INT32 assumed_longest_latency = 40;
00959
00960
00961
00962
00963
00964
00965 static INT32 cycle_count;
00966
00967 static void (*make_interference)(void*,void*);
00968
00969
00970
00971
00972
00973
00974
00975
00976
00977
00978
00979 static void
00980 Increase_Assumed_Longest_Latency(INT32 new_longest_latency )
00981 {
00982 DevWarn("Assumed longest latency should be at least %d",
00983 new_longest_latency);
00984 writing = TYPE_MEM_POOL_REALLOC_N(VOID_LIST*,&interference_pool,writing,
00985 cycle_count + assumed_longest_latency,
00986 cycle_count + new_longest_latency);
00987 assumed_longest_latency = new_longest_latency;
00988 }
00989
00990
00991
00992
00993
00994
00995
00996
00997
00998 BOOL
00999 CGTARG_Interference_Required(void)
01000 {
01001 return FALSE;
01002 }
01003
01004
01005
01006
01007
01008
01009
01010
01011
01012 void
01013 CGTARG_Interference_Initialize( INT32 cycle_count_local, BOOL is_loop_local,
01014 void (*make_interference_local)(void*,void*) )
01015 {
01016 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
01017 }
01018
01019
01020
01021
01022
01023
01024
01025
01026
01027 void
01028 CGTARG_Result_Live_Range( void* lrange, OP* op, INT32 offset )
01029 {
01030 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
01031 }
01032
01033
01034
01035
01036
01037
01038
01039
01040
01041 void
01042 CGTARG_Operand_Live_Range( void* lrange, INT opnd, OP* op, INT32 offset )
01043 {
01044 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
01045 }
01046
01047
01048
01049
01050
01051
01052
01053
01054
01055 void
01056 CGTARG_Interference_Finalize(void)
01057 {
01058 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
01059 }
01060
01061
01062
01063
01064
01065
01066
01067
01068
01069
01070 BOOL
01071 CGTARG_Preg_Register_And_Class(
01072 WN_OFFSET preg,
01073 ISA_REGISTER_CLASS *p_rclass,
01074 REGISTER *p_reg
01075 )
01076 {
01077 ISA_REGISTER_CLASS rclass;
01078 INT regnum;
01079
01080
01081
01082 if (!Preg_Is_Dedicated(preg))
01083 return FALSE;
01084
01085 if (!Preg_Offset_Is_Int(preg) &&
01086 !Preg_Offset_Is_Float(preg) &&
01087 !Preg_Offset_Is_Fcc(preg))
01088 return FALSE;
01089
01090
01091
01092
01093 if (Preg_Offset_Is_Int(preg)) {
01094 regnum = preg - (Int_Preg_Min_Offset - 1);
01095 rclass = ISA_REGISTER_CLASS_integer;
01096 }
01097 else if (Preg_Offset_Is_Float(preg)) {
01098 regnum = preg - Float_Preg_Min_Offset;
01099 rclass = ISA_REGISTER_CLASS_float;
01100 }
01101 else if (Preg_Offset_Is_Fcc(preg)) {
01102 regnum = preg - Fcc_Preg_Min_Offset;
01103 rclass = ISA_REGISTER_CLASS_fcc;
01104 }
01105 else if (preg == 0) {
01106 regnum = 0;
01107 rclass = ISA_REGISTER_CLASS_integer;
01108 }
01109 else {
01110 return FALSE;
01111 }
01112
01113
01114 for ( REGISTER reg = REGISTER_MIN;
01115 reg <= REGISTER_CLASS_last_register(rclass);
01116 reg++ )
01117 {
01118 if ( REGISTER_machine_id(rclass,reg) == regnum )
01119 {
01120 *p_reg = reg;
01121 *p_rclass = rclass;
01122 return TRUE;
01123 }
01124 }
01125
01126 FmtAssert(FALSE, ("failed to map preg %d", preg));
01127
01128 }
01129
01130
01131
01132
01133
01134
01135
01136
01137
01138
01139 void CGTARG_Compute_Branch_Parameters(INT32 *mispredict, INT32 *fixed, INT32 *brtaken, double *factor)
01140 {
01141 *mispredict = 0;
01142 *fixed = 0;
01143 *brtaken = 0;
01144 *factor = 0.0;
01145
01146 if (Is_Target_Sb1() || Is_Target_R10K())
01147 {
01148 *mispredict= 7; *fixed= 1; *brtaken= 1; *factor = 1.0;
01149 }
01150 #ifdef TARG_SL
01151 else if (Is_Target_Sl1_pcore() || Is_Target_Sl1_dsp()) {
01152 *mispredict= 7; *fixed= 1; *brtaken= 1; *factor = 1.0;
01153 }
01154 else if ( Is_Target_Sl2_pcore() || Is_Target_Sl2_mcore()) {
01155 *mispredict= 3; *fixed= 1; *brtaken= 1; *factor = 1.0;
01156 }
01157 #endif
01158 else
01159 {
01160 FmtAssert(FALSE, ("invalid target"));
01161 }
01162
01163
01164
01165
01166
01167
01168 if (CG_branch_mispredict_penalty >= 0)
01169 *mispredict= CG_branch_mispredict_penalty ;
01170
01171 if (CG_branch_mispredict_factor >= 0)
01172 *factor= CG_branch_mispredict_factor * (.01);
01173 }
01174
01175
01176
01177
01178
01179
01180
01181
01182
01183
01184 BOOL CGTARG_Can_Change_To_Brlikely(OP *xfer_op, TOP *new_opcode)
01185 {
01186 return FALSE;
01187 }
01188
01189
01190
01191
01192
01193
01194
01195
01196
01197
01198 BOOL CGTARG_Is_Long_Latency(TOP op)
01199 {
01200 return (TI_LATENCY_Result_Available_Cycle(op, 0) -
01201 TI_LATENCY_Operand_Access_Cycle(op, 0)) > 2;
01202 }
01203
01204
01205
01206
01207
01208
01209
01210
01211
01212 VARIANT CGTARG_Analyze_Branch(
01213 OP *br,
01214 TN **tn1,
01215 TN **tn2)
01216 {
01217 INT variant;
01218
01219
01220
01221
01222 *tn1 = OP_opnd(br, 0);
01223 *tn2 = OP_opnd(br, 1);
01224
01225 switch (OP_code(br))
01226 {
01227 case TOP_beq:
01228 variant = V_BR_I4EQ;
01229 break;
01230
01231 case TOP_bne:
01232 variant = V_BR_I4NE;
01233 break;
01234
01235 case TOP_bgez:
01236 variant = V_BR_I4GE;
01237 *tn2 = Gen_Literal_TN(0,4);
01238 break;
01239
01240 case TOP_bltz:
01241 variant = V_BR_I4LT;
01242 *tn2 = Gen_Literal_TN(0,4);
01243 break;
01244
01245 case TOP_bgtz:
01246 variant = V_BR_I4GT;
01247 *tn2 = Gen_Literal_TN(0,4);
01248 break;
01249
01250 case TOP_blez:
01251 variant = V_BR_I4LE;
01252 *tn2 = Gen_Literal_TN(0,4);
01253 break;
01254
01255 case TOP_bc1t:
01256 variant = V_BR_F_TRUE;
01257 *tn2 = NULL;
01258 break;
01259
01260 case TOP_bc1f:
01261 variant = V_BR_F_FALSE;
01262 *tn2 = NULL;
01263 break;
01264
01265 default:
01266 variant = V_BR_NONE;
01267 *tn1 = NULL;
01268 *tn2 = NULL;
01269
01270 Is_True( !OP_cond( br ), ("unexpected conditional branch %d\n", OP_code(br) ) );
01271
01272 break;
01273 }
01274
01275 return variant;
01276 }
01277
01278
01279
01280
01281
01282
01283
01284
01285
01286
01287 VARIANT CGTARG_Analyze_Compare(
01288 OP *br,
01289 TN **tn1,
01290 TN **tn2,
01291 OP **compare_op)
01292 {
01293 TN *cond_tn1;
01294 TN *cond_tn2;
01295
01296
01297
01298 INT variant = CGTARG_Analyze_Branch(br, &cond_tn1, &cond_tn2);
01299
01300
01301
01302
01303
01304 *compare_op = NULL;
01305 *tn1 = cond_tn1;
01306 *tn2 = cond_tn2;
01307
01308 return variant;
01309 }
01310
01311
01312
01313
01314
01315
01316
01317
01318
01319
01320 TOP
01321 CGTARG_Equiv_Nonindex_Memory_Op ( OP *op )
01322 {
01323 return TOP_UNDEFINED;
01324 }
01325
01326
01327
01328
01329
01330
01331
01332
01333
01334 TOP
01335 CGTARG_Which_OP_Select ( UINT16 bit_size, BOOL is_float, BOOL is_fcc )
01336 {
01337 FmtAssert( FALSE, ( "CGTARG_Which_OP_Select: Unsupported Target") );
01338 return TOP_UNDEFINED;
01339 }
01340
01341
01342
01343
01344
01345
01346
01347
01348
01349 static BOOL
01350 Is_OP_fp_op1(OP *op)
01351 {
01352 return FALSE;
01353 }
01354
01355
01356
01357
01358
01359
01360
01361 void
01362 Insert_Stop_Bits(BB *bb)
01363 {
01364 }
01365
01366
01367
01368
01369
01370
01371
01372
01373
01374 INT32 CGTARG_Special_Min_II(BB* loop_body, BOOL trace)
01375 {
01376 return 0;
01377 }
01378
01379
01380
01381
01382
01383
01384
01385
01386
01387 void
01388 Hardware_Workarounds(void)
01389 {
01390 }
01391
01392
01393
01394
01395
01396
01397
01398
01399
01400 void CGTARG_Initialize(void)
01401 {
01402 INT32 i;
01403
01404
01405
01406 for(i = 0; i <= TOP_count; ++i) {
01407 CGTARG_Invert_Table[i] = TOP_UNDEFINED;
01408 CGTARG_Immed_To_Reg_Table[i] = TOP_UNDEFINED;
01409 }
01410
01411 for (i = 0; i <= ISA_REGISTER_CLASS_MAX; ++i) {
01412 INT j;
01413 for (j = 0; j <= ISA_REGISTER_CLASS_MAX; ++j) {
01414 CGTARG_Inter_RegClass_Copy_Table[i][j][FALSE] = TOP_UNDEFINED;
01415 CGTARG_Inter_RegClass_Copy_Table[i][j][TRUE] = TOP_UNDEFINED;
01416 }
01417 }
01418
01419
01420
01421 CGTARG_Invert_Table[TOP_add_s] = TOP_sub_s;
01422 CGTARG_Invert_Table[TOP_add_d] = TOP_sub_d;
01423 CGTARG_Invert_Table[TOP_madd_s] = TOP_nmadd_s;
01424 CGTARG_Invert_Table[TOP_madd_d] = TOP_nmadd_d;
01425 CGTARG_Invert_Table[TOP_add] = TOP_sub;
01426 CGTARG_Invert_Table[TOP_addu] = TOP_subu;
01427 CGTARG_Invert_Table[TOP_dadd] = TOP_dsub;
01428 CGTARG_Invert_Table[TOP_daddu] = TOP_dsubu;
01429
01430 CGTARG_Invert_Table[TOP_sub_s] = TOP_add_s;
01431 CGTARG_Invert_Table[TOP_sub_d] = TOP_add_d;
01432 CGTARG_Invert_Table[TOP_nmadd_s] = TOP_madd_s;
01433 CGTARG_Invert_Table[TOP_nmadd_d] = TOP_madd_d;
01434 CGTARG_Invert_Table[TOP_sub] = TOP_add;
01435 CGTARG_Invert_Table[TOP_subu] = TOP_addu;
01436 CGTARG_Invert_Table[TOP_dsub] = TOP_dadd;
01437 CGTARG_Invert_Table[TOP_dsubu] = TOP_daddu;
01438
01439 CGTARG_Invert_Table[TOP_or] = TOP_nor;
01440 CGTARG_Invert_Table[TOP_nor] = TOP_or;
01441
01442 CGTARG_Invert_Table[TOP_movf] = TOP_movt;
01443 CGTARG_Invert_Table[TOP_movt] = TOP_movf;
01444 CGTARG_Invert_Table[TOP_movz] = TOP_movn;
01445 CGTARG_Invert_Table[TOP_movn] = TOP_movz;
01446 CGTARG_Invert_Table[TOP_movf_s] = TOP_movt_s;
01447 CGTARG_Invert_Table[TOP_movt_s] = TOP_movf_s;
01448 CGTARG_Invert_Table[TOP_movz_s] = TOP_movn_s;
01449 CGTARG_Invert_Table[TOP_movn_s] = TOP_movz_s;
01450 CGTARG_Invert_Table[TOP_movf_d] = TOP_movt_d;
01451 CGTARG_Invert_Table[TOP_movt_d] = TOP_movf_d;
01452 CGTARG_Invert_Table[TOP_movz_d] = TOP_movn_d;
01453 CGTARG_Invert_Table[TOP_movn_d] = TOP_movz_d;
01454
01455 CGTARG_Invert_Table[TOP_beq] = TOP_bne;
01456 CGTARG_Invert_Table[TOP_bne] = TOP_beq;
01457
01458 CGTARG_Invert_Table[TOP_bgez] = TOP_bltz;
01459 CGTARG_Invert_Table[TOP_bgtz] = TOP_blez;
01460 CGTARG_Invert_Table[TOP_bltz] = TOP_bgez;
01461 CGTARG_Invert_Table[TOP_blez] = TOP_bgtz;
01462 CGTARG_Invert_Table[TOP_bgezal] = TOP_bltzal;
01463 CGTARG_Invert_Table[TOP_bltzal] = TOP_bgezal;
01464
01465 CGTARG_Invert_Table[TOP_bc1f] = TOP_bc1t;
01466 CGTARG_Invert_Table[TOP_bc1t] = TOP_bc1f;
01467
01468 CGTARG_Invert_Table[TOP_c_f_s] = TOP_c_t_s;
01469 CGTARG_Invert_Table[TOP_c_f_d] = TOP_c_t_d;
01470 CGTARG_Invert_Table[TOP_c_t_s] = TOP_c_f_s;
01471 CGTARG_Invert_Table[TOP_c_t_d] = TOP_c_f_d;
01472 CGTARG_Invert_Table[TOP_c_un_s] = TOP_c_or_s;
01473 CGTARG_Invert_Table[TOP_c_un_d] = TOP_c_or_d;
01474 CGTARG_Invert_Table[TOP_c_or_s] = TOP_c_un_s;
01475 CGTARG_Invert_Table[TOP_c_or_d] = TOP_c_un_d;
01476 CGTARG_Invert_Table[TOP_c_eq_s] = TOP_c_neq_s;
01477 CGTARG_Invert_Table[TOP_c_eq_d] = TOP_c_neq_d;
01478 CGTARG_Invert_Table[TOP_c_neq_s] = TOP_c_eq_s;
01479 CGTARG_Invert_Table[TOP_c_neq_d] = TOP_c_eq_d;
01480 CGTARG_Invert_Table[TOP_c_ueq_s] = TOP_c_olg_s;
01481 CGTARG_Invert_Table[TOP_c_ueq_d] = TOP_c_olg_d;
01482 CGTARG_Invert_Table[TOP_c_olg_s] = TOP_c_ueq_s;
01483 CGTARG_Invert_Table[TOP_c_olg_d] = TOP_c_ueq_d;
01484 CGTARG_Invert_Table[TOP_c_olt_s] = TOP_c_uge_s;
01485 CGTARG_Invert_Table[TOP_c_olt_d] = TOP_c_uge_d;
01486 CGTARG_Invert_Table[TOP_c_uge_s] = TOP_c_olt_s;
01487 CGTARG_Invert_Table[TOP_c_uge_d] = TOP_c_olt_d;
01488 CGTARG_Invert_Table[TOP_c_ult_s] = TOP_c_oge_s;
01489 CGTARG_Invert_Table[TOP_c_ult_d] = TOP_c_oge_d;
01490 CGTARG_Invert_Table[TOP_c_oge_s] = TOP_c_ult_s;
01491 CGTARG_Invert_Table[TOP_c_oge_d] = TOP_c_ult_d;
01492 CGTARG_Invert_Table[TOP_c_ole_s] = TOP_c_ugt_s;
01493 CGTARG_Invert_Table[TOP_c_ole_d] = TOP_c_ugt_d;
01494 CGTARG_Invert_Table[TOP_c_ugt_s] = TOP_c_ole_s;
01495 CGTARG_Invert_Table[TOP_c_ugt_d] = TOP_c_ole_d;
01496 CGTARG_Invert_Table[TOP_c_ule_s] = TOP_c_ogt_s;
01497 CGTARG_Invert_Table[TOP_c_ule_d] = TOP_c_ogt_d;
01498 CGTARG_Invert_Table[TOP_c_ogt_s] = TOP_c_ule_s;
01499 CGTARG_Invert_Table[TOP_c_ogt_d] = TOP_c_ule_d;
01500 CGTARG_Invert_Table[TOP_c_sf_s] = TOP_c_st_s;
01501 CGTARG_Invert_Table[TOP_c_sf_d] = TOP_c_st_d;
01502 CGTARG_Invert_Table[TOP_c_st_s] = TOP_c_sf_s;
01503 CGTARG_Invert_Table[TOP_c_st_d] = TOP_c_sf_d;
01504 CGTARG_Invert_Table[TOP_c_ngle_s] = TOP_c_gle_s;
01505 CGTARG_Invert_Table[TOP_c_ngle_d] = TOP_c_gle_d;
01506 CGTARG_Invert_Table[TOP_c_gle_s] = TOP_c_ngle_s;
01507 CGTARG_Invert_Table[TOP_c_gle_d] = TOP_c_ngle_d;
01508 CGTARG_Invert_Table[TOP_c_seq_s] = TOP_c_sne_s;
01509 CGTARG_Invert_Table[TOP_c_seq_d] = TOP_c_sne_d;
01510 CGTARG_Invert_Table[TOP_c_sne_s] = TOP_c_seq_s;
01511 CGTARG_Invert_Table[TOP_c_sne_d] = TOP_c_seq_d;
01512 CGTARG_Invert_Table[TOP_c_ngl_s] = TOP_c_gl_s;
01513 CGTARG_Invert_Table[TOP_c_ngl_d] = TOP_c_gl_d;
01514 CGTARG_Invert_Table[TOP_c_gl_s] = TOP_c_ngl_s;
01515 CGTARG_Invert_Table[TOP_c_gl_d] = TOP_c_ngl_d;
01516 CGTARG_Invert_Table[TOP_c_nlt_s] = TOP_c_lt_s;
01517 CGTARG_Invert_Table[TOP_c_nlt_d] = TOP_c_lt_d;
01518 CGTARG_Invert_Table[TOP_c_lt_s] = TOP_c_nlt_s;
01519 CGTARG_Invert_Table[TOP_c_lt_d] = TOP_c_nlt_d;
01520 CGTARG_Invert_Table[TOP_c_nge_s] = TOP_c_ge_s;
01521 CGTARG_Invert_Table[TOP_c_nge_d] = TOP_c_ge_d;
01522 CGTARG_Invert_Table[TOP_c_ge_s] = TOP_c_nge_s;
01523 CGTARG_Invert_Table[TOP_c_ge_d] = TOP_c_nge_d;
01524 CGTARG_Invert_Table[TOP_c_le_s] = TOP_c_nle_s;
01525 CGTARG_Invert_Table[TOP_c_le_d] = TOP_c_nle_d;
01526 CGTARG_Invert_Table[TOP_c_nle_s] = TOP_c_le_s;
01527 CGTARG_Invert_Table[TOP_c_nle_d] = TOP_c_le_d;
01528 CGTARG_Invert_Table[TOP_c_ngt_s] = TOP_c_gt_s;
01529 CGTARG_Invert_Table[TOP_c_ngt_d] = TOP_c_gt_d;
01530 CGTARG_Invert_Table[TOP_c_gt_s] = TOP_c_ngt_s;
01531 CGTARG_Invert_Table[TOP_c_gt_d] = TOP_c_ngt_d;
01532
01533 CGTARG_Invert_Table[TOP_teq] = TOP_tne;
01534 CGTARG_Invert_Table[TOP_tne] = TOP_teq;
01535 CGTARG_Invert_Table[TOP_tge] = TOP_tlt;
01536 CGTARG_Invert_Table[TOP_tlt] = TOP_tge;
01537 CGTARG_Invert_Table[TOP_tgeu] = TOP_tltu;
01538 CGTARG_Invert_Table[TOP_tltu] = TOP_tgeu;
01539
01540 CGTARG_Invert_Table[TOP_teqi] = TOP_tnei;
01541 CGTARG_Invert_Table[TOP_tnei] = TOP_teqi;
01542 CGTARG_Invert_Table[TOP_tgei] = TOP_tlti;
01543 CGTARG_Invert_Table[TOP_tlti] = TOP_tgei;
01544 CGTARG_Invert_Table[TOP_tgeiu] = TOP_tltiu;
01545 CGTARG_Invert_Table[TOP_tltiu] = TOP_tgeiu;
01546
01547
01548
01549 CGTARG_Immed_To_Reg_Table[TOP_addi] = TOP_add;
01550 CGTARG_Immed_To_Reg_Table[TOP_daddi] = TOP_dadd;
01551 CGTARG_Immed_To_Reg_Table[TOP_addiu] = TOP_addu;
01552 CGTARG_Immed_To_Reg_Table[TOP_daddiu] = TOP_daddu;
01553 CGTARG_Immed_To_Reg_Table[TOP_slti] = TOP_slt;
01554 CGTARG_Immed_To_Reg_Table[TOP_sltiu] = TOP_sltu;
01555 CGTARG_Immed_To_Reg_Table[TOP_andi] = TOP_and;
01556 CGTARG_Immed_To_Reg_Table[TOP_ori] = TOP_or;
01557 CGTARG_Immed_To_Reg_Table[TOP_xori] = TOP_xor;
01558 CGTARG_Immed_To_Reg_Table[TOP_teqi] = TOP_teq;
01559 CGTARG_Immed_To_Reg_Table[TOP_tgei] = TOP_tge;
01560 CGTARG_Immed_To_Reg_Table[TOP_tgeiu] = TOP_tgeu;
01561 CGTARG_Immed_To_Reg_Table[TOP_tlti] = TOP_tlt;
01562 CGTARG_Immed_To_Reg_Table[TOP_tltiu] = TOP_tltu;
01563 CGTARG_Immed_To_Reg_Table[TOP_tnei] = TOP_tne;
01564
01565
01566
01567 CGTARG_Inter_RegClass_Copy_Table[ISA_REGISTER_CLASS_float]
01568 [ISA_REGISTER_CLASS_integer]
01569 [FALSE] = TOP_mfc1;
01570 CGTARG_Inter_RegClass_Copy_Table[ISA_REGISTER_CLASS_float]
01571 [ISA_REGISTER_CLASS_integer]
01572 [TRUE] = TOP_dmfc1;
01573
01574 CGTARG_Inter_RegClass_Copy_Table[ISA_REGISTER_CLASS_integer]
01575 [ISA_REGISTER_CLASS_float]
01576 [FALSE] = TOP_mtc1;
01577 CGTARG_Inter_RegClass_Copy_Table[ISA_REGISTER_CLASS_integer]
01578 [ISA_REGISTER_CLASS_float]
01579 [TRUE] = TOP_dmtc1;
01580 }
01581
01582
01583
01584
01585
01586
01587
01588
01589
01590
01591 void CGTARG_Load_From_Memory(TN *tn, ST *mem_loc, OPS *ops)
01592 {
01593 TYPE_ID mtype = TY_mtype(ST_type(mem_loc));
01594 Exp_Load(mtype, mtype, tn, mem_loc, 0, ops, 0);
01595 }
01596
01597
01598
01599
01600
01601
01602
01603
01604
01605
01606 void CGTARG_Store_To_Memory(TN *tn, ST *mem_loc, OPS *ops)
01607 {
01608 TYPE_ID mtype = TY_mtype(ST_type(mem_loc));
01609 Exp_Store(mtype, tn, mem_loc, 0, ops, 0);
01610 }
01611
01612
01613
01614
01615
01616
01617
01618
01619
01620
01621 void CGTARG_Init_Assoc_Base(void)
01622 {
01623 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
01624 }
01625
01626
01627
01628
01629
01630
01631
01632
01633
01634
01635 INT CGTARG_Copy_Operand(OP *op)
01636 {
01637 TOP opr = OP_code(op);
01638 switch (opr)
01639 {
01640 case TOP_addi:
01641 case TOP_addiu:
01642 case TOP_daddi:
01643 case TOP_daddiu:
01644 case TOP_sll:
01645 case TOP_srl:
01646 case TOP_sra:
01647 case TOP_dsll:
01648 case TOP_dsrl:
01649 case TOP_dsra:
01650 if (TN_has_value(OP_opnd(op,1)) && TN_value(OP_opnd(op,1)) == 0)
01651 return 0;
01652 break;
01653
01654 case TOP_andi:
01655 {
01656 TN *src1 = OP_opnd( op, 1 );
01657 if (TN_is_constant(src1)) {
01658 INT64 val;
01659 if (TN_has_value(src1))
01660 val = TN_value(src1);
01661 else FmtAssert(FALSE,("unexpected constant in CGTARG_Copy_Operand"));
01662 if (val == -1)
01663 return 0;
01664 }
01665 break;
01666 }
01667
01668 case TOP_ori:
01669 case TOP_xori:
01670 {
01671 TN *src1 = OP_opnd( op, 1 );
01672 if (TN_is_constant(src1)) {
01673 INT64 val;
01674 if (TN_has_value(src1))
01675 val = TN_value(src1);
01676 else FmtAssert(FALSE,("unexpected constant in CGTARG_Copy_Operand"));
01677 if (val == 0)
01678 return 0;
01679 }
01680 break;
01681 }
01682
01683 case TOP_or:
01684 case TOP_xor:
01685 case TOP_addu:
01686 case TOP_daddu:
01687 if (OP_opnd( op, 1) == Zero_TN)
01688 return 0;
01689 else if (OP_opnd( op, 0) == Zero_TN)
01690 return 1;
01691 break;
01692
01693 }
01694
01695 if (OP_copy(op)) {
01696 if (opr == TOP_add || opr == TOP_dadd ||
01697 opr == TOP_addu || opr == TOP_daddu ||
01698 opr == TOP_or ||
01699 opr == TOP_mov_s || opr== TOP_mov_d)
01700 return 0;
01701 }
01702
01703 return -1;
01704 }
01705
01706
01707
01708
01709
01710
01711
01712
01713
01714
01715 BOOL
01716 CGTARG_Can_Fit_Immediate_In_Add_Instruction (INT64 immed)
01717 {
01718 return ISA_LC_Value_In_Class (immed, LC_simm16);
01719 }
01720
01721
01722
01723
01724
01725
01726
01727
01728
01729
01730 BOOL
01731 CGTARG_Can_Load_Immediate_In_Single_Instruction (INT64 immed)
01732 {
01733 return ISA_LC_Value_In_Class (immed, LC_simm16);
01734 }
01735
01736
01737
01738
01739
01740
01741
01742
01743
01744
01745
01746
01747 void
01748 CGTARG_Predicate_OP(BB* bb, OP* op, TN* pred_tn)
01749 {
01750 if (OP_has_predicate(op)) {
01751 FmtAssert( FALSE, ( "CGTARG_Which_OP_Select: Unsupported Target") );
01752 }
01753 }
01754
01755
01756
01757
01758
01759
01760
01761
01762
01763 BOOL
01764 CGTARG_Branches_On_True(OP* br_op, OP* cmp_op)
01765 {
01766 return FALSE;
01767 }
01768
01769
01770
01771
01772
01773
01774
01775
01776
01777
01778
01779 TOP
01780 CGTARG_Parallel_Compare(OP* cmp_op, COMPARE_TYPE ctype)
01781 {
01782 return TOP_UNDEFINED;
01783 }
01784
01785
01786
01787
01788
01789
01790
01791
01792
01793 BOOL
01794 CGTARG_Dependence_Required(OP *pred_op, OP *succ_op)
01795 {
01796
01797 #if defined(TARG_SL2)
01798 switch(OP_code(pred_op))
01799 {
01800 case TOP_c2_thctrl_lock:
01801 case TOP_c2_thctrl_unlock:
01802 case TOP_c2_thctrl_deact:
01803 case TOP_c2_thctrl_act:
01804 case TOP_c2_thctrl_mode4:
01805 case TOP_c2_thctrl_mode5:
01806 case TOP_c2_thctrl_mode6:
01807 case TOP_c2_thctrl_mode7:
01808 case TOP_c2_fork_m:
01809 case TOP_c2_fork_n:
01810 case TOP_peripheral_rw_begin:
01811 case TOP_peripheral_rw_end:
01812 return TRUE;
01813 }
01814 switch(OP_code(succ_op))
01815 {
01816 case TOP_c2_thctrl_lock:
01817 case TOP_c2_thctrl_unlock:
01818 case TOP_c2_thctrl_deact:
01819 case TOP_c2_thctrl_act:
01820 case TOP_c2_thctrl_mode4:
01821 case TOP_c2_thctrl_mode5:
01822 case TOP_c2_thctrl_mode6:
01823 case TOP_c2_thctrl_mode7:
01824 case TOP_c2_fork_m:
01825 case TOP_c2_fork_n:
01826 case TOP_c2_joint:
01827 case TOP_loop:
01828 case TOP_peripheral_rw_begin:
01829 case TOP_peripheral_rw_end:
01830 return TRUE;
01831 }
01832 #endif
01833 return FALSE;
01834 }
01835
01836
01837
01838
01839
01840
01841
01842
01843
01844 void
01845 CGTARG_Adjust_Latency(OP *pred_op, OP *succ_op, CG_DEP_KIND kind, UINT8 opnd, INT *latency)
01846 {
01847 #if !defined(TARG_SL2)
01848
01849
01850
01851
01852
01853
01854
01855
01856
01857
01858
01859 TN* operand = NULL;
01860 if(OP_opnds(succ_op) > opnd)
01861 operand = OP_opnd(succ_op, opnd);
01862
01863 if(OP_has_bypass(pred_op))
01864 *latency = 0;
01865 else if(operand && TN_is_register(operand) && TN_register_class(operand) == ISA_REGISTER_CLASS_cop_vreg)
01866 {
01867 *latency = 2;
01868 }
01869 #endif
01870 }
01871
01872
01873
01874
01875
01876
01877 void
01878 CGTARG_Mem_AR_Dep(OP *pred_op, OP *succ_op, CG_DEP_KIND kind)
01879 {
01880
01881
01882 switch (kind) {
01883 case CG_DEP_MEMIN:
01884 {
01885
01886
01887
01888
01889
01890
01891
01892
01893
01894
01895
01896 BOOL mac_load = OP_c3_load(succ_op) && (!OP_memtrap(succ_op));
01897
01898 if (OP_store(pred_op) && mac_load) {
01899 Set_OP_ARdep(succ_op);
01900 }
01901 break;
01902 }
01903 case CG_DEP_MEMANTI:
01904 {
01905
01906
01907
01908
01909
01910
01911
01912
01913
01914
01915
01916
01917 if ((BB_zdl_body(OP_bb(pred_op)) || BB_loophead(OP_bb(pred_op)))) {
01918 BOOL mac_load = OP_c3_load(pred_op) && (!OP_memtrap(pred_op));
01919 if (mac_load && OP_store(succ_op)) {
01920 Set_OP_ARdep(pred_op);
01921 }
01922 }
01923 break;
01924 }
01925 default:
01926 break;
01927 }
01928 return;
01929 }
01930
01931
01932
01933
01934
01935
01936
01937
01938
01939 void
01940 CGTARG_Generate_Remainder_Branch(TN *trip_count, TN *label_tn,
01941 OPS *prolog_ops, OPS *body_ops)
01942 {
01943 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
01944 }
01945
01946
01947
01948
01949
01950
01951
01952
01953
01954
01955 BOOL CGTARG_OP_is_counted_loop(OP *op)
01956 {
01957 return FALSE;
01958 }
01959
01960
01961
01962
01963
01964
01965
01966
01967
01968
01969 void
01970 CGTARG_Generate_Branch_Cloop(OP *br_op,
01971 TN *unrolled_trip_count,
01972 TN *trip_count_tn,
01973 INT32 ntimes,
01974 TN *label_tn,
01975 OPS *prolog_ops,
01976 OPS *body_ops)
01977 {
01978 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
01979 }
01980
01981 static TN* asm_constraint_tn[10];
01982 static ISA_REGISTER_SUBCLASS asm_constraint_sc[10];
01983 static char asm_constraint_name[10][8];
01984 static INT asm_constraint_index;
01985
01986
01987 void
01988 CGTARG_Init_Asm_Constraints (void)
01989 {
01990
01991 Setup_Output_Parameter_Locations (MTYPE_To_TY(MTYPE_I8));
01992 for (INT i = 0; i < 10; ++i) {
01993 asm_constraint_tn[i] = NULL;
01994 asm_constraint_sc[i] = ISA_REGISTER_SUBCLASS_UNDEFINED;
01995 asm_constraint_name[i][0] = '\0';
01996 }
01997 asm_constraint_index = 0;
01998 }
01999
02000
02001
02002
02003
02004
02005 extern TN*
02006 CGTARG_TN_For_Asm_Operand (const char* constraint,
02007 const WN* load,
02008 TN* pref_tn,
02009 ISA_REGISTER_SUBCLASS* subclass, TYPE_ID id)
02010 {
02011
02012
02013
02014
02015 static const char* modifiers = "=&%";
02016 while (strchr(modifiers, *constraint))
02017 {
02018 constraint++;
02019 }
02020
02021
02022
02023
02024
02025
02026
02027 if (*constraint != 'm')
02028 {
02029 const char* m = constraint;
02030 while (*++m)
02031 {
02032 if (*m == 'm')
02033 {
02034 constraint = m;
02035 break;
02036 }
02037 }
02038 }
02039
02040
02041
02042 static const char* immediates = "in";
02043 while (strchr(immediates, *constraint) && *(constraint+1))
02044 {
02045 constraint++;
02046 }
02047
02048 TN* ret_tn;
02049
02050
02051 if (strchr(immediates, *constraint))
02052 {
02053 if (load && WN_operator(load)==OPR_LDID && WN_class(load)==CLASS_PREG)
02054 {
02055
02056 load = Preg_Is_Rematerializable(WN_load_offset(load), NULL);
02057 }
02058 FmtAssert(load && WN_operator(load) == OPR_INTCONST,
02059 ("Cannot find immediate operand for ASM"));
02060 ret_tn = Gen_Literal_TN(WN_const_val(load),
02061 MTYPE_bit_size(WN_rtype(load))/8);
02062 }
02063
02064 else if (isdigit(*constraint))
02065 {
02066 INT prev_index = *constraint - '0';
02067 FmtAssert(asm_constraint_tn[prev_index],
02068 ("numeric matching constraint refers to NULL value"));
02069 ret_tn = asm_constraint_tn[prev_index];
02070 }
02071 else if (strchr("m", *constraint))
02072 {
02073 TYPE_ID rtype = (load != NULL ? WN_rtype(load) : MTYPE_I4);
02074 FmtAssert(MTYPE_is_integral(rtype),
02075 ("ASM operand does not satisfy its constraint"));
02076 ret_tn = (pref_tn ? pref_tn : Build_TN_Of_Mtype(rtype));
02077 }
02078 else if ((*constraint == 'r') || (*constraint == 'a') ||
02079 (*constraint == 'b') || (*constraint == 'v') ||
02080 (*constraint == 'h') || (*constraint == 'l') ||
02081 (*constraint == 'd'))
02082 {
02083 TYPE_ID rtype;
02084 if (load != NULL) {
02085 rtype = WN_rtype(load);
02086 } else {
02087
02088
02089
02090 rtype = ((*constraint == 'b') ? MTYPE_B : MTYPE_I4);
02091 }
02092 ret_tn = (pref_tn ? pref_tn : Build_TN_Of_Mtype(rtype));
02093 }
02094 else if (*constraint == 't')
02095 {
02096 FmtAssert(pref_tn && TN_is_dedicated(pref_tn) &&
02097 TN_register_class(pref_tn)==ISA_REGISTER_CLASS_UNDEFINED,
02098 ("ASM constraint 't' requires a state register"));
02099 ret_tn = pref_tn;
02100 }
02101 else if (*constraint == 'f')
02102 {
02103 if (load && (WN_desc(load) != MTYPE_F4 || WN_rtype(load) != MTYPE_F4)) {
02104 FmtAssert(FALSE, ("ASM operand does not satisfy its constraint"));
02105 }
02106 ret_tn = (pref_tn ? pref_tn : Build_TN_Of_Mtype(MTYPE_F4));
02107 }
02108 else
02109 {
02110 FmtAssert(FALSE, ("ASM constraint <%s> not supported", constraint));
02111 }
02112
02113 asm_constraint_tn[asm_constraint_index] = ret_tn;
02114 asm_constraint_index++;
02115
02116 return ret_tn;
02117 }
02118
02119
02120 static char *
02121 Get_TN_Assembly_Name (TN *tn)
02122 {
02123 return "moo";
02124 }
02125
02126 void
02127 CGTARG_TN_And_Name_For_Asm_Constraint (char *constraint, TYPE_ID mtype,
02128 TYPE_ID desc, TN **tn, char **name)
02129 {
02130 INT i;
02131 if (*constraint == '=') {
02132
02133 CGTARG_TN_And_Name_For_Asm_Constraint (constraint+1,
02134 mtype, desc, tn, name);
02135 return;
02136 }
02137 if (mtype == MTYPE_V) {
02138
02139 if (*constraint == 'f') mtype = MTYPE_F8;
02140 else mtype = MTYPE_I8;
02141 }
02142 switch (*constraint) {
02143 case 'r':
02144 FmtAssert(MTYPE_is_integral(mtype),
02145 ("ASM constraint is integer but parameter is not"));
02146 break;
02147 case 'f':
02148 FmtAssert(MTYPE_is_float(mtype),
02149 ("ASM constraint is float but parameter is not"));
02150 break;
02151 case 'm':
02152 break;
02153 case '0':
02154 case '1':
02155 case '2':
02156 case '3':
02157 case '4':
02158 case '5':
02159 case '6':
02160 case '7':
02161 case '8':
02162 case '9':
02163 i = *constraint - '0';
02164 FmtAssert(asm_constraint_tn[i],
02165 ("numeric matching constraint refers to NULL value"));
02166 ++asm_constraint_index;
02167 *tn = asm_constraint_tn[i];
02168 *name = asm_constraint_name[i];
02169 return;
02170 case 'i':
02171
02172 *tn = NULL;
02173 *name = NULL;
02174 return;
02175 default:
02176 FmtAssert(FALSE, ("ASM constraint <%s> not supported", constraint));
02177 }
02178 PLOC ploc = Get_Output_Parameter_Location (MTYPE_To_TY(mtype));
02179 *tn = PREG_To_TN (MTYPE_To_PREG(mtype), PLOC_reg(ploc));
02180 asm_constraint_tn[asm_constraint_index] = *tn;
02181 *name = Get_TN_Assembly_Name(*tn);
02182 if (*constraint == 'm') {
02183 sprintf(asm_constraint_name[asm_constraint_index], "[%s]",
02184 *name);
02185 } else {
02186 sprintf(asm_constraint_name[asm_constraint_index], "%s",
02187 *name);
02188 }
02189 *name = asm_constraint_name[asm_constraint_index];
02190 ++asm_constraint_index;
02191 }
02192
02193
02194
02195
02196
02197
02198
02199 char CGTARG_Asm_Opnd_Modifiers[] = { 'r' };
02200 INT CGTARG_Num_Asm_Opnd_Modifiers = 1;
02201
02202 const char*
02203 CGTARG_Modified_Asm_Opnd_Name(char modifier, TN* tn, char *tn_name)
02204 {
02205 if (modifier == 'r') {
02206 return tn_name;
02207 }
02208 else {
02209 FmtAssert(FALSE, ("Unknown ASM operand modifier '%c'", modifier));
02210 }
02211
02212 }
02213
02214
02215
02216
02217
02218
02219
02220
02221 void
02222 CGTARG_Postprocess_Asm_String (char*)
02223 {
02224 }
02225
02226
02227
02228
02229
02230
02231
02232
02233
02234 BOOL CGTARG_Unconditional_Compare(OP *op, TOP* uncond_ver)
02235 {
02236 return FALSE;
02237 }
02238
02239
02240
02241
02242
02243
02244
02245
02246
02247 TOP CGTARG_Invert_Branch(BB* bb)
02248 {
02249 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
02250 }
02251
02252
02253
02254
02255
02256
02257
02258
02259
02260
02261 void CGTARG_Init_OP_cond_def_kind(OP *op)
02262 {
02263 if( OP_has_predicate(op) ) {
02264 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
02265 } else {
02266 {
02267 Set_OP_cond_def_kind(op, OP_ALWAYS_UNC_DEF);
02268 }
02269 }
02270 }
02271
02272
02273
02274
02275
02276
02277
02278
02279
02280
02281
02282 TOP CGTARG_Get_unc_Variant(TOP top)
02283 {
02284
02285 FmtAssert(FALSE,("NOT YET IMPLEMENTED"));
02286 return TOP_UNDEFINED;
02287 }
02288
02290
02291
02292
02293
02294 void
02295 Make_Branch_Conditional(BB *bb)
02296 {
02297 return;
02298 }
02299
02300
02301
02302
02303
02304
02305
02306
02307
02308
02309 BOOL
02310 CGTARG_Check_OP_For_HB_Suitability(OP *op)
02311 {
02312 switch(Eager_Level) {
02313 case EAGER_NONE:
02314 return FALSE;
02315 case EAGER_SAFE:
02316 if (OP_fadd(op) ||
02317 OP_fdiv(op) ||
02318 OP_fsub(op) ||
02319 OP_fmul(op) ||
02320 OP_load(op) ||
02321 OP_store(op) ||
02322 OP_prefetch(op) ||
02323
02324 OP_idiv(op) ||
02325 OP_imul(op) ||
02326 (OP_code(op) == TOP_mflo) ||
02327 (OP_code(op) == TOP_mfhi))
02328 return FALSE;
02329 else
02330 return TRUE;
02331 case EAGER_ARITH:
02332 if (OP_load(op) ||
02333 OP_store(op) ||
02334 OP_prefetch(op) ||
02335
02336 OP_fdiv(op) ||
02337 OP_idiv(op) ||
02338 OP_imul(op) ||
02339 (OP_code(op) == TOP_mflo) ||
02340 (OP_code(op) == TOP_mfhi))
02341 return FALSE;
02342 else
02343 return TRUE;
02344 case EAGER_DIVIDE:
02345 if (OP_load(op) ||
02346 OP_store(op) ||
02347 OP_prefetch(op) ||
02348 OP_idiv(op) ||
02349 OP_imul(op) ||
02350 (OP_code(op) == TOP_mflo) ||
02351 (OP_code(op) == TOP_mfhi))
02352 return FALSE;
02353 else
02354 return TRUE;
02355 case EAGER_MEMORY:
02356 case EAGER_OTHER:
02357 if (OP_idiv(op) ||
02358 OP_imul(op) ||
02359 (OP_code(op) == TOP_mflo) ||
02360 (OP_code(op) == TOP_mfhi))
02361 return FALSE;
02362 else
02363 return TRUE;
02364 default:
02365 FmtAssert(FALSE, ("Handle this case"));
02366 return FALSE;
02367 }
02368 }
02369