745 if (_max_monitors > 0 && _monitor_top != bad_monitors) {
746 int base = _max_locals + _max_stack;
747 len = base + _monitor_top;
748 for (int i = base; i < len; i++) {
749 dst[i] = src[i];
750 }
751 }
752 }
753
754
755 // Merge the states for the current block and the next. As long as a
756 // block is reachable the locals and stack must be merged. If the
757 // stack heights don't match then this is a verification error and
758 // it's impossible to interpret the code. Simultaneously monitor
759 // states are being check to see if they nest statically. If monitor
760 // depths match up then their states are merged. Otherwise the
761 // mismatch is simply recorded and interpretation continues since
762 // monitor matching is purely informational and doesn't say anything
763 // about the correctness of the code.
764 void GenerateOopMap::merge_state_into_bb(BasicBlock *bb) {
765 assert(bb->is_alive(), "merging state into a dead basicblock");
766
767 if (_stack_top == bb->_stack_top) {
768 // always merge local state even if monitors don't match.
769 if (merge_local_state_vectors(_state, bb->_state)) {
770 bb->set_changed(true);
771 }
772 if (_monitor_top == bb->_monitor_top) {
773 // monitors still match so continue merging monitor states.
774 if (merge_monitor_state_vectors(_state, bb->_state)) {
775 bb->set_changed(true);
776 }
777 } else {
778 if (TraceMonitorMismatch) {
779 report_monitor_mismatch("monitor stack height merge conflict");
780 }
781 // When the monitor stacks are not matched, we set _monitor_top to
782 // bad_monitors. This signals that, from here on, the monitor stack cannot
783 // be trusted. In particular, monitorexit bytecodes may throw
784 // exceptions. We mark this block as changed so that the change
1172 // monitor stack height is 0, we are about to pop a monitor
1173 // off of an empty stack. In either case, the bytecode
1174 // could throw an exception.
1175 if (_monitor_top != bad_monitors && _monitor_top != 0) {
1176 return;
1177 }
1178 break;
1179 }
1180
1181 if (_has_exceptions) {
1182 int bci = itr->bci();
1183 ExceptionTable exct(method());
1184 for(int i = 0; i< exct.length(); i++) {
1185 int start_pc = exct.start_pc(i);
1186 int end_pc = exct.end_pc(i);
1187 int handler_pc = exct.handler_pc(i);
1188 int catch_type = exct.catch_type_index(i);
1189
1190 if (start_pc <= bci && bci < end_pc) {
1191 BasicBlock *excBB = get_basic_block_at(handler_pc);
1192 CellTypeState *excStk = excBB->stack();
1193 CellTypeState *cOpStck = stack();
1194 CellTypeState cOpStck_0 = cOpStck[0];
1195 int cOpStackTop = _stack_top;
1196
1197 // Exception stacks are always the same.
1198 assert(method()->max_stack() > 0, "sanity check");
1199
1200 // We remembered the size and first element of "cOpStck"
1201 // above; now we temporarily set them to the appropriate
1202 // values for an exception handler. */
1203 cOpStck[0] = CellTypeState::make_slot_ref(_max_locals);
1204 _stack_top = 1;
1205
1206 merge_state_into_bb(excBB);
1207
1208 // Now undo the temporary change.
1209 cOpStck[0] = cOpStck_0;
1210 _stack_top = cOpStackTop;
1211
1786 void GenerateOopMap::do_monitorexit(int bci) {
1787 CellTypeState actual = pop();
1788 if (_monitor_top == bad_monitors) {
1789 return;
1790 }
1791 check_type(refCTS, actual);
1792 CellTypeState expected = monitor_pop();
1793 if (!actual.is_lock_reference() || !expected.equal(actual)) {
1794 // The monitor we are exiting is not verifiably the one
1795 // on the top of our monitor stack. This causes a monitor
1796 // mismatch.
1797 _monitor_top = bad_monitors;
1798 _monitor_safe = false;
1799
1800 // We need to mark this basic block as changed so that
1801 // this monitorexit will be visited again. We need to
1802 // do this to ensure that we have accounted for the
1803 // possibility that this bytecode will throw an
1804 // exception.
1805 BasicBlock* bb = get_basic_block_containing(bci);
1806 bb->set_changed(true);
1807 bb->_monitor_top = bad_monitors;
1808
1809 if (TraceMonitorMismatch) {
1810 report_monitor_mismatch("improper monitor pair");
1811 }
1812 } else {
1813 // This code is a fix for the case where we have repeated
1814 // locking of the same object in straightline code. We clear
1815 // out the lock when it is popped from the monitor stack
1816 // and replace it with an unobtrusive reference value that can
1817 // be locked again.
1818 //
1819 // Note: when generateOopMap is fixed to properly handle repeated,
1820 // nested, redundant locks on the same object, then this
1821 // fix will need to be removed at that time.
1822 replace_all_CTS_matches(actual, CellTypeState::make_line_ref(bci));
1823 }
1824 }
1825
2173
2174 // Note: Since we are skipping dead-code when we are reporting results, then
2175 // the no. of encountered gc-points might be fewer than the previously number
2176 // we have counted. (dead-code is a pain - it should be removed before we get here)
2177 fill_stackmap_epilog();
2178
2179 // Report initvars
2180 fill_init_vars(_init_vars);
2181
2182 _report_result = false;
2183 }
2184
2185 void GenerateOopMap::result_for_basicblock(int bci) {
2186 if (TraceNewOopMapGeneration) tty->print_cr("Report result pass for basicblock");
2187
2188 // We now want to report the result of the parse
2189 _report_result = true;
2190
2191 // Find basicblock and report results
2192 BasicBlock* bb = get_basic_block_containing(bci);
2193 assert(bb->is_reachable(), "getting result from unreachable basicblock");
2194 bb->set_changed(true);
2195 interp_bb(bb);
2196 }
2197
2198 //
2199 // Conflict handling code
2200 //
2201
2202 void GenerateOopMap::record_refval_conflict(int varNo) {
2203 assert(varNo>=0 && varNo< _max_locals, "index out of range");
2204
2205 if (TraceOopMapRewrites) {
2206 tty->print("### Conflict detected (local no: %d)\n", varNo);
2207 }
2208
2209 if (!_new_var_map) {
2210 _new_var_map = NEW_RESOURCE_ARRAY(int, _max_locals);
2211 for (int k = 0; k < _max_locals; k++) _new_var_map[k] = k;
2212 }
|
745 if (_max_monitors > 0 && _monitor_top != bad_monitors) {
746 int base = _max_locals + _max_stack;
747 len = base + _monitor_top;
748 for (int i = base; i < len; i++) {
749 dst[i] = src[i];
750 }
751 }
752 }
753
754
755 // Merge the states for the current block and the next. As long as a
756 // block is reachable the locals and stack must be merged. If the
757 // stack heights don't match then this is a verification error and
758 // it's impossible to interpret the code. Simultaneously monitor
759 // states are being check to see if they nest statically. If monitor
760 // depths match up then their states are merged. Otherwise the
761 // mismatch is simply recorded and interpretation continues since
762 // monitor matching is purely informational and doesn't say anything
763 // about the correctness of the code.
764 void GenerateOopMap::merge_state_into_bb(BasicBlock *bb) {
765 guarantee(bb != NULL, "null basicblock");
766 assert(bb->is_alive(), "merging state into a dead basicblock");
767
768 if (_stack_top == bb->_stack_top) {
769 // always merge local state even if monitors don't match.
770 if (merge_local_state_vectors(_state, bb->_state)) {
771 bb->set_changed(true);
772 }
773 if (_monitor_top == bb->_monitor_top) {
774 // monitors still match so continue merging monitor states.
775 if (merge_monitor_state_vectors(_state, bb->_state)) {
776 bb->set_changed(true);
777 }
778 } else {
779 if (TraceMonitorMismatch) {
780 report_monitor_mismatch("monitor stack height merge conflict");
781 }
782 // When the monitor stacks are not matched, we set _monitor_top to
783 // bad_monitors. This signals that, from here on, the monitor stack cannot
784 // be trusted. In particular, monitorexit bytecodes may throw
785 // exceptions. We mark this block as changed so that the change
1173 // monitor stack height is 0, we are about to pop a monitor
1174 // off of an empty stack. In either case, the bytecode
1175 // could throw an exception.
1176 if (_monitor_top != bad_monitors && _monitor_top != 0) {
1177 return;
1178 }
1179 break;
1180 }
1181
1182 if (_has_exceptions) {
1183 int bci = itr->bci();
1184 ExceptionTable exct(method());
1185 for(int i = 0; i< exct.length(); i++) {
1186 int start_pc = exct.start_pc(i);
1187 int end_pc = exct.end_pc(i);
1188 int handler_pc = exct.handler_pc(i);
1189 int catch_type = exct.catch_type_index(i);
1190
1191 if (start_pc <= bci && bci < end_pc) {
1192 BasicBlock *excBB = get_basic_block_at(handler_pc);
1193 guarantee(excBB != NULL, "no basic block for exception");
1194 CellTypeState *excStk = excBB->stack();
1195 CellTypeState *cOpStck = stack();
1196 CellTypeState cOpStck_0 = cOpStck[0];
1197 int cOpStackTop = _stack_top;
1198
1199 // Exception stacks are always the same.
1200 assert(method()->max_stack() > 0, "sanity check");
1201
1202 // We remembered the size and first element of "cOpStck"
1203 // above; now we temporarily set them to the appropriate
1204 // values for an exception handler. */
1205 cOpStck[0] = CellTypeState::make_slot_ref(_max_locals);
1206 _stack_top = 1;
1207
1208 merge_state_into_bb(excBB);
1209
1210 // Now undo the temporary change.
1211 cOpStck[0] = cOpStck_0;
1212 _stack_top = cOpStackTop;
1213
1788 void GenerateOopMap::do_monitorexit(int bci) {
1789 CellTypeState actual = pop();
1790 if (_monitor_top == bad_monitors) {
1791 return;
1792 }
1793 check_type(refCTS, actual);
1794 CellTypeState expected = monitor_pop();
1795 if (!actual.is_lock_reference() || !expected.equal(actual)) {
1796 // The monitor we are exiting is not verifiably the one
1797 // on the top of our monitor stack. This causes a monitor
1798 // mismatch.
1799 _monitor_top = bad_monitors;
1800 _monitor_safe = false;
1801
1802 // We need to mark this basic block as changed so that
1803 // this monitorexit will be visited again. We need to
1804 // do this to ensure that we have accounted for the
1805 // possibility that this bytecode will throw an
1806 // exception.
1807 BasicBlock* bb = get_basic_block_containing(bci);
1808 guarantee(bb != NULL, "no basic block for bci");
1809 bb->set_changed(true);
1810 bb->_monitor_top = bad_monitors;
1811
1812 if (TraceMonitorMismatch) {
1813 report_monitor_mismatch("improper monitor pair");
1814 }
1815 } else {
1816 // This code is a fix for the case where we have repeated
1817 // locking of the same object in straightline code. We clear
1818 // out the lock when it is popped from the monitor stack
1819 // and replace it with an unobtrusive reference value that can
1820 // be locked again.
1821 //
1822 // Note: when generateOopMap is fixed to properly handle repeated,
1823 // nested, redundant locks on the same object, then this
1824 // fix will need to be removed at that time.
1825 replace_all_CTS_matches(actual, CellTypeState::make_line_ref(bci));
1826 }
1827 }
1828
2176
2177 // Note: Since we are skipping dead-code when we are reporting results, then
2178 // the no. of encountered gc-points might be fewer than the previously number
2179 // we have counted. (dead-code is a pain - it should be removed before we get here)
2180 fill_stackmap_epilog();
2181
2182 // Report initvars
2183 fill_init_vars(_init_vars);
2184
2185 _report_result = false;
2186 }
2187
2188 void GenerateOopMap::result_for_basicblock(int bci) {
2189 if (TraceNewOopMapGeneration) tty->print_cr("Report result pass for basicblock");
2190
2191 // We now want to report the result of the parse
2192 _report_result = true;
2193
2194 // Find basicblock and report results
2195 BasicBlock* bb = get_basic_block_containing(bci);
2196 guarantee(bb != NULL, "no basic block for bci");
2197 assert(bb->is_reachable(), "getting result from unreachable basicblock");
2198 bb->set_changed(true);
2199 interp_bb(bb);
2200 }
2201
2202 //
2203 // Conflict handling code
2204 //
2205
2206 void GenerateOopMap::record_refval_conflict(int varNo) {
2207 assert(varNo>=0 && varNo< _max_locals, "index out of range");
2208
2209 if (TraceOopMapRewrites) {
2210 tty->print("### Conflict detected (local no: %d)\n", varNo);
2211 }
2212
2213 if (!_new_var_map) {
2214 _new_var_map = NEW_RESOURCE_ARRAY(int, _max_locals);
2215 for (int k = 0; k < _max_locals; k++) _new_var_map[k] = k;
2216 }
|