< prev index next >

src/share/vm/opto/loopnode.hpp

Print this page




  47 //
  48 // Idealized loops are the set of loops I perform more interesting
  49 // transformations on, beyond simple hoisting.
  50 
  51 //------------------------------LoopNode---------------------------------------
  52 // Simple loop header.  Fall in path on left, loop-back path on right.
  53 class LoopNode : public RegionNode {
  54   // Size is bigger to hold the flags.  However, the flags do not change
  55   // the semantics so it does not appear in the hash & cmp functions.
  56   virtual uint size_of() const { return sizeof(*this); }
  57 protected:
  58   short _loop_flags;
  59   // Names for flag bitfields
  60   enum { Normal=0, Pre=1, Main=2, Post=3, PreMainPostFlagsMask=3,
  61          MainHasNoPreLoop=4,
  62          HasExactTripCount=8,
  63          InnerLoop=16,
  64          PartialPeelLoop=32,
  65          PartialPeelFailed=64,
  66          HasReductions=128,
  67          PassedSlpAnalysis=256 };


  68   char _unswitch_count;
  69   enum { _unswitch_max=3 };
  70 
  71 public:
  72   // Names for edge indices
  73   enum { Self=0, EntryControl, LoopBackControl };
  74 
  75   int is_inner_loop() const { return _loop_flags & InnerLoop; }
  76   void set_inner_loop() { _loop_flags |= InnerLoop; }
  77 
  78   int is_partial_peel_loop() const { return _loop_flags & PartialPeelLoop; }
  79   void set_partial_peel_loop() { _loop_flags |= PartialPeelLoop; }
  80   int partial_peel_has_failed() const { return _loop_flags & PartialPeelFailed; }
  81   void mark_partial_peel_failed() { _loop_flags |= PartialPeelFailed; }
  82   void mark_has_reductions() { _loop_flags |= HasReductions; }

  83   void mark_passed_slp() { _loop_flags |= PassedSlpAnalysis; }

  84 
  85   int unswitch_max() { return _unswitch_max; }
  86   int unswitch_count() { return _unswitch_count; }
  87   void set_unswitch_count(int val) {
  88     assert (val <= unswitch_max(), "too many unswitches");
  89     _unswitch_count = val;
  90   }
  91 
  92   LoopNode( Node *entry, Node *backedge ) : RegionNode(3), _loop_flags(0), _unswitch_count(0) {
  93     init_class_id(Class_Loop);
  94     init_req(EntryControl, entry);
  95     init_req(LoopBackControl, backedge);
  96   }
  97 
  98   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
  99   virtual int Opcode() const;
 100   bool can_be_counted_loop(PhaseTransform* phase) const {
 101     return req() == 3 && in(0) != NULL &&
 102       in(1) != NULL && phase->type(in(1)) != Type::TOP &&
 103       in(2) != NULL && phase->type(in(2)) != Type::TOP;


 195   // It will be RCE'd and unrolled and aligned.
 196 
 197   // A following 'post' loop will run any remaining iterations.  Used
 198   // during Range Check Elimination, the 'post' loop will do any final
 199   // iterations with full checks.  Also used by Loop Unrolling, where
 200   // the 'post' loop will do any epilog iterations needed.  Basically,
 201   // a 'post' loop can not profitably be further unrolled or RCE'd.
 202 
 203   // A preceding 'pre' loop will run at least 1 iteration (to do peeling),
 204   // it may do under-flow checks for RCE and may do alignment iterations
 205   // so the following main loop 'knows' that it is striding down cache
 206   // lines.
 207 
 208   // A 'main' loop that is ONLY unrolled or peeled, never RCE'd or
 209   // Aligned, may be missing it's pre-loop.
 210   int is_normal_loop   () const { return (_loop_flags&PreMainPostFlagsMask) == Normal; }
 211   int is_pre_loop      () const { return (_loop_flags&PreMainPostFlagsMask) == Pre;    }
 212   int is_main_loop     () const { return (_loop_flags&PreMainPostFlagsMask) == Main;   }
 213   int is_post_loop     () const { return (_loop_flags&PreMainPostFlagsMask) == Post;   }
 214   int is_reduction_loop() const { return (_loop_flags&HasReductions) == HasReductions; }

 215   int has_passed_slp   () const { return (_loop_flags&PassedSlpAnalysis) == PassedSlpAnalysis; }

 216   int is_main_no_pre_loop() const { return _loop_flags & MainHasNoPreLoop; }
 217   void set_main_no_pre_loop() { _loop_flags |= MainHasNoPreLoop; }
 218 
 219   int main_idx() const { return _main_idx; }
 220 
 221 
 222   void set_pre_loop  (CountedLoopNode *main) { assert(is_normal_loop(),""); _loop_flags |= Pre ; _main_idx = main->_idx; }
 223   void set_main_loop (                     ) { assert(is_normal_loop(),""); _loop_flags |= Main;                         }
 224   void set_post_loop (CountedLoopNode *main) { assert(is_normal_loop(),""); _loop_flags |= Post; _main_idx = main->_idx; }
 225   void set_normal_loop(                    ) { _loop_flags &= ~PreMainPostFlagsMask; }
 226 
 227   void set_trip_count(uint tc) { _trip_count = tc; }
 228   uint trip_count()            { return _trip_count; }
 229 
 230   bool has_exact_trip_count() const { return (_loop_flags & HasExactTripCount) != 0; }
 231   void set_exact_trip_count(uint tc) {
 232     _trip_count = tc;
 233     _loop_flags |= HasExactTripCount;
 234   }
 235   void set_nonexact_trip_count() {
 236     _loop_flags &= ~HasExactTripCount;



 237   }
 238 
 239   void set_profile_trip_cnt(float ptc) { _profile_trip_cnt = ptc; }
 240   float profile_trip_cnt()             { return _profile_trip_cnt; }
 241 
 242   void double_unrolled_count() { _unrolled_count_log2++; }
 243   int  unrolled_count()        { return 1 << MIN2(_unrolled_count_log2, BitsPerInt-3); }
 244 
 245   void set_node_count_before_unroll(int ct)  { _node_count_before_unroll = ct; }
 246   int  node_count_before_unroll()            { return _node_count_before_unroll; }
 247   void set_slp_max_unroll(int unroll_factor) { _slp_maximum_unroll_factor = unroll_factor; }
 248   int  slp_max_unroll() const                { return _slp_maximum_unroll_factor; }
 249 
 250 #ifndef PRODUCT
 251   virtual void dump_spec(outputStream *st) const;
 252 #endif
 253 };
 254 
 255 //------------------------------CountedLoopEndNode-----------------------------
 256 // CountedLoopEndNodes end simple trip counted loops.  They act much like




  47 //
  48 // Idealized loops are the set of loops I perform more interesting
  49 // transformations on, beyond simple hoisting.
  50 
  51 //------------------------------LoopNode---------------------------------------
  52 // Simple loop header.  Fall in path on left, loop-back path on right.
  53 class LoopNode : public RegionNode {
  54   // Size is bigger to hold the flags.  However, the flags do not change
  55   // the semantics so it does not appear in the hash & cmp functions.
  56   virtual uint size_of() const { return sizeof(*this); }
  57 protected:
  58   short _loop_flags;
  59   // Names for flag bitfields
  60   enum { Normal=0, Pre=1, Main=2, Post=3, PreMainPostFlagsMask=3,
  61          MainHasNoPreLoop=4,
  62          HasExactTripCount=8,
  63          InnerLoop=16,
  64          PartialPeelLoop=32,
  65          PartialPeelFailed=64,
  66          HasReductions=128,
  67          WasSlpAnalyzed=256,
  68          PassedSlpAnalysis=512,
  69          NoMoreSlp=1024 };
  70   char _unswitch_count;
  71   enum { _unswitch_max=3 };
  72 
  73 public:
  74   // Names for edge indices
  75   enum { Self=0, EntryControl, LoopBackControl };
  76 
  77   int is_inner_loop() const { return _loop_flags & InnerLoop; }
  78   void set_inner_loop() { _loop_flags |= InnerLoop; }
  79 
  80   int is_partial_peel_loop() const { return _loop_flags & PartialPeelLoop; }
  81   void set_partial_peel_loop() { _loop_flags |= PartialPeelLoop; }
  82   int partial_peel_has_failed() const { return _loop_flags & PartialPeelFailed; }
  83   void mark_partial_peel_failed() { _loop_flags |= PartialPeelFailed; }
  84   void mark_has_reductions() { _loop_flags |= HasReductions; }
  85   void mark_was_slp() { _loop_flags |= WasSlpAnalyzed; }
  86   void mark_passed_slp() { _loop_flags |= PassedSlpAnalysis; }
  87   void mark_no_slp() { _loop_flags |= NoMoreSlp; }
  88 
  89   int unswitch_max() { return _unswitch_max; }
  90   int unswitch_count() { return _unswitch_count; }
  91   void set_unswitch_count(int val) {
  92     assert (val <= unswitch_max(), "too many unswitches");
  93     _unswitch_count = val;
  94   }
  95 
  96   LoopNode( Node *entry, Node *backedge ) : RegionNode(3), _loop_flags(0), _unswitch_count(0) {
  97     init_class_id(Class_Loop);
  98     init_req(EntryControl, entry);
  99     init_req(LoopBackControl, backedge);
 100   }
 101 
 102   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
 103   virtual int Opcode() const;
 104   bool can_be_counted_loop(PhaseTransform* phase) const {
 105     return req() == 3 && in(0) != NULL &&
 106       in(1) != NULL && phase->type(in(1)) != Type::TOP &&
 107       in(2) != NULL && phase->type(in(2)) != Type::TOP;


 199   // It will be RCE'd and unrolled and aligned.
 200 
 201   // A following 'post' loop will run any remaining iterations.  Used
 202   // during Range Check Elimination, the 'post' loop will do any final
 203   // iterations with full checks.  Also used by Loop Unrolling, where
 204   // the 'post' loop will do any epilog iterations needed.  Basically,
 205   // a 'post' loop can not profitably be further unrolled or RCE'd.
 206 
 207   // A preceding 'pre' loop will run at least 1 iteration (to do peeling),
 208   // it may do under-flow checks for RCE and may do alignment iterations
 209   // so the following main loop 'knows' that it is striding down cache
 210   // lines.
 211 
 212   // A 'main' loop that is ONLY unrolled or peeled, never RCE'd or
 213   // Aligned, may be missing it's pre-loop.
 214   int is_normal_loop   () const { return (_loop_flags&PreMainPostFlagsMask) == Normal; }
 215   int is_pre_loop      () const { return (_loop_flags&PreMainPostFlagsMask) == Pre;    }
 216   int is_main_loop     () const { return (_loop_flags&PreMainPostFlagsMask) == Main;   }
 217   int is_post_loop     () const { return (_loop_flags&PreMainPostFlagsMask) == Post;   }
 218   int is_reduction_loop() const { return (_loop_flags&HasReductions) == HasReductions; }
 219   int was_slp_analyzed () const { return (_loop_flags&WasSlpAnalyzed) == WasSlpAnalyzed; }
 220   int has_passed_slp   () const { return (_loop_flags&PassedSlpAnalysis) == PassedSlpAnalysis; }
 221   int ignore_slp       () const { return (_loop_flags&NoMoreSlp) == NoMoreSlp; }
 222   int is_main_no_pre_loop() const { return _loop_flags & MainHasNoPreLoop; }
 223   void set_main_no_pre_loop() { _loop_flags |= MainHasNoPreLoop; }
 224 
 225   int main_idx() const { return _main_idx; }
 226 
 227 
 228   void set_pre_loop  (CountedLoopNode *main) { assert(is_normal_loop(),""); _loop_flags |= Pre ; _main_idx = main->_idx; }
 229   void set_main_loop (                     ) { assert(is_normal_loop(),""); _loop_flags |= Main;                         }
 230   void set_post_loop (CountedLoopNode *main) { assert(is_normal_loop(),""); _loop_flags |= Post; _main_idx = main->_idx; }
 231   void set_normal_loop(                    ) { _loop_flags &= ~PreMainPostFlagsMask; }
 232 
 233   void set_trip_count(uint tc) { _trip_count = tc; }
 234   uint trip_count()            { return _trip_count; }
 235 
 236   bool has_exact_trip_count() const { return (_loop_flags & HasExactTripCount) != 0; }
 237   void set_exact_trip_count(uint tc) {
 238     _trip_count = tc;
 239     _loop_flags |= HasExactTripCount;
 240   }
 241   void set_nonexact_trip_count() {
 242     _loop_flags &= ~HasExactTripCount;
 243   }
 244   void set_notpassed_slp() {
 245     _loop_flags &= ~PassedSlpAnalysis;
 246   }
 247 
 248   void set_profile_trip_cnt(float ptc) { _profile_trip_cnt = ptc; }
 249   float profile_trip_cnt()             { return _profile_trip_cnt; }
 250 
 251   void double_unrolled_count() { _unrolled_count_log2++; }
 252   int  unrolled_count()        { return 1 << MIN2(_unrolled_count_log2, BitsPerInt-3); }
 253 
 254   void set_node_count_before_unroll(int ct)  { _node_count_before_unroll = ct; }
 255   int  node_count_before_unroll()            { return _node_count_before_unroll; }
 256   void set_slp_max_unroll(int unroll_factor) { _slp_maximum_unroll_factor = unroll_factor; }
 257   int  slp_max_unroll() const                { return _slp_maximum_unroll_factor; }
 258 
 259 #ifndef PRODUCT
 260   virtual void dump_spec(outputStream *st) const;
 261 #endif
 262 };
 263 
 264 //------------------------------CountedLoopEndNode-----------------------------
 265 // CountedLoopEndNodes end simple trip counted loops.  They act much like


< prev index next >