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 #ifndef sched_path_INCLUDED
00051 #define sched_path_INCLUDED
00052
00053 #include <stdint.h>
00054
00055 #include <list>
00056 #include <vector>
00057
00058 #include "ipfec_defs.h"
00059
00060 #include "tracing.h"
00061 #include "bb.h"
00062 #include "region.h"
00063
00064 #include "sched_util.h"
00065
00066
00067
00068
00069 typedef INT32 EXEC_PATH_ID;
00070 #define EXEC_PATH_MAX_ID (0x7fffffff)
00071 #define INVALID_EXEC_PATH_ID (EXEC_PATH_ID(-1))
00072 #define EXEC_PATH_ID_IS_INVALID(x) ((x) < 0 || (x) > EXEC_PATH_MAX_ID)
00073 #define ASSIGN_INVALID_EXEC_PATH_ID(x) ((x) = -1)
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087 class PATH_NODE_INFO {
00088 private:
00089 REGIONAL_CFG_NODE * _node ;
00090 BB * _bb_node ;
00091 REGION * _rgn_node ;
00092
00093 REGIONAL_CFG_EDGE * _incoming_edge;
00094 float _incoming_edge_prob ;
00095
00096 float _prob ;
00097
00098 public:
00099 REGIONAL_CFG_NODE* Node (void) const { return _node ; }
00100 REGIONAL_CFG_EDGE* Incoming_Edge (void) const {
00101 return _incoming_edge;
00102 }
00103 float Incoming_Edge_prob (void) const {
00104 return _incoming_edge ?
00105 _incoming_edge -> Prob () : 0.0f;
00106 }
00107
00108 BOOL Associated_With_This_Node (BB* b) const {
00109 return _bb_node == b;
00110 }
00111
00112 BOOL Associated_With_This_Node (REGION * r) const {
00113 return _rgn_node == r;
00114 }
00115
00116 BOOL Associated_With_This_Node (REGIONAL_CFG_NODE *n) const {
00117 return n == _node ;
00118 }
00119
00120 float Prob_From_Root (void) const { return _prob ; }
00121
00122 PATH_NODE_INFO (REGIONAL_CFG_NODE *n,
00123 REGIONAL_CFG_EDGE * incoming_edge,
00124 float prob) {
00125
00126 _node = n ;
00127 _incoming_edge = incoming_edge;
00128
00129 _prob = prob;
00130
00131 if (n->Is_Region ()) {
00132 _rgn_node = n->Region_Node ();
00133 _bb_node = NULL;
00134 } else {
00135 _bb_node = n->BB_Node ();
00136 _rgn_node = NULL;
00137 }
00138
00139 }
00140
00141 ~PATH_NODE_INFO (void) { }
00142
00143 };
00144
00145 typedef mempool_allocator<PATH_NODE_INFO> PATH_NODE_ALLOC;
00146 typedef std::vector<PATH_NODE_INFO,PATH_NODE_ALLOC> PATH_NODE_INFO_VECT;
00147 typedef PATH_NODE_INFO_VECT::iterator PATH_NODE_INFO_VECT_ITER;
00148 typedef PATH_NODE_INFO_VECT::const_iterator
00149 PATH_NODE_INFO_VECT_CONST_ITER;
00150
00151
00152 class EXEC_PATH {
00153
00154 friend class EXEC_PATH_MGR ;
00155
00156 private:
00157
00158
00159
00160
00161 PATH_NODE_INFO_VECT _path_node_seq;
00162
00163
00164
00165
00166
00167 enum { EP_HASH_BUCKET_NUM = 23,};
00168 enum { INVALID_NODE_INFO_IDX = -1,};
00169
00170 struct EP_HASH_BUCKET {
00171 INT32 node_idx ;
00172 struct EP_HASH_BUCKET * next ;
00173 EP_HASH_BUCKET (void) {
00174 node_idx = INVALID_NODE_INFO_IDX ; next = NULL;
00175 }
00176 };
00177
00178 EXEC_PATH::EP_HASH_BUCKET _hash_tab[EP_HASH_BUCKET_NUM] ;
00179
00180 inline INT32 Hash_Key (BB * b) { return BB_id(b) % EP_HASH_BUCKET_NUM ; }
00181 inline INT32 Hash_Key (REGION *r) { return r->Id() % EP_HASH_BUCKET_NUM;}
00182 inline INT32 Hash_Key (REGIONAL_CFG_NODE* n) {
00183 return n->Is_Region () ?
00184 Hash_Key (n->Region_Node ()) :
00185 Hash_Key (n->BB_Node ());
00186 }
00187 inline void Add_Hash (REGIONAL_CFG_NODE *n, INT32 idx_2_node_info) {
00188
00189 INT32 hk = Hash_Key (n);
00190 if (_hash_tab[hk].node_idx == INVALID_NODE_INFO_IDX) {
00191 _hash_tab[hk].node_idx = idx_2_node_info;
00192 _hash_tab[hk].next = NULL;
00193 } else {
00194 EXEC_PATH::EP_HASH_BUCKET * p = &_hash_tab[hk];
00195 while (p->next) { p = p->next ; }
00196 p -> next = CXX_NEW (EXEC_PATH::EP_HASH_BUCKET, _mp);
00197 p -> next -> node_idx = idx_2_node_info ;
00198 p -> next -> next = NULL;
00199 }
00200 }
00201
00202 inline INT32 Get_Path_Node_Info_Idx (REGIONAL_CFG_NODE *n) {
00203
00204 INT32 hk = Hash_Key (n);
00205 INT32 idx;
00206 while ((idx = _hash_tab[hk].node_idx) !=
00207 INVALID_NODE_INFO_IDX) {
00208
00209 if (_path_node_seq[idx].Associated_With_This_Node(n)) {
00210 return idx;
00211 }
00212 }
00213 return INVALID_NODE_INFO_IDX;
00214 }
00215
00216 inline void Setup_Hash (void) {
00217 for (INT i = _path_node_seq.size() - 1 ; i >= 0; i--) {
00218 Add_Hash (_path_node_seq[i].Node (), i);
00219 }
00220 }
00221
00222 MEM_POOL * _mp ;
00223 EXEC_PATH_ID _id ;
00224
00225 mBOOL _has_call;
00226 mBOOL _has_nested_rgn;
00227
00228 INT16 _bb_num;
00229 INT16 _nested_rgn_num;
00230
00231 void Append_Path_Segment
00232 (REGIONAL_CFG_EDGE *incoming_edge, REGIONAL_CFG_NODE *node);
00233
00234 void Set_Has_Call (void) { _has_call = TRUE ; }
00235 void Set_Has_Nested_Rgn (void) { _has_nested_rgn = TRUE; }
00236
00237 INT16 Inc_Path_BB_Num (void) { return ++_bb_num ; }
00238 INT16 Inc_Path_Nested_Rgn_Num (void) { return ++_nested_rgn_num; }
00239
00240 public:
00241
00242
00243
00244 EXEC_PATH (EXEC_PATH_ID id, MEM_POOL* mp) ;
00245 EXEC_PATH (const EXEC_PATH& ep, MEM_POOL *mp) ;
00246
00247 ~EXEC_PATH (void) { }
00248 EXEC_PATH& operator = (const EXEC_PATH& ep);
00249
00250
00251
00252 EXEC_PATH_ID Id (void) const { return _id ; }
00253 INT32 Path_Len (void) const { return _path_node_seq.size() ; }
00254
00255 INT16 BB_Node_In_Total (void) const { return _bb_num ; }
00256 INT16 Rgn_Node_In_Total (void) const { return _nested_rgn_num ; }
00257
00258 BOOL Path_Has_Call (void) const { return _has_call ; }
00259 BOOL Path_Has_Nested_Rgn (void) const { return _has_nested_rgn; }
00260
00261 INT32 Node_Index (REGIONAL_CFG_NODE *n) {
00262 return Get_Path_Node_Info_Idx (n);
00263 }
00264
00265
00266
00267 BOOL Node_In_Path (BB *b) {
00268 for (PATH_NODE_INFO_VECT_ITER iter = _path_node_seq.begin ();
00269 iter != _path_node_seq.end (); iter++) {
00270
00271 if ((*iter).Associated_With_This_Node(b)) {
00272 return TRUE;
00273 }
00274 }
00275 return FALSE ;
00276 }
00277
00278 BOOL Node_In_Path (REGION *r) {
00279 for (PATH_NODE_INFO_VECT_ITER iter = _path_node_seq.begin ();
00280 iter != _path_node_seq.end (); iter++) {
00281
00282 if ((*iter).Associated_With_This_Node(r)) {
00283 return TRUE;
00284 }
00285 }
00286 return FALSE ;
00287 }
00288
00289
00290
00291
00292 void Dump (FILE *f=stderr);
00293 #ifdef Is_True_On
00294 void gdb_dump (void);
00295 #endif
00296 };
00297
00298
00299
00300 typedef mempool_allocator<EXEC_PATH*> EXEC_PATH_ALLOC;
00301 typedef std::vector<EXEC_PATH*,EXEC_PATH_ALLOC> EXEC_PATH_VECTOR;
00302 typedef EXEC_PATH_VECTOR::iterator EXEC_PATH_VECT_ITER;
00303 typedef EXEC_PATH_VECTOR::const_iterator EXEC_PATH_VECT_CONST_ITER;
00304
00305
00306
00307
00308
00309
00310
00311
00312
00313 class EXEC_PATH_SET {
00314
00315 #ifdef UINT64
00316 typedef UINT64 BV_WORD;
00317 enum { BV_WORD_SIZE = 64, };
00318 enum { BV_WORD_SIZE_LOG_2 = 6,};
00319 #else
00320 typedef UINT32 BV_WORD;
00321 enum { BV_WORD_SIZE = 32, };
00322 enum { BV_WORD_SIZE_LOG_2 = 5,};
00323 #endif
00324
00325
00326
00327
00328
00329
00330
00331
00332 BV_WORD BV_WORD_SHIFT_LEFT (BV_WORD w, UINT32 shift_l_by) {
00333 return (shift_l_by < BV_WORD_SIZE) ?
00334 (w << shift_l_by) : 0;
00335 }
00336
00337 BV_WORD BV_WORD_SHIFT_RIGHT (BV_WORD w, UINT32 shift_r_by) {
00338 return (shift_r_by < BV_WORD_SIZE) ?
00339 (w >> shift_r_by) : 0 ;
00340 }
00341
00342
00343
00344 BOOL BV_WORD_Test_Bit (BV_WORD w, UINT32 pos) {
00345 return (pos < BV_WORD_SIZE) ?
00346 (w & (1 << pos)) : FALSE;
00347 }
00348
00349 BV_WORD BV_WORD_Set_Bit (BV_WORD& w, UINT32 pos) {
00350 return pos < BV_WORD_SIZE ? (w |= (1 << pos)) : w;
00351 }
00352
00353 BV_WORD BV_WORD_Xor_Bit (BV_WORD& w, UINT pos) {
00354 return pos < BV_WORD_SIZE ? (w ^= (1 << pos)) : w;
00355 }
00356
00357 BV_WORD BV_WORD_Clear_Bit (BV_WORD& w, UINT pos) {
00358 return pos < BV_WORD_SIZE ? (w &= ~(1 << pos)) : w ;
00359 }
00360
00361 private:
00362
00363 BV_WORD * _bv;
00364 BV_WORD _bv_words[4];
00365
00366
00367
00368
00369
00370
00371
00372
00373 BV_WORD _msw_mask;
00374 mINT32 _bv_words_num;
00375 mINT32 _size;
00376
00377 MEM_POOL * _mp ;
00378
00379
00380
00381
00382
00383
00384 BOOL Path_Id_Is_Valid (EXEC_PATH_ID path_id,
00385 BOOL abort_exec_if_invalid = TRUE) {
00386
00387 if (EXEC_PATH_ID_IS_INVALID(path_id) ||
00388 path_id >= _size) {
00389
00390 if (abort_exec_if_invalid) {
00391 Fail_FmtAssertion ("Invalid path_id %d", path_id);
00392 }
00393
00394 return FALSE ;
00395 }
00396
00397 return TRUE;
00398 }
00399
00400 BOOL Equal_Size (const EXEC_PATH_SET& eps,
00401 BOOL abort_exec_if_invalid = TRUE) {
00402
00403 if (_size != eps.Size ()) {
00404 if (abort_exec_if_invalid) {
00405 Fail_FmtAssertion
00406 ("two sets' size do not match(%d vs. %d)",
00407 _size, eps.Size ());
00408 }
00409 return FALSE;
00410 }
00411
00412 return TRUE;
00413 }
00414
00415
00416
00417
00418
00419 void WordIdx_BitPos (EXEC_PATH_ID path_id,
00420 INT32& word_idx, INT32& bitpos) {
00421 word_idx = path_id >> BV_WORD_SIZE_LOG_2;
00422 bitpos = path_id % BV_WORD_SIZE ;
00423 }
00424
00425
00426
00427 EXEC_PATH_SET& operator & (const EXEC_PATH_SET& eps);
00428 void operator &= (const EXEC_PATH_SET& eps);
00429
00430
00431
00432 EXEC_PATH_SET& operator << (const UINT16 shift_l_by);
00433 void operator <<= (const UINT16 shift_l_by);
00434 EXEC_PATH_SET& operator >> (const UINT16 shift_r_by);
00435 void operator >>= (const UINT16 shift_r_by);
00436
00437
00438
00439 EXEC_PATH_SET& operator ~ (void) ;
00440 void Bitwise_Not (void) ;
00441
00442
00443
00444 EXEC_PATH_SET& operator | (const EXEC_PATH_SET& eps) ;
00445 void operator |= (const EXEC_PATH_SET& eps) ;
00446
00447
00448
00449
00450
00451 BOOL There_Are_Continguous_Path_Id
00452 (EXEC_PATH_ID begin_path_id, INT32 length);
00453
00454
00455
00456
00457
00458
00459 BV_WORD Pattern_Word (UINT32 middle_one_num, UINT32 low_zero_num) {
00460
00461 Is_True (low_zero_num + middle_one_num <= BV_WORD_SIZE,
00462 ("low_zero_num(%d) + middle_one_num(%d) >"
00463 " BV_WORD_SIZE",
00464 low_zero_num, middle_one_num));
00465
00466 return (middle_one_num != BV_WORD_SIZE) ?
00467 (((1 << middle_one_num) - 1) << low_zero_num) :
00468 BV_WORD(-1);
00469 }
00470 public:
00471
00472 EXEC_PATH_SET (MEM_POOL *mp, mINT32 size=128);
00473 EXEC_PATH_SET& operator = (const EXEC_PATH_SET& eps);
00474 EXEC_PATH_SET (EXEC_PATH_SET& ps, MEM_POOL *mp) {
00475 _mp = mp ; *this = ps ;
00476 }
00477 void Clear (void) { for (mINT32 i = _bv_words_num - 1; i >= 0 ;i--) {
00478 _bv[i] = 0;
00479 }
00480 }
00481
00482 BOOL Is_Empty (void) const { for (mINT32 i=_bv_words_num - 1; i >= 0; i--) {
00483 if (_bv[i]) return FALSE;
00484 }
00485 return TRUE;
00486 }
00487
00488
00489
00490
00491 INT32 Size (void) const { return _size ; }
00492 void Resize (INT32 new_size) ;
00493
00494
00495
00496
00497 BOOL Is_Member (EXEC_PATH_ID path) ;
00498
00499
00500
00501 void Add_Path_Id (const EXEC_PATH_ID id) ;
00502 void Del_Path_Id (const EXEC_PATH_ID id) ;
00503
00504
00505
00506 EXEC_PATH_SET& operator + (const EXEC_PATH_SET& eps) {
00507 return (*this) | eps ;
00508 }
00509
00510 void operator += (const EXEC_PATH_SET& eps) { (*this) |= eps ; }
00511 void Union_Range_Inclusively (EXEC_PATH_ID from, EXEC_PATH_ID to);
00512 void Union_Partioned_Path_Set
00513 (EXEC_PATH_SET& eps, INT32 pred_path_num,
00514 INT32 succ_path_num,INT32 base);
00515
00516
00517
00518 EXEC_PATH_SET& operator - (const EXEC_PATH_SET& eps) ;
00519 void operator -= (const EXEC_PATH_SET& eps) ;
00520
00521
00522
00523
00524 EXEC_PATH_SET& Universe (void);
00525 void Set_To_Be_Universe (void);
00526
00527
00528
00529
00530 BOOL Intersection_Is_Empty (EXEC_PATH_SET* eps);
00531
00532
00533
00534
00535
00536
00537
00538 EXEC_PATH_SET& Subset (EXEC_PATH_ID from, EXEC_PATH_ID to);
00539
00540
00541 BOOL Is_Subset_Of (EXEC_PATH_SET* eps);
00542
00543
00544
00545
00546
00547
00548
00549
00550 EXEC_PATH_ID First_Path_Id (void) ;
00551 EXEC_PATH_ID Next_Path_Id
00552 (EXEC_PATH_ID path, BOOL check_membership=TRUE) ;
00553 EXEC_PATH_ID Last_Path_Id (void) ;
00554 EXEC_PATH_ID Prev_Path_Id
00555 (EXEC_PATH_ID path, BOOL check_membership=TRUE) ;
00556
00557
00558
00559
00560 void Dump (FILE * f=stderr);
00561
00562 #ifdef Is_True_On
00563 void gdb_dump (void);
00564 #endif
00565 };
00566
00567
00568
00569
00570
00571
00572
00573
00574
00575
00576 class EXEC_PATH_MGR {
00577 private:
00578
00579 REGION * _region;
00580
00581
00582 EXEC_PATH_VECTOR _pathv ;
00583 MEM_POOL * _mp;
00584
00585
00586 typedef struct tagEP_NODE_INFO {
00587
00588 REGIONAL_CFG_NODE *n;
00589 MEM_POOL * mp;
00590 mINT32 subgraph_path_num ;
00591
00592 mINT32 path_num;
00593
00594 EXEC_PATH_SET eps;
00595
00596 tagEP_NODE_INFO (REGIONAL_CFG_NODE *node,MEM_POOL* memp) :
00597 mp(memp), eps(memp), n(node) {
00598 subgraph_path_num = 0;
00599 path_num = 0;
00600 }
00601
00602 ~tagEP_NODE_INFO (void) { } ;
00603
00604 } EP_NODE_INFO;
00605
00606 CFG_NODE_MAP _ep_node_info ;
00607 BOOL _path_info_invalid ;
00608 mINT32 _total_paths;
00609
00610 enum { MAX_PATH_NUM = 128, };
00611
00612
00613
00614
00615
00616 INT32 Calc_Subgraph_Path_Num (void);
00617
00618
00619 public:
00620
00621 EXEC_PATH_MGR (MEM_POOL * mp);
00622 ~EXEC_PATH_MGR (void) { }
00623
00624 BOOL Path_Info_Is_Invalid (void) const {return _path_info_invalid;}
00625
00626
00627
00628
00629 EXEC_PATH_MGR& operator = (EXEC_PATH_MGR& epm);
00630
00631
00632 EXEC_PATH * Path (EXEC_PATH_ID pid) const {
00633 return (_pathv.size() > pid) ? _pathv[pid] : NULL;
00634 }
00635 REGION * Scope (void) { return _region ; }
00636
00637 INT32 Path_In_Total (void) const { return _total_paths; }
00638
00639
00640
00641 INT32 Acquire_Path_Info (REGION *r) ;
00642
00643 EXEC_PATH_SET* Get_Path_Flow_Thru (BB* bb);
00644 EXEC_PATH_SET* Get_Path_Flow_Thru (REGION* r);
00645 EXEC_PATH_SET* Get_Path_Flow_Thru (REGIONAL_CFG_NODE* r) {
00646 return r->Is_Region () ?
00647 Get_Path_Flow_Thru (r->Region_Node ()) :
00648 Get_Path_Flow_Thru (r->BB_Node ());
00649 }
00650
00651
00652
00653 void Dump (FILE *f=stderr);
00654
00655 #ifdef Is_True_On
00656 void gdb_dump (void);
00657 #endif
00658
00659 };
00660
00661
00662
00663
00664
00665
00666
00667
00668
00669
00670
00671
00672
00673
00674
00675
00676
00677 class SUB_SEME_EXEC_PATH_MGR {
00678 private:
00679
00680 REGION * _base_graph;
00681 REGIONAL_CFG_NODE * _sub_SEME_root;
00682 MEM_POOL * _mp;
00683
00684 EXEC_PATH_VECTOR _paths;
00685
00686 public:
00687
00688 SUB_SEME_EXEC_PATH_MGR (MEM_POOL *mp);
00689 ~SUB_SEME_EXEC_PATH_MGR (void);
00690
00691 void Derive_Exec_Path_Info (EXEC_PATH_MGR * exec_path_mgr,
00692 REGIONAL_CFG_NODE* sub_SEME_root) ;
00693
00694 INT32 Path_In_Total (void) const { return _paths.size(); }
00695
00696 EXEC_PATH * First_Path (void) const {
00697 return Path_In_Total () ? _paths[0] : NULL;
00698 }
00699
00700 EXEC_PATH * Last_Path (void) const {
00701 return Path_In_Total () ?
00702 _paths[Path_In_Total () - 1]:
00703 NULL;
00704 }
00705
00706 EXEC_PATH * Next_Path (EXEC_PATH * ep) const {
00707 EXEC_PATH_ID pid = ep->Id ();
00708 return (pid+ 1 >= Path_In_Total ()) ?
00709 _paths[pid + 1] :
00710 NULL;
00711 }
00712 };
00713
00714 #endif
00715