Mercurial > hg > graal-compiler
comparison src/share/vm/opto/chaitin.hpp @ 14478:bb9356ec5967
Merge
author | hseigel |
---|---|
date | Sun, 23 Feb 2014 13:16:03 -0500 |
parents | c84312468f5c |
children | 99fc8c086679 |
comparison
equal
deleted
inserted
replaced
14477:96d2c94bbdd0 | 14478:bb9356ec5967 |
---|---|
96 _eff_degree += mod; | 96 _eff_degree += mod; |
97 assert(!_mask.is_AllStack() || (_mask.is_AllStack() && lo_degree()), "_eff_degree can't be bigger than AllStack_size - _num_regs if the mask supports stack registers"); | 97 assert(!_mask.is_AllStack() || (_mask.is_AllStack() && lo_degree()), "_eff_degree can't be bigger than AllStack_size - _num_regs if the mask supports stack registers"); |
98 } | 98 } |
99 // Compute the degree between 2 live ranges | 99 // Compute the degree between 2 live ranges |
100 int compute_degree( LRG &l ) const; | 100 int compute_degree( LRG &l ) const; |
101 bool mask_is_nonempty_and_up() const { | |
102 return mask().is_UP() && mask_size(); | |
103 } | |
104 bool is_float_or_vector() const { | |
105 return _is_float || _is_vector; | |
106 } | |
101 | 107 |
102 private: | 108 private: |
103 RegMask _mask; // Allowed registers for this LRG | 109 RegMask _mask; // Allowed registers for this LRG |
104 uint _mask_size; // cache of _mask.Size(); | 110 uint _mask_size; // cache of _mask.Size(); |
105 public: | 111 public: |
127 void set_mask( const RegMask &rm ) { _mask = rm; debug_only(_msize_valid=0;)} | 133 void set_mask( const RegMask &rm ) { _mask = rm; debug_only(_msize_valid=0;)} |
128 void AND( const RegMask &rm ) { _mask.AND(rm); debug_only(_msize_valid=0;)} | 134 void AND( const RegMask &rm ) { _mask.AND(rm); debug_only(_msize_valid=0;)} |
129 void SUBTRACT( const RegMask &rm ) { _mask.SUBTRACT(rm); debug_only(_msize_valid=0;)} | 135 void SUBTRACT( const RegMask &rm ) { _mask.SUBTRACT(rm); debug_only(_msize_valid=0;)} |
130 void Clear() { _mask.Clear() ; debug_only(_msize_valid=1); _mask_size = 0; } | 136 void Clear() { _mask.Clear() ; debug_only(_msize_valid=1); _mask_size = 0; } |
131 void Set_All() { _mask.Set_All(); debug_only(_msize_valid=1); _mask_size = RegMask::CHUNK_SIZE; } | 137 void Set_All() { _mask.Set_All(); debug_only(_msize_valid=1); _mask_size = RegMask::CHUNK_SIZE; } |
138 | |
132 void Insert( OptoReg::Name reg ) { _mask.Insert(reg); debug_only(_msize_valid=0;) } | 139 void Insert( OptoReg::Name reg ) { _mask.Insert(reg); debug_only(_msize_valid=0;) } |
133 void Remove( OptoReg::Name reg ) { _mask.Remove(reg); debug_only(_msize_valid=0;) } | 140 void Remove( OptoReg::Name reg ) { _mask.Remove(reg); debug_only(_msize_valid=0;) } |
134 void clear_to_pairs() { _mask.clear_to_pairs(); debug_only(_msize_valid=0;) } | 141 void clear_to_pairs() { _mask.clear_to_pairs(); debug_only(_msize_valid=0;) } |
135 void clear_to_sets() { _mask.clear_to_sets(_num_regs); debug_only(_msize_valid=0;) } | 142 void clear_to_sets() { _mask.clear_to_sets(_num_regs); debug_only(_msize_valid=0;) } |
136 | 143 |
481 | 488 |
482 // Add edge between reg and everything in the vector. | 489 // Add edge between reg and everything in the vector. |
483 // Same as _ifg->add_vector(reg,live) EXCEPT use the RegMask | 490 // Same as _ifg->add_vector(reg,live) EXCEPT use the RegMask |
484 // information to trim the set of interferences. Return the | 491 // information to trim the set of interferences. Return the |
485 // count of edges added. | 492 // count of edges added. |
486 void interfere_with_live( uint reg, IndexSet *live ); | 493 void interfere_with_live(uint lid, IndexSet* liveout); |
494 #ifdef ASSERT | |
487 // Count register pressure for asserts | 495 // Count register pressure for asserts |
488 uint count_int_pressure( IndexSet *liveout ); | 496 uint count_int_pressure(IndexSet* liveout); |
489 uint count_float_pressure( IndexSet *liveout ); | 497 uint count_float_pressure(IndexSet* liveout); |
498 #endif | |
490 | 499 |
491 // Build the interference graph using virtual registers only. | 500 // Build the interference graph using virtual registers only. |
492 // Used for aggressive coalescing. | 501 // Used for aggressive coalescing. |
493 void build_ifg_virtual( ); | 502 void build_ifg_virtual( ); |
503 | |
504 class Pressure { | |
505 public: | |
506 // keeps track of the register pressure at the current | |
507 // instruction (used when stepping backwards in the block) | |
508 uint _current_pressure; | |
509 | |
510 // keeps track of the instruction index of the first low to high register pressure | |
511 // transition (starting from the top) in the block | |
512 // if high_pressure_index == 0 then the whole block is high pressure | |
513 // if high_pressure_index = b.end_idx() + 1 then the whole block is low pressure | |
514 uint _high_pressure_index; | |
515 | |
516 // stores the highest pressure we find | |
517 uint _final_pressure; | |
518 | |
519 // number of live ranges that constitute high register pressure | |
520 const uint _high_pressure_limit; | |
521 | |
522 // lower the register pressure and look for a low to high pressure | |
523 // transition | |
524 void lower(LRG& lrg, uint& location) { | |
525 _current_pressure -= lrg.reg_pressure(); | |
526 if (_current_pressure == _high_pressure_limit) { | |
527 _high_pressure_index = location; | |
528 if (_current_pressure > _final_pressure) { | |
529 _final_pressure = _current_pressure + 1; | |
530 } | |
531 } | |
532 } | |
533 | |
534 // raise the pressure and store the pressure if it's the biggest | |
535 // pressure so far | |
536 void raise(LRG &lrg) { | |
537 _current_pressure += lrg.reg_pressure(); | |
538 if (_current_pressure > _final_pressure) { | |
539 _final_pressure = _current_pressure; | |
540 } | |
541 } | |
542 | |
543 Pressure(uint high_pressure_index, uint high_pressure_limit) | |
544 : _current_pressure(0) | |
545 , _high_pressure_index(high_pressure_index) | |
546 , _high_pressure_limit(high_pressure_limit) | |
547 , _final_pressure(0) {} | |
548 }; | |
549 | |
550 void lower_pressure(Block* b, uint location, LRG& lrg, IndexSet* liveout, Pressure& int_pressure, Pressure& float_pressure); | |
551 void raise_pressure(Block* b, LRG& lrg, Pressure& int_pressure, Pressure& float_pressure); | |
552 void check_for_high_pressure_transition_at_fatproj(uint& block_reg_pressure, uint location, LRG& lrg, Pressure& pressure, const int op_regtype); | |
553 void add_input_to_liveout(Block* b, Node* n, IndexSet* liveout, double cost, Pressure& int_pressure, Pressure& float_pressure); | |
554 void compute_initial_block_pressure(Block* b, IndexSet* liveout, Pressure& int_pressure, Pressure& float_pressure, double cost); | |
555 bool remove_node_if_not_used(Block* b, uint location, Node* n, uint lid, IndexSet* liveout); | |
556 void assign_high_score_to_immediate_copies(Block* b, Node* n, LRG& lrg, uint next_inst, uint last_inst); | |
557 void remove_interference_from_copy(Block* b, uint location, uint lid_copy, IndexSet* liveout, double cost, Pressure& int_pressure, Pressure& float_pressure); | |
558 void remove_bound_register_from_interfering_live_ranges(LRG& lrg, IndexSet* liveout, uint& must_spill); | |
559 void check_for_high_pressure_block(Pressure& pressure); | |
560 void adjust_high_pressure_index(Block* b, uint& hrp_index, Pressure& pressure); | |
494 | 561 |
495 // Build the interference graph using physical registers when available. | 562 // Build the interference graph using physical registers when available. |
496 // That is, if 2 live ranges are simultaneously alive but in their | 563 // That is, if 2 live ranges are simultaneously alive but in their |
497 // acceptable register sets do not overlap, then they do not interfere. | 564 // acceptable register sets do not overlap, then they do not interfere. |
498 uint build_ifg_physical( ResourceArea *a ); | 565 uint build_ifg_physical( ResourceArea *a ); |
552 void post_allocate_copy_removal(); | 619 void post_allocate_copy_removal(); |
553 Node *skip_copies( Node *c ); | 620 Node *skip_copies( Node *c ); |
554 // Replace the old node with the current live version of that value | 621 // Replace the old node with the current live version of that value |
555 // and yank the old value if it's dead. | 622 // and yank the old value if it's dead. |
556 int replace_and_yank_if_dead( Node *old, OptoReg::Name nreg, | 623 int replace_and_yank_if_dead( Node *old, OptoReg::Name nreg, |
557 Block *current_block, Node_List& value, Node_List& regnd ) { | 624 Block *current_block, Node_List& value, Node_List& regnd ) { |
558 Node* v = regnd[nreg]; | 625 Node* v = regnd[nreg]; |
559 assert(v->outcnt() != 0, "no dead values"); | 626 assert(v->outcnt() != 0, "no dead values"); |
560 old->replace_by(v); | 627 old->replace_by(v); |
561 return yank_if_dead(old, current_block, &value, ®nd); | 628 return yank_if_dead(old, current_block, &value, ®nd); |
562 } | 629 } |
563 | 630 |
564 int yank_if_dead( Node *old, Block *current_block, Node_List *value, Node_List *regnd ) { | 631 int yank_if_dead( Node *old, Block *current_block, Node_List *value, Node_List *regnd ) { |
565 return yank_if_dead_recurse(old, old, current_block, value, regnd); | 632 return yank_if_dead_recurse(old, old, current_block, value, regnd); |
566 } | 633 } |
567 int yank_if_dead_recurse(Node *old, Node *orig_old, Block *current_block, | 634 int yank_if_dead_recurse(Node *old, Node *orig_old, Block *current_block, |
568 Node_List *value, Node_List *regnd); | 635 Node_List *value, Node_List *regnd); |
569 int yank( Node *old, Block *current_block, Node_List *value, Node_List *regnd ); | 636 int yank( Node *old, Block *current_block, Node_List *value, Node_List *regnd ); |
570 int elide_copy( Node *n, int k, Block *current_block, Node_List &value, Node_List ®nd, bool can_change_regs ); | 637 int elide_copy( Node *n, int k, Block *current_block, Node_List &value, Node_List ®nd, bool can_change_regs ); |
571 int use_prior_register( Node *copy, uint idx, Node *def, Block *current_block, Node_List &value, Node_List ®nd ); | 638 int use_prior_register( Node *copy, uint idx, Node *def, Block *current_block, Node_List &value, Node_List ®nd ); |
572 bool may_be_copy_of_callee( Node *def ) const; | 639 bool may_be_copy_of_callee( Node *def ) const; |
573 | 640 |
574 // If nreg already contains the same constant as val then eliminate it | 641 // If nreg already contains the same constant as val then eliminate it |
575 bool eliminate_copy_of_constant(Node* val, Node* n, | 642 bool eliminate_copy_of_constant(Node* val, Node* n, |
576 Block *current_block, Node_List& value, Node_List ®nd, | 643 Block *current_block, Node_List& value, Node_List ®nd, |
577 OptoReg::Name nreg, OptoReg::Name nreg2); | 644 OptoReg::Name nreg, OptoReg::Name nreg2); |
578 // Extend the node to LRG mapping | 645 // Extend the node to LRG mapping |
579 void add_reference( const Node *node, const Node *old_node); | 646 void add_reference( const Node *node, const Node *old_node); |
580 | 647 |
581 private: | 648 private: |
582 | 649 |