001/* 002 * This file is part of the Jikes RVM project (http://jikesrvm.org). 003 * 004 * This file is licensed to You under the Eclipse Public License (EPL); 005 * You may not use this file except in compliance with the License. You 006 * may obtain a copy of the License at 007 * 008 * http://www.opensource.org/licenses/eclipse-1.0.php 009 * 010 * See the COPYRIGHT.txt file distributed with this work for information 011 * regarding copyright ownership. 012 */ 013package org.jikesrvm.osr; 014 015import static org.jikesrvm.compilers.opt.driver.OptConstants.OSR_PROLOGUE; 016 017import java.util.Enumeration; 018 019import org.jikesrvm.compilers.opt.OptOptions; 020import org.jikesrvm.compilers.opt.driver.CompilerPhase; 021import org.jikesrvm.compilers.opt.inlining.InlineSequence; 022import org.jikesrvm.compilers.opt.ir.IR; 023import org.jikesrvm.compilers.opt.ir.Instruction; 024 025/** 026 * OSR_AdjustBCIndex is an optimizing phase performed on HIR. 027 * It adjust the byte code index of instructions from specialized 028 * byte code to its original byte code. 029 */ 030public class AdjustBCIndexes extends CompilerPhase { 031 032 @Override 033 public final boolean shouldPerform(OptOptions options) { 034 return true; 035 } 036 037 /** 038 * Return this instance of this phase. This phase contains no 039 * per-compilation instance fields. 040 * @param ir not used 041 * @return this 042 */ 043 @Override 044 public CompilerPhase newExecution(IR ir) { 045 return this; 046 } 047 048 @Override 049 public final String getName() { 050 return "AdjustBytecodeIndexes"; 051 } 052 053 @Override 054 public final void perform(IR ir) { 055 if (!ir.method.isForOsrSpecialization()) return; 056 int offset = ir.method.getOsrPrologueLength(); 057 058 for (Enumeration<Instruction> ie = ir.forwardInstrEnumerator(); ie.hasMoreElements();) { 059 Instruction s = ie.nextElement(); 060 061 if ((s.position != null) && (s.position.method != ir.method)) { 062 // also adjust InlineSequence of the direct callee 063 InlineSequence caller = s.position.caller; 064 if ((caller != null) && (caller.method == ir.method)) { 065 // adjust the call site's bcIndex 066 s.position.bcIndex -= offset; 067 } 068 continue; 069 } 070 071 if (s.bcIndex >= offset) { 072 s.bcIndex -= offset; 073 } else if (s.bcIndex >= 0) { 074 s.bcIndex = OSR_PROLOGUE; 075 } 076 } 077 } 078}