Thu, 16 Apr 2009 15:50:32 -0700
6828024: verification of fixed interval usage is too weak
Reviewed-by: kvn
src/share/vm/c1/c1_LinearScan.cpp | file | annotate | diff | comparison | revisions | |
src/share/vm/includeDB_compiler1 | file | annotate | diff | comparison | revisions |
1.1 --- a/src/share/vm/c1/c1_LinearScan.cpp Thu Apr 16 10:40:42 2009 -0700 1.2 +++ b/src/share/vm/c1/c1_LinearScan.cpp Thu Apr 16 15:50:32 2009 -0700 1.3 @@ -2956,9 +2956,11 @@ 1.4 1.5 NOT_PRODUCT(print_intervals("After Register Allocation")); 1.6 NOT_PRODUCT(print_lir(2, "LIR after register allocation:")); 1.7 + 1.8 + sort_intervals_after_allocation(); 1.9 + 1.10 DEBUG_ONLY(verify()); 1.11 1.12 - sort_intervals_after_allocation(); 1.13 eliminate_spill_moves(); 1.14 assign_reg_num(); 1.15 CHECK_BAILOUT(); 1.16 @@ -3147,6 +3149,16 @@ 1.17 1.18 1.19 void LinearScan::verify_no_oops_in_fixed_intervals() { 1.20 + Interval* fixed_intervals; 1.21 + Interval* other_intervals; 1.22 + create_unhandled_lists(&fixed_intervals, &other_intervals, is_precolored_cpu_interval, NULL); 1.23 + 1.24 + // to ensure a walking until the last instruction id, add a dummy interval 1.25 + // with a high operation id 1.26 + other_intervals = new Interval(any_reg); 1.27 + other_intervals->add_range(max_jint - 2, max_jint - 1); 1.28 + IntervalWalker* iw = new IntervalWalker(this, fixed_intervals, other_intervals); 1.29 + 1.30 LIR_OpVisitState visitor; 1.31 for (int i = 0; i < block_count(); i++) { 1.32 BlockBegin* block = block_at(i); 1.33 @@ -3159,6 +3171,54 @@ 1.34 1.35 visitor.visit(op); 1.36 1.37 + if (visitor.info_count() > 0) { 1.38 + iw->walk_before(op->id()); 1.39 + bool check_live = true; 1.40 + if (op->code() == lir_move) { 1.41 + LIR_Op1* move = (LIR_Op1*)op; 1.42 + check_live = (move->patch_code() == lir_patch_none); 1.43 + } 1.44 + LIR_OpBranch* branch = op->as_OpBranch(); 1.45 + if (branch != NULL && branch->stub() != NULL && branch->stub()->is_exception_throw_stub()) { 1.46 + // Don't bother checking the stub in this case since the 1.47 + // exception stub will never return to normal control flow. 1.48 + check_live = false; 1.49 + } 1.50 + 1.51 + // Make sure none of the fixed registers is live across an 1.52 + // oopmap since we can't handle that correctly. 1.53 + if (check_live) { 1.54 + for (Interval* interval = iw->active_first(fixedKind); 1.55 + interval != Interval::end(); 1.56 + interval = interval->next()) { 1.57 + if (interval->current_to() > op->id() + 1) { 1.58 + // This interval is live out of this op so make sure 1.59 + // that this interval represents some value that's 1.60 + // referenced by this op either as an input or output. 1.61 + bool ok = false; 1.62 + for_each_visitor_mode(mode) { 1.63 + int n = visitor.opr_count(mode); 1.64 + for (int k = 0; k < n; k++) { 1.65 + LIR_Opr opr = visitor.opr_at(mode, k); 1.66 + if (opr->is_fixed_cpu()) { 1.67 + if (interval_at(reg_num(opr)) == interval) { 1.68 + ok = true; 1.69 + break; 1.70 + } 1.71 + int hi = reg_numHi(opr); 1.72 + if (hi != -1 && interval_at(hi) == interval) { 1.73 + ok = true; 1.74 + break; 1.75 + } 1.76 + } 1.77 + } 1.78 + } 1.79 + assert(ok, "fixed intervals should never be live across an oopmap point"); 1.80 + } 1.81 + } 1.82 + } 1.83 + } 1.84 + 1.85 // oop-maps at calls do not contain registers, so check is not needed 1.86 if (!visitor.has_call()) { 1.87
2.1 --- a/src/share/vm/includeDB_compiler1 Thu Apr 16 10:40:42 2009 -0700 2.2 +++ b/src/share/vm/includeDB_compiler1 Thu Apr 16 15:50:32 2009 -0700 2.3 @@ -270,6 +270,7 @@ 2.4 2.5 c1_LinearScan.cpp bitMap.inline.hpp 2.6 c1_LinearScan.cpp c1_CFGPrinter.hpp 2.7 +c1_LinearScan.cpp c1_CodeStubs.hpp 2.8 c1_LinearScan.cpp c1_Compilation.hpp 2.9 c1_LinearScan.cpp c1_FrameMap.hpp 2.10 c1_LinearScan.cpp c1_IR.hpp