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 #define __STDC_LIMIT_MACROS
00041 #include <stdint.h>
00042 #if defined(BUILD_OS_DARWIN)
00043 #include <darwin_elf.h>
00044 #else
00045 #include <elf.h>
00046 #endif
00047 #include <sys/elf_whirl.h>
00048 #include <cmplrs/host.h>
00049 #include <assert.h>
00050 #define USE_STANDARD_TYPES
00051 #include "defs.h"
00052 #include "config.h"
00053 #include "wn.h"
00054 #include "strtab.h"
00055 #include "stab.h"
00056 #include "const.h"
00057 #include "irbdata.h"
00058 #define USE_DST_INTERNALS
00059 #include "dwarf_DST_mem.h"
00060 #include "pu_info.h"
00061 #include "ir_bwrite.h"
00062 #include "ipc_file.h"
00063 #include "ipl_summary.h"
00064 #include "ipa_cg.h"
00065 #include "ipa_section_annot.h"
00066 #include "erglob.h"
00067 #include "ipc_file.h"
00068 #include "ipa_lno_info.h"
00069 #include "ipa_lno_file.h"
00070 #include "ipa_lno_write.h"
00071 #include "ipa_lno_summary.h"
00072 #include "ipc_compile.h"
00073 #include "ipa_section.h"
00074 #include "ipaa.h"
00075 #include "ipa_option.h"
00076 #include "ipa_summary.h"
00077 #include "linker.h"
00078 #include "process.h"
00079 #include "ipo_defs.h"
00080 #include "ipc_symtab_merge.h"
00081 #include "ipa_reshape.h"
00082
00083
00084
00085
00086
00087
00088
00089 static void IPA_LNO_Map_Term(IPA_NODE* node,
00090 TERM* term,
00091 IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00092 {
00093 INT32 size;
00094 if (term->Get_type() == LTKIND_IV) {
00095 INT ivar_idx = term->Get_desc();
00096 SUMMARY_PROCEDURE* osp = node->Summary_Proc();
00097 IVAR* ivar = IPA_get_ivar_array(node, size);
00098 ivar += ivar_idx;
00099 IVAR ivar_mapped = *ivar;
00100 if (ivar->Is_Formal()) {
00101 UINT32 old_formal_position = ivar_mapped.Formal_Position();
00102 IPA_NODE_SECTION_INFO* sec = node->Section_Annot();
00103 STATE* state = sec->Get_formal(old_formal_position);
00104 if (state->Is_removed()) {
00105 VALUE_DYN_ARRAY* formal_array = node->Cprop_Annot();
00106 SUMMARY_VALUE* sv = &(*formal_array)[old_formal_position];
00107 if (sv->Is_constant()) {
00108 INT64 int_value = sv->Get_int_const_value();
00109 term->Set_type(LTKIND_CONST);
00110 term->Set_coeff(int_value);
00111 term->Set_desc(CONST_DESC);
00112 term->Set_projected_level(0);
00113 return;
00114 } else if (sv->Is_const_st()) {
00115 ST_IDX st_idx = sv->Get_const_st_idx();
00116 ivar_mapped.Set_St_Idx(st_idx);
00117 ivar_mapped.Set_Offset(0);
00118 ivar_mapped.Set_Mtype(TY_mtype(ST_type(st_idx)));
00119 } else {
00120 FmtAssert(FALSE,
00121 ("IPA_LNO_Map_Term: Unexpected constant index type"));
00122 }
00123 } else {
00124 INT removed_count = 0;
00125 SUMMARY_PROCEDURE* osp = node->Summary_Proc();
00126 for (INT i = 0; i < old_formal_position; i++) {
00127 STATE* state_local = sec->Get_formal(i);
00128 if (state_local->Is_removed())
00129 removed_count++;
00130 }
00131 INT32 new_formal_position = ivar_mapped.Formal_Position();
00132 new_formal_position -= removed_count;
00133 FmtAssert(new_formal_position >= 0,
00134 ("IPA_LNO_Map_Term: negative formal position"));
00135 ivar_mapped.Set_Formal_Position(new_formal_position);
00136 }
00137 }
00138 INT mapped_idx = -1;
00139 INT i;
00140
00141 for (i = 0; i < IPA_LNO_Summary->Ivar_Count(); i++) {
00142 if (*IPA_LNO_Summary->Ivar(i) == ivar_mapped)
00143 break;
00144 }
00145 if (i < IPA_LNO_Summary->Ivar_Count()) {
00146 mapped_idx = i;
00147 } else {
00148 IPA_LNO_Summary->Ivar_Array()->AddElement(ivar_mapped);
00149 mapped_idx = IPA_LNO_Summary->Ivar_Array()->Lastidx();
00150 }
00151 term->Set_desc(mapped_idx);
00152 }
00153 }
00154
00155
00156
00157
00158
00159
00160
00161 UINT64 IPA_LNO_Get_Key(TERM* term, INT num_terms)
00162 {
00163 UINT64 key = 0;
00164
00165
00166
00167
00168 UINT64 temp = 0;
00169 temp = (INT64) num_terms << 56;
00170 key = key | temp;
00171 temp = (INT64) term->Get_type() << 48;
00172 key = key | temp;
00173 temp = (INT64) term->Get_desc() << 32;
00174 key = key | temp;
00175 temp = (INT64) term->Get_coeff();
00176 key = key | temp;
00177 return key;
00178 }
00179
00180
00181
00182
00183
00184
00185
00186
00187 static void IPA_LNO_Insert_Terms(TERM* term_in,
00188 INT idx,
00189 INT count,
00190 IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00191 {
00192 MEM_POOL* mem_pool = IPA_LNO_Summary->Mem_Pool();
00193 UINT64 key = IPA_LNO_Get_Key(term_in, count);
00194 TERM_HASH_TABLE *hash_table = IPA_LNO_Summary->Term_Hash_Table();
00195 INTEGER_ARRAY* int_array;
00196 INT id;
00197
00198 if (int_array = hash_table->Find(key)) {
00199 for (INT i = 0; i <= int_array->Lastidx(); i++) {
00200 id = (*int_array)[i];
00201 TERM* start_term = IPA_LNO_Summary->Term(id);
00202 if (term_in->Is_equal(start_term, count))
00203 return;
00204 }
00205
00206 id = int_array->Newidx();
00207 (*int_array)[id] = idx;
00208 return;
00209 }
00210
00211
00212
00213
00214 int_array = (INTEGER_ARRAY*) CXX_NEW(INTEGER_ARRAY(mem_pool), mem_pool);
00215 id = int_array->Newidx();
00216 (*int_array)[id] = idx;
00217 hash_table->Enter(key, int_array);
00218 }
00219
00220
00221
00222
00223
00224
00225
00226
00227 static INT IPA_LNO_Search_For_Terms(LINEX* lx,
00228 IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00229 {
00230 TERM* term = lx->Get_term(0);
00231 UINT64 key = IPA_LNO_Get_Key(term, lx->Num_terms());
00232 TERM_HASH_TABLE* hash_table = IPA_LNO_Summary->Term_Hash_Table();
00233 INTEGER_ARRAY* int_array = hash_table->Find(key);
00234 if (!int_array)
00235 return 0;
00236
00237 for (INT i = 0; i <= int_array->Lastidx(); i++) {
00238 INT id = (*int_array)[i];
00239 TERM* term_local = IPA_LNO_Summary->Term(id);
00240 if (term_local->Is_equal(term, lx->Num_terms())) {
00241
00242 return id + 1;
00243 }
00244 }
00245 return 0;
00246 }
00247
00248
00249
00250
00251
00252
00253
00254 static INT IPA_LNO_Map_Projected_Node_Array(IPA_NODE* node,
00255 PROJECTED_ARRAY* pna_in,
00256 IPA_LNO_WRITE_SUMMARY*
00257 IPA_LNO_Summary)
00258 {
00259 INT new_idx = -1;
00260 INT reuse_linex_idx = -1;
00261 PROJECTED_ARRAY* projected_node_array
00262 = IPA_LNO_Summary->Projected_Node_Array();
00263 TERM_ARRAY* term_array = IPA_LNO_Summary->Term_Array();
00264
00265 for (INT i = 0; i <= pna_in->Lastidx(); i++) {
00266 INT idx = projected_node_array->Newidx();
00267 if (i == 0)
00268 new_idx = idx;
00269 PROJECTED_NODE* pn_in = &(*pna_in)[i];
00270 PROJECTED_NODE* pn_out = &(*projected_node_array)[idx];
00271 pn_out->Set_flags(pn_in->Get_flags());
00272
00273
00274 LINEX* lx_upper = pn_in->Get_upper_linex();
00275 if (!pn_in->Is_messy_ub() && lx_upper->Num_terms() != -1) {
00276 for (INT j = 0; j <= lx_upper->Num_terms(); j++) {
00277 IPA_LNO_Map_Term(node, lx_upper->Get_term(j), IPA_LNO_Summary);
00278 }
00279 INT reuse_linex_idx = IPA_LNO_Search_For_Terms(lx_upper,IPA_LNO_Summary);
00280 if (reuse_linex_idx == 0) {
00281 for (INT j = 0; j <= lx_upper->Num_terms(); j++) {
00282 term_array->AddElement(*(lx_upper->Get_term(j)));
00283 }
00284 INT first_term_idx = term_array->Lastidx() - lx_upper->Num_terms();
00285 IPA_LNO_Insert_Terms(lx_upper->Get_term(0), first_term_idx,
00286 lx_upper->Num_terms(), IPA_LNO_Summary);
00287 pn_out->Set_ub_term_index(first_term_idx);
00288 } else {
00289 pn_out->Set_ub_term_index(reuse_linex_idx-1);
00290 }
00291 pn_out->Set_ub_term_count(lx_upper->Num_terms()+1);
00292 } else {
00293 pn_out->Set_ub_term_index(-1);
00294 pn_out->Set_ub_term_count(0);
00295 }
00296
00297
00298 LINEX* lx_lower = pn_in->Get_lower_linex();
00299 if (!pn_in->Is_messy_lb() && lx_lower->Num_terms() != -1) {
00300 for (INT j = 0; j <= lx_lower->Num_terms(); j++) {
00301 IPA_LNO_Map_Term(node, lx_lower->Get_term(j), IPA_LNO_Summary);
00302 }
00303 INT reuse_linex_idx = IPA_LNO_Search_For_Terms(lx_lower,IPA_LNO_Summary);
00304 if (reuse_linex_idx == 0) {
00305 for (INT j = 0; j <= lx_lower->Num_terms(); j++) {
00306 term_array->AddElement(*(lx_lower->Get_term(j)));
00307 }
00308 INT first_term_idx = term_array->Lastidx() - lx_lower->Num_terms();
00309 IPA_LNO_Insert_Terms(lx_lower->Get_term(0), first_term_idx,
00310 lx_lower->Num_terms(), IPA_LNO_Summary);
00311 pn_out->Set_lb_term_index(first_term_idx);
00312 } else {
00313 pn_out->Set_lb_term_index(reuse_linex_idx-1);
00314 }
00315 pn_out->Set_lb_term_count(lx_lower->Num_terms()+1);
00316 } else {
00317 pn_out->Set_lb_term_index(-1);
00318 pn_out->Set_lb_term_count(0);
00319 }
00320
00321
00322 LINEX* lx_step = pn_in->Get_step_linex();
00323 if (!pn_in->Is_messy_step() && lx_step->Num_terms() != -1) {
00324 for (INT j = 0; j <= lx_step->Num_terms(); j++) {
00325 IPA_LNO_Map_Term(node, lx_step->Get_term(j), IPA_LNO_Summary);
00326 }
00327 INT reuse_linex_idx = IPA_LNO_Search_For_Terms(lx_step,IPA_LNO_Summary);
00328 if (reuse_linex_idx == 0) {
00329 for (INT j = 0; j <= lx_step->Num_terms(); j++) {
00330 term_array->AddElement(*(lx_step->Get_term(j)));
00331 }
00332 INT first_term_idx = term_array->Lastidx() - lx_step->Num_terms();
00333 IPA_LNO_Insert_Terms(lx_step->Get_term(0), first_term_idx,
00334 lx_step->Num_terms(), IPA_LNO_Summary);
00335 pn_out->Set_step_term_index(first_term_idx);
00336 } else {
00337 pn_out->Set_step_term_index(reuse_linex_idx-1);
00338 }
00339 pn_out->Set_step_term_count(lx_step->Num_terms()+1);
00340 } else {
00341 pn_out->Set_step_term_index(-1);
00342 pn_out->Set_step_term_count(0);
00343 }
00344
00345
00346 LINEX* lx_segment_length = pn_in->Get_segment_length_linex();
00347 if (lx_segment_length != NULL) {
00348 for (INT j = 0; j <= lx_segment_length->Num_terms(); j++) {
00349 IPA_LNO_Map_Term(node, lx_segment_length->Get_term(j),IPA_LNO_Summary);
00350 }
00351 INT reuse_linex_idx = IPA_LNO_Search_For_Terms(lx_segment_length,
00352 IPA_LNO_Summary);
00353 if (reuse_linex_idx == 0) {
00354 for (INT j = 0; j <= lx_segment_length->Num_terms(); j++) {
00355 term_array->AddElement(*(lx_segment_length->Get_term(j)));
00356 }
00357 INT first_term_idx = term_array->Lastidx() -
00358 lx_segment_length->Num_terms();
00359 IPA_LNO_Insert_Terms(lx_segment_length->Get_term(0), first_term_idx,
00360 lx_segment_length->Num_terms(), IPA_LNO_Summary);
00361 pn_out->Set_segment_length_term_index(first_term_idx);
00362 } else {
00363 pn_out->Set_segment_length_term_index(reuse_linex_idx-1);
00364 }
00365 pn_out->Set_segment_length_term_count(lx_segment_length->Num_terms()+1);
00366 } else {
00367 pn_out->Set_segment_length_term_index(-1);
00368 pn_out->Set_segment_length_term_count(0);
00369 }
00370
00371
00372 LINEX* lx_segment_stride = pn_in->Get_segment_stride_linex();
00373 if (lx_segment_stride != NULL) {
00374 for (INT j = 0; j <= lx_segment_stride->Num_terms(); j++) {
00375 IPA_LNO_Map_Term(node, lx_segment_stride->Get_term(j),IPA_LNO_Summary);
00376 }
00377 INT reuse_linex_idx = IPA_LNO_Search_For_Terms(lx_segment_stride,
00378 IPA_LNO_Summary);
00379 if (reuse_linex_idx == 0) {
00380 for (INT j = 0; j <= lx_segment_stride->Num_terms(); j++) {
00381 term_array->AddElement(*(lx_segment_stride->Get_term(j)));
00382 }
00383 INT first_term_idx = term_array->Lastidx() -
00384 lx_segment_stride->Num_terms();
00385 IPA_LNO_Insert_Terms(lx_segment_stride->Get_term(0), first_term_idx,
00386 lx_segment_stride->Num_terms(), IPA_LNO_Summary);
00387 pn_out->Set_segment_stride_term_index(first_term_idx);
00388 } else {
00389 pn_out->Set_segment_stride_term_index(reuse_linex_idx-1);
00390 }
00391 pn_out->Set_segment_stride_term_count(lx_segment_stride->Num_terms()+1);
00392 } else {
00393 pn_out->Set_segment_stride_term_index(-1);
00394 pn_out->Set_segment_stride_term_count(0);
00395 }
00396 }
00397
00398 return new_idx;
00399 }
00400
00401
00402
00403
00404
00405
00406
00407 static INT IPA_LNO_Map_Projected_Region(IPA_NODE* node,
00408 PROJECTED_REGION* pr_in,
00409 IPA_LNO_WRITE_SUMMARY*
00410 IPA_LNO_Summary)
00411 {
00412 PROJECTED_REGION_ARRAY* projected_region_array =
00413 IPA_LNO_Summary->Projected_Region_Array();
00414 INT idx = projected_region_array->Newidx();
00415 PROJECTED_REGION* pr_out = &(*projected_region_array)[idx];
00416 pr_out->Copy_write(pr_in);
00417 if (pr_in->Is_messy_region()) {
00418 pr_out->Set_id(-1);
00419 } else {
00420 INT new_idx = pr_in->Get_projected_array()
00421 ? IPA_LNO_Map_Projected_Node_Array(node,
00422 pr_in->Get_projected_array(), IPA_LNO_Summary) : -1;
00423 pr_out->Set_id(new_idx);
00424 }
00425 return idx;
00426 }
00427
00428
00429
00430
00431
00432
00433
00434 static INT IPA_LNO_Map_Formal_Array(IPA_NODE* node,
00435 INT old_position,
00436 INT new_position,
00437 STATE* state,
00438 IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00439 {
00440 IPA_LNO_SUMMARY_FORMAL_ARRAY* formal_array
00441 = IPA_LNO_Summary->Formal_Array();
00442 INT idx = formal_array->Newidx();
00443 IPA_LNO_SUMMARY_FORMAL* sf = &((*formal_array)[idx]);
00444 SUMMARY_PROCEDURE* osp = node->Summary_Proc();
00445 INT formal_index = osp->Get_formal_index() + old_position;
00446 SUMMARY_FORMAL* old_formal_array = IPA_get_formal_array(node);
00447 SUMMARY_FORMAL* osf = &old_formal_array[formal_index];
00448 INT symbol_index = osf->Get_symbol_index();
00449 SUMMARY_SYMBOL* old_symbol_array = IPA_get_symbol_array(node);
00450 SUMMARY_SYMBOL* oss = &old_symbol_array[symbol_index];
00451 sf->Set_Machine_Type(osf->Get_machine_type());
00452 sf->Clear_State();
00453 sf->Set_Position(new_position);
00454 if (state->Is_scalar()) {
00455 sf->Set_Scalar();
00456 IPAA_NODE_INFO* ipaa = node->Mod_Ref_Info();
00457 if (ipaa == NULL || ipaa->Is_formal_dref_elmt(old_position)
00458 || ipaa->Is_formal_iref_elmt(old_position))
00459 sf->Set_Use();
00460 if (ipaa == NULL || ipaa->Is_formal_dmod_elmt(old_position)
00461 || ipaa->Is_formal_imod_elmt(old_position))
00462 sf->Set_May_Kill();
00463 sf->Set_Mod_Array_Section_Index(-1);
00464 sf->Set_Ref_Array_Section_Index(-1);
00465 sf->Set_Decl_Array_Section_Index(-1);
00466 } else if (osf->Get_region_index() != -1) {
00467 sf->Set_Array();
00468 sf->Reset_Scalar();
00469 if (state->Get_projected_mod_region() == NULL) {
00470 sf->Set_Mod_Array_Section_Index(-1);
00471 } else {
00472 sf->Set_May_Kill();
00473 INT idx_mod = IPA_LNO_Map_Projected_Region(node,
00474 state->Get_projected_mod_region(), IPA_LNO_Summary);
00475 sf->Set_Mod_Array_Section_Index(idx_mod);
00476 }
00477 if (state->Get_projected_ref_region() == NULL) {
00478 sf->Set_Ref_Array_Section_Index(-1);
00479 } else {
00480 sf->Set_Use();
00481 INT idx_ref = IPA_LNO_Map_Projected_Region(node,
00482 state->Get_projected_ref_region(), IPA_LNO_Summary);
00483 sf->Set_Ref_Array_Section_Index(idx_ref);
00484 }
00485 PROJECTED_REGION* proj_region_array
00486 = IPA_get_proj_region_array(node);
00487 INT idx_region = osf->Get_region_index();
00488 REGION_ARRAYS* region_array = IPA_get_region_array(node);
00489 REGION_ARRAYS* ra = ®ion_array[idx_region];
00490 INT idx_proj_region = ra->Get_idx();
00491 PROJECTED_REGION* pr_decl_old = &proj_region_array[idx_proj_region];
00492 PROJECTED_REGION* pr_decl_new = Projected_Region_To_Memory(node,
00493 pr_decl_old, &IPA_LNO_mem_pool);
00494 INT idx_decl = IPA_LNO_Map_Projected_Region(node, pr_decl_new,
00495 IPA_LNO_Summary);
00496 sf->Set_Decl_Array_Section_Index(idx_decl);
00497 } else {
00498 sf->Set_Unknown();
00499 sf->Set_Mod_Array_Section_Index(-1);
00500 sf->Set_Ref_Array_Section_Index(-1);
00501 sf->Set_Decl_Array_Section_Index(-1);
00502 }
00503 return idx;
00504 }
00505
00506
00507
00508
00509
00510
00511
00512
00513
00514
00515
00516
00517
00518
00519
00520 static void IPA_LNO_Map_Global_Array(IPA_NODE* node,
00521 GLOBAL_ARRAY_INFO* css,
00522 IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00523 {
00524 PROJECTED_REGION* pr_mod = css->Get_projected_mod_region();
00525 INT idx_mod = (pr_mod == NULL) ?
00526 -1 : IPA_LNO_Map_Projected_Region(node, pr_mod, IPA_LNO_Summary);
00527
00528 PROJECTED_REGION* pr_ref = css->Get_projected_ref_region();
00529 INT idx_ref = (pr_ref == NULL) ?
00530 -1 : IPA_LNO_Map_Projected_Region(node, pr_ref, IPA_LNO_Summary);
00531
00532 IPA_LNO_SUMMARY_GLOBAL_ARRAY* globals = IPA_LNO_Summary->Global_Array();
00533 globals->AddElement(IPA_LNO_SUMMARY_GLOBAL(css->St_Idx(),
00534 idx_mod, idx_ref,
00535 FALSE, FALSE));
00536 }
00537
00538
00539
00540
00541
00542
00543
00544
00545
00546
00547 static INT IPA_LNO_Map_Value(SUMMARY_VALUE* svv_old,
00548 INT formal_index_base,
00549 INT global_index_base,
00550 IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00551 {
00552 DYN_ARRAY<SUMMARY_VALUE>* value_array = IPA_LNO_Summary->Value_Array();
00553 INT idx = value_array->Newidx();
00554 SUMMARY_VALUE* svv_new = &((*value_array)[idx]);
00555 bcopy(svv_old, svv_new, sizeof(SUMMARY_VALUE));
00556 if (svv_old->Is_formal()) {
00557 svv_new->Set_formal_index(formal_index_base + svv_old->Get_formal_index());
00558 } else if (svv_old->Is_global()) {
00559 svv_new->Set_global_index(global_index_base + svv_old->Get_global_index());
00560 }
00561 return idx;
00562 }
00563
00564
00565
00566
00567
00568
00569
00570
00571
00572
00573 static void IPA_LNO_Map_Expr_Node(SUMMARY_EXPR* sxx_old,
00574 SUMMARY_EXPR* sxx_new,
00575 INT value_index_base,
00576 INT expr_index_base,
00577 INT kid)
00578 {
00579 if (sxx_old->Is_expr_value(kid)) {
00580 INT old_index = sxx_old->Get_node_index(kid);
00581 sxx_new->Set_node_index(kid, value_index_base + old_index);
00582 } else if (sxx_old->Is_expr_expr(kid)) {
00583 INT old_index = sxx_old->Get_node_index(kid);
00584 sxx_new->Set_node_index(kid, expr_index_base + old_index);
00585 } else {
00586 FmtAssert(FALSE,
00587 ("IPA_LNO_Map_Expr: Not handling other cases yet"));
00588 }
00589 }
00590
00591
00592
00593
00594
00595
00596
00597
00598
00599 static INT IPA_LNO_Map_Expr(SUMMARY_EXPR* sxx_old,
00600 INT value_index_base,
00601 INT expr_index_base,
00602 IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00603 {
00604 DYN_ARRAY<SUMMARY_EXPR>* expr_array = IPA_LNO_Summary->Expr_Array();
00605 INT idx = expr_array->Newidx();
00606 SUMMARY_EXPR* sxx_new = &((*expr_array)[idx]);
00607 bcopy(sxx_old, sxx_new, sizeof(SUMMARY_EXPR));
00608 if (sxx_old->Has_const_operand()) {
00609 IPA_LNO_Map_Expr_Node(sxx_old, sxx_new, value_index_base,
00610 expr_index_base, 0);
00611 } else {
00612 IPA_LNO_Map_Expr_Node(sxx_old, sxx_new, value_index_base,
00613 expr_index_base, 0);
00614 IPA_LNO_Map_Expr_Node(sxx_old, sxx_new, value_index_base,
00615 expr_index_base, 1);
00616 }
00617 return idx;
00618 }
00619
00620
00621
00622
00623
00624
00625 extern void IPA_LNO_Map_Node(IPA_NODE* node,
00626 IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00627 {
00628
00629 IPA_NODE* ipan_main_entry = Main_Entry(node);
00630 IPA_NODE_CONTEXT context(ipan_main_entry);
00631
00632
00633 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE))
00634 fprintf(stdout, "\nLNO mapping for function %s\n", node->Name());
00635
00636 IPA_LNO_SUMMARY_PROCEDURE_ARRAY* procedure_array
00637 = IPA_LNO_Summary->Procedure_Array();
00638 INT idx = procedure_array->Newidx();
00639 IPA_LNO_SUMMARY_PROCEDURE* sp = &((*procedure_array)[idx]);
00640 sp->Reset_Has_Incomplete_Array_Info();
00641 SUMMARY_PROCEDURE* osp = node->Summary_Proc();
00642 if (osp->Has_incomplete_array_info())
00643 sp->Set_Has_Incomplete_Array_Info();
00644 sp->Set_St_Idx(ST_st_idx(node->Func_ST()));
00645
00646
00647 sp->Set_Formal_Index(-1);
00648 sp->Set_Formal_Count(0);
00649 IPA_NODE_SECTION_INFO* sec = node->Section_Annot();
00650 if (sec != NULL) {
00651 INT k = 0;
00652 for (INT i = 0; i < osp->Get_formal_count(); i++) {
00653 STATE* state = sec->Get_formal(i);
00654 if (!state->Is_removed()) {
00655 INT idx = IPA_LNO_Map_Formal_Array(node, i, k, state,
00656 IPA_LNO_Summary);
00657 if (k++ == 0)
00658 sp->Set_Formal_Index(idx);
00659 }
00660 }
00661 sp->Set_Formal_Count(k);
00662 }
00663
00664 IPAA_NODE_INFO* modref_info = node->Mod_Ref_Info();
00665
00666
00667 IPA_LNO_SUMMARY_GLOBAL_ARRAY* globals = IPA_LNO_Summary->Global_Array();
00668 INT global_count = 0;
00669 sp->Set_Global_Index(-1);
00670 ST* st;
00671 INT i;
00672 FOREACH_SYMBOL (GLOBAL_SYMTAB, st, i) {
00673 if (ST_class(st) == CLASS_VAR &&
00674 ST_base_idx(st) == ST_st_idx(st) &&
00675 TY_kind(ST_type(st)) != KIND_ARRAY &&
00676 !ST_is_split_common(st)) {
00677 ST_IDX st_idx = ST_st_idx(st);
00678 BOOL scalar_mod = modref_info == NULL
00679 || modref_info->Is_def_elmt(ST_IDX_index(st_idx));
00680 BOOL scalar_ref = modref_info == NULL
00681 || modref_info->Is_eref_elmt(ST_IDX_index(st_idx));
00682 if (scalar_mod || scalar_ref || ST_sclass(st) == SCLASS_PSTATIC) {
00683
00684 if (ST_sclass(st) == SCLASS_PSTATIC) {
00685 if (!ST_is_const_var(st))
00686 scalar_mod = TRUE;
00687 scalar_ref = TRUE;
00688 }
00689
00690 COMMON_BLOCK_ELEMENTS_MAP::const_iterator block_iter =
00691 Common_Block_Elements_Map->find(st_idx);
00692 if (block_iter == Common_Block_Elements_Map->end()) {
00693
00694 globals->AddElement(IPA_LNO_SUMMARY_GLOBAL(st_idx,
00695 -1, -1,
00696 scalar_mod, scalar_ref));
00697 if (global_count++ == 0)
00698 sp->Set_Global_Index(globals->Lastidx());
00699 }
00700 else {
00701
00702 const BLOCK_ELEMENTS* block = (*block_iter).second;
00703 BLOCK_ELEMENTS::const_iterator element = block->begin();
00704 BLOCK_ELEMENTS::const_iterator element_end = block->end();
00705
00706 for (; element != element_end; ++element) {
00707 ST_IDX elem_st_idx = (*element).second;
00708 if (ST_class(elem_st_idx) == CLASS_VAR &&
00709 TY_kind(ST_type(elem_st_idx)) != KIND_ARRAY) {
00710
00711 globals->AddElement(IPA_LNO_SUMMARY_GLOBAL(elem_st_idx,
00712 -1, -1,
00713 scalar_mod,
00714 scalar_ref));
00715 if (global_count++ == 0)
00716 sp->Set_Global_Index(globals->Lastidx());
00717 }
00718 }
00719 }
00720 }
00721 }
00722 }
00723
00724 if (sec != NULL) {
00725 ST_IDX st_idx;
00726 GLOBAL_ARRAY_LIST* csl = NULL;
00727 GLOBAL_ARRAY_TABLE* cst = sec->Global_Array_Table();
00728 GLOBAL_ARRAY_TABLE_ITER cst_iter(cst);
00729 while (cst_iter.Step(&st_idx, &csl)) {
00730 GLOBAL_ARRAY_LIST_ITER iter(csl);
00731 if (csl->Is_messy())
00732 sp->Set_Has_Incomplete_Array_Info();
00733 for (iter.First(); !iter.Is_Empty(); iter.Next()) {
00734 IPA_LNO_Map_Global_Array(node, iter.Cur(), IPA_LNO_Summary);
00735 if (global_count++ == 0)
00736 sp->Set_Global_Index(globals->Lastidx());
00737 }
00738 }
00739 }
00740 sp->Set_Global_Count(global_count);
00741
00742
00743 sp->Set_Value_Index(-1);
00744 sp->Set_Value_Count(0);
00745 INT value_count_base = IPA_LNO_Summary->Value_Count();
00746 if (sec != NULL) {
00747 DYN_ARRAY<SUMMARY_VALUE>* sv = sec->Get_value();
00748 for (INT i = 0; i <= sv->Lastidx(); i++) {
00749 SUMMARY_VALUE* svv = &(*sv)[i];
00750 INT idx = IPA_LNO_Map_Value(svv, sp->Formal_Index(),
00751 sp->Global_Index(), IPA_LNO_Summary);
00752 if (i == 0)
00753 sp->Set_Value_Index(idx);
00754 }
00755 sp->Set_Value_Count(sv->Lastidx() + 1);
00756 }
00757
00758
00759 sp->Set_Expr_Index(-1);
00760 sp->Set_Expr_Count(0);
00761 INT expr_count_base = IPA_LNO_Summary->Expr_Count();
00762 if (sec != NULL) {
00763 DYN_ARRAY<SUMMARY_EXPR>* sx = sec->Get_expr();
00764 for (INT i = 0; i <= sx->Lastidx(); i++) {
00765 SUMMARY_EXPR* sxx = &(*sx)[i];
00766 INT idx = IPA_LNO_Map_Expr(sxx, value_count_base, expr_count_base,
00767 IPA_LNO_Summary);
00768 if (i == 0)
00769 sp->Set_Expr_Index(idx);
00770 }
00771 sp->Set_Expr_Count(sx->Lastidx() + 1);
00772 }
00773 }
00774
00775
00776
00777
00778
00779
00780
00781
00782
00783 static IPA_LNO_WRITE_FILE *IPA_LNO_Open_Output_Info(char* output_file)
00784 {
00785 Set_Error_Phase("Writing IPA LNO file");
00786 IPA_LNO_WRITE_FILE* IPA_LNO_Output_File =
00787 CXX_NEW(IPA_LNO_WRITE_FILE(), Malloc_Mem_Pool);
00788 IPA_LNO_Output_File->Open_Write_File(output_file);
00789 if (IPA_LNO_Output_File->ofl == NULL)
00790 ErrMsg(EC_IPALNO_Create, IPA_LNO_Output_File->ofl->file_name, errno);
00791 return IPA_LNO_Output_File;
00792 }
00793
00794
00795
00796
00797
00798
00799
00800 static void IPA_LNO_Write_Sections(IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary,
00801 IPA_LNO_WRITE_FILE* IPA_LNO_Output_File)
00802 {
00803 char* buffer = NULL;
00804 INT buffer_size = 0;
00805 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE))
00806 fprintf(stdout, "\n+++ BEGIN WRITING IPA LNO FILE +++\n");
00807 if (IPA_LNO_Summary->Ivar_Count() > 0) {
00808 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00809 fprintf(stdout, "Writing %d ivars:\n", IPA_LNO_Summary->Ivar_Count());
00810 for (INT i = 0; i < IPA_LNO_Summary->Ivar_Count(); i++)
00811 IPA_LNO_Summary->Ivar(i)->IPA_LNO_Print_File(stdout, i);
00812 }
00813 buffer = (char *) IPA_LNO_Summary->Ivar(0);
00814 buffer_size = sizeof(IVAR) * IPA_LNO_Summary->Ivar_Count();
00815 IPA_LNO_Output_File->Write_Section(IPA_IVAR, IPA_IVAR_NAME,
00816 buffer, buffer_size);
00817 }
00818 if (IPA_LNO_Summary->Procedure_Count() > 0) {
00819 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00820 fprintf(stdout, "Writing %d procedures:\n",
00821 IPA_LNO_Summary->Procedure_Count());
00822 for (INT i = 0; i < IPA_LNO_Summary->Procedure_Count(); i++)
00823 IPA_LNO_Summary->Procedure(i)->Print(stdout, i);
00824 }
00825 buffer = (char *) IPA_LNO_Summary->Procedure(0);
00826 buffer_size = sizeof(IPA_LNO_SUMMARY_PROCEDURE)
00827 * IPA_LNO_Summary->Procedure_Count();
00828 IPA_LNO_Output_File->Write_Section(IPA_PROCEDURE, IPA_PROCEDURE_NAME,
00829 buffer, buffer_size);
00830 }
00831 if (IPA_LNO_Summary->Formal_Count() > 0) {
00832 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00833 fprintf(stdout, "Writing %d formals:\n",
00834 IPA_LNO_Summary->Formal_Count());
00835 for (INT i = 0; i < IPA_LNO_Summary->Formal_Count(); i++)
00836 IPA_LNO_Summary->Formal(i)->Print(stdout, i);
00837 }
00838 buffer = (char *) IPA_LNO_Summary->Formal(0);
00839 buffer_size = sizeof(IPA_LNO_SUMMARY_FORMAL)
00840 * IPA_LNO_Summary->Formal_Count();
00841 IPA_LNO_Output_File->Write_Section(IPA_FORMAL, IPA_FORMAL_NAME,
00842 buffer, buffer_size);
00843 }
00844 if (IPA_LNO_Summary->Global_Count() > 0) {
00845 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00846 fprintf(stdout, "Writing %d globals:\n",
00847 IPA_LNO_Summary->Global_Count());
00848 for (INT i = 0; i < IPA_LNO_Summary->Global_Count(); i++)
00849 IPA_LNO_Summary->Global(i)->Print(stdout, i);
00850 }
00851 buffer = (char *) IPA_LNO_Summary->Global(0);
00852 buffer_size = sizeof(IPA_LNO_SUMMARY_GLOBAL)
00853 * IPA_LNO_Summary->Global_Count();
00854 IPA_LNO_Output_File->Write_Section(IPA_GLOBAL, IPA_GLOBAL_NAME,
00855 buffer, buffer_size);
00856 }
00857 if (IPA_LNO_Summary->Projected_Region_Count() > 0) {
00858 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00859 fprintf(stdout, "Writing %d projected regions:\n",
00860 IPA_LNO_Summary->Projected_Region_Count());
00861 for (INT i = 0; i < IPA_LNO_Summary->Projected_Region_Count(); i++)
00862 IPA_LNO_Summary->Projected_Region(i)->IPA_LNO_Print_File(stdout, i);
00863 }
00864 buffer = (char *) IPA_LNO_Summary->Projected_Region(0);
00865 buffer_size = sizeof(PROJECTED_REGION)
00866 * IPA_LNO_Summary->Projected_Region_Count();
00867 IPA_LNO_Output_File->Write_Section(IPA_PROJECTED_REGION,
00868 IPA_PROJECTED_REGION_NAME, buffer, buffer_size);
00869 }
00870 if (IPA_LNO_Summary->Projected_Node_Count() > 0) {
00871 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00872 fprintf(stdout, "Writing %d projected nodes:\n",
00873 IPA_LNO_Summary->Projected_Node_Count());
00874 for (INT i = 0; i < IPA_LNO_Summary->Projected_Node_Count(); i++)
00875 IPA_LNO_Summary->Projected_Node(i)->IPA_LNO_Print_File(stdout, i);
00876 }
00877 buffer = (char *) IPA_LNO_Summary->Projected_Node(0);
00878 buffer_size = sizeof(PROJECTED_NODE)
00879 * IPA_LNO_Summary->Projected_Node_Count();
00880 IPA_LNO_Output_File->Write_Section(IPA_PROJECTED_ARRAY,
00881 IPA_PROJECTED_ARRAY_NAME, buffer, buffer_size);
00882 }
00883 if (IPA_LNO_Summary->Term_Count() > 0) {
00884 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00885 fprintf(stdout, "Writing %d terms:\n",
00886 IPA_LNO_Summary->Term_Count());
00887 for (INT i = 0; i < IPA_LNO_Summary->Term_Count(); i++)
00888 IPA_LNO_Summary->Term(i)->IPA_LNO_Print_File(stdout, i);
00889 }
00890 buffer = (char *) IPA_LNO_Summary->Term(0);
00891 buffer_size = sizeof(TERM) * IPA_LNO_Summary->Term_Count();
00892 IPA_LNO_Output_File->Write_Section(IPA_TERM_ARRAY, IPA_TERM_ARRAY_NAME,
00893 buffer, buffer_size);
00894 }
00895 if (IPA_LNO_Summary->Value_Count() > 0) {
00896 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00897 fprintf(stdout, "Writing %d values:\n",
00898 IPA_LNO_Summary->Value_Count());
00899 for (INT i = 0; i < IPA_LNO_Summary->Value_Count(); i++)
00900 IPA_LNO_Summary->Value(i)->WB_Print(stdout, i);
00901 }
00902 buffer = (char *) IPA_LNO_Summary->Value(0);
00903 buffer_size = sizeof(SUMMARY_VALUE) * IPA_LNO_Summary->Value_Count();
00904 IPA_LNO_Output_File->Write_Section(IPA_VALUE, IPA_VALUE_NAME,
00905 buffer, buffer_size);
00906 }
00907 if (IPA_LNO_Summary->Expr_Count() > 0) {
00908 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE)) {
00909 fprintf(stdout, "Writing %d exprs:\n",
00910 IPA_LNO_Summary->Expr_Count());
00911 for (INT i = 0; i < IPA_LNO_Summary->Expr_Count(); i++)
00912 IPA_LNO_Summary->Expr(i)->WB_Print(stdout, i);
00913 }
00914 buffer = (char *) IPA_LNO_Summary->Expr(0);
00915 buffer_size = sizeof(SUMMARY_EXPR) * IPA_LNO_Summary->Expr_Count();
00916 IPA_LNO_Output_File->Write_Section(IPA_EXPR, IPA_EXPR_NAME,
00917 buffer, buffer_size);
00918 }
00919 if (Get_Trace(TP_IPA, IPA_TRACE_LNO_WRITE))
00920 fprintf(stdout, "+++ END WRITING IPA LNO FILE +++\n\n");
00921 }
00922
00923
00924
00925
00926
00927
00928
00929
00930 static void IPA_LNO_Close_Output_Info(IPA_LNO_WRITE_FILE* IPA_LNO_Output_File)
00931 {
00932 Output_File* ofl = IPA_LNO_Output_File->ofl;
00933 if (ofl->output_fd < 0)
00934 ErrMsg(EC_IPALNO_Close, ofl->file_name, errno);
00935 INT error_code = IPA_LNO_Output_File->Close_Write_File();
00936 if (error_code == IPALNO_CLOSE_ERROR)
00937 ErrMsg(EC_IPALNO_Close, ofl->file_name, errno);
00938 }
00939
00940
00941
00942
00943
00944
00945
00946 extern void IPA_LNO_Write_Summary(IPA_LNO_WRITE_SUMMARY* IPA_LNO_Summary)
00947 {
00948 FmtAssert(IPA_LNO_Summary != NULL,
00949 ("IPA_LNO_Write_Summary: NULL summary"));
00950
00951 extern string tmpdir __attribute__((weak));
00952
00953 char* dirname = (char *) tmpdir;
00954 char* buffer = (char *) MEM_POOL_Alloc(Malloc_Mem_Pool,
00955 sizeof(char) * (strlen(dirname) + strlen("/IPA.LNO") + 1));
00956 sprintf(buffer, "%s%s", dirname, "/IPA.LNO");
00957 IPA_LNO_WRITE_FILE*
00958 IPA_LNO_Output_File = IPA_LNO_Open_Output_Info(buffer);
00959 MEM_POOL_FREE(Malloc_Mem_Pool, buffer);
00960
00961
00962 IPA_LNO_Write_Sections(IPA_LNO_Summary, IPA_LNO_Output_File);
00963
00964
00965 IPA_LNO_Close_Output_Info(IPA_LNO_Output_File);
00966 }