# HG changeset patch # User Christian Haeubl # Date 1327112657 28800 # Node ID 271220b49abc4eb8e7416b203ce2d3a412f18dd0 # Parent f7251c729b311fb6345332bb34f307654f8db4df profiling info fixes diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.cri/src/com/oracle/max/cri/ri/RiProfilingInfo.java --- a/graal/com.oracle.max.cri/src/com/oracle/max/cri/ri/RiProfilingInfo.java Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.cri/src/com/oracle/max/cri/ri/RiProfilingInfo.java Fri Jan 20 18:24:17 2012 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2009, 2011, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -27,20 +27,42 @@ * Represents profiling information for one specific method. */ public interface RiProfilingInfo { - // iterating the profiling information - boolean setBCI(int bci); - int currentBCI(); - boolean next(); - boolean isAtValidData(); + /** + * Returns an estimate of how often the branch at the given byte code was taken. + * @return The estimated probability, with 0.0 meaning never and 1.0 meaning always, or -1 if this information is not available. + */ + double getBranchTakenProbability(int bci); + + /** + * Returns an estimate of how often the switch cases are taken at the given BCI. + * @return An array of double values that contains the estimated probabilities, with 0.0 meaning never and 1.0 meaning always, + * or null if this information is not available. The default case is stored as the last entry. + */ + double[] getSwitchProbabilities(int bci); + + /** + * Returns all types that were encountered at the given BCI. + * @return An array containing all types that were encountered during profiling at the given BCI, or null if not available. + */ + RiResolvedType[] getTypes(int bci); - // invokevirtual/invokeinterface - RiResolvedType[] getTypes(); - double[] getTypeProbabilities(); + /** + * Returns an estimate of how often each individual type is encountered at the given BCI. + * @return An array of double values that contains the estimated probabilities, with 0.0 meaning never and 1.0 meaning always, + * or null if this information is not available. + */ + double[] getTypeProbabilities(int bci); - // branches - double getBranchTakenProbability(); - double[] getSwitchProbabilities(); + /** + * Returns true if the given BCI did throw an implicit exception (NullPointerException, ClassCastException, + * ArrayStoreException, or ArithmeticException) during profiling. + * @return true if any of the exceptions was encountered during profiling, false otherwise. + */ + boolean getImplicitExceptionSeen(int bci); - // exceptions - boolean hasExceptionOccurred(); + /** + * Returns an estimate how often the current BCI was executed. + * @return the estimated execution count or -1 if not available. + */ + int getExecutionCount(int bci); } diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.compiler/src/com/oracle/max/graal/compiler/phases/InliningPhase.java --- a/graal/com.oracle.max.graal.compiler/src/com/oracle/max/graal/compiler/phases/InliningPhase.java Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.compiler/src/com/oracle/max/graal/compiler/phases/InliningPhase.java Fri Jan 20 18:24:17 2012 -0800 @@ -181,10 +181,11 @@ if (GraalOptions.ProbabilityAnalysis) { ratio = invoke.node().probability(); } else { - RiTypeProfile profile = caller.typeProfile(invoke.bci()); - if (profile != null && profile.count > 0) { + RiProfilingInfo profilingInfo = method.profilingInfo(); + int executionCount = profilingInfo.getExecutionCount(invoke.bci()); + if (executionCount > 0) { RiResolvedMethod parent = invoke.stateAfter().method(); - ratio = profile.count / (float) parent.invocationCount(); + ratio = executionCount / (float) parent.invocationCount(); } else { ratio = 1; } diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.compiler/src/com/oracle/max/graal/compiler/util/InliningUtil.java --- a/graal/com.oracle.max.graal.compiler/src/com/oracle/max/graal/compiler/util/InliningUtil.java Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.compiler/src/com/oracle/max/graal/compiler/util/InliningUtil.java Fri Jan 20 18:24:17 2012 -0800 @@ -263,14 +263,19 @@ } return null; } - RiTypeProfile profile = parent.typeProfile(invoke.bci()); - if (profile != null && profile.probabilities != null && profile.probabilities.length > 0 && profile.morphism == 1) { + + int invokeBCI = invoke.bci(); + RiProfilingInfo profilingInfo = parent.profilingInfo(); + RiResolvedType[] types = profilingInfo.getTypes(invokeBCI); + double[] typeProbabilities = profilingInfo.getTypeProbabilities(invokeBCI); + if (types != null && typeProbabilities != null && types.length == 1) { + assert types.length == typeProbabilities.length : "length must match"; if (GraalOptions.InlineWithTypeCheck) { // type check and inlining... - concrete = profile.types[0].resolveMethodImpl(callTarget.targetMethod()); + concrete = types[0].resolveMethodImpl(callTarget.targetMethod()); if (concrete != null && checkTargetConditions(concrete)) { double weight = callback == null ? 0 : callback.inliningWeight(parent, concrete, invoke); - return new TypeGuardInlineInfo(invoke, weight, level, concrete, profile.types[0], profile.probabilities[0]); + return new TypeGuardInlineInfo(invoke, weight, level, concrete, types[0], typeProbabilities[0]); } return null; } else { diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/bridge/CompilerToVMImpl.java --- a/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/bridge/CompilerToVMImpl.java Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/bridge/CompilerToVMImpl.java Fri Jan 20 18:24:17 2012 -0800 @@ -111,7 +111,7 @@ public native boolean RiType_isInitialized(HotSpotTypeResolved klass); @Override - public native RiProfilingInfo RiMethod_profilingInfo(HotSpotMethodResolved method); + public native HotSpotMethodData RiMethod_methodData(HotSpotMethodResolved method); @Override public native RiType getType(Class javaClass); diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HOTSPOTMETHODDATAACCESSOR.JAVA --- a/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HOTSPOTMETHODDATAACCESSOR.JAVA Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HOTSPOTMETHODDATAACCESSOR.JAVA Fri Jan 20 18:24:17 2012 -0800 @@ -28,12 +28,15 @@ int getTag(); int getBCI(HotSpotMethodData data, int position); int getSize(HotSpotMethodData data, int position); - boolean hasExceptionOccurred(HotSpotMethodData data, int position); - long getExecutionCount(HotSpotMethodDataAccessor data, int position); RiResolvedType[] getTypes(HotSpotMethodData data, int position); double[] getTypeProbabilities(HotSpotMethodData data, int position); double getBranchTakenProbability(HotSpotMethodData data, int position); + double[] getSwitchProbabilities(HotSpotMethodData data, int position); + + boolean getImplicitExceptionSeen(HotSpotMethodData data, int position); + + int getExecutionCount(HotSpotMethodData data, int position); } diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HOTSPOTPROFILINGINFOIMPL.JAVA --- a/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HOTSPOTPROFILINGINFOIMPL.JAVA Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HOTSPOTPROFILINGINFOIMPL.JAVA Fri Jan 20 18:24:17 2012 -0800 @@ -34,71 +34,104 @@ */ private static final long serialVersionUID = -8307682725047864875L; - private boolean atValidData; private int position; + private int hintPosition; + private int hintBCI; private HotSpotMethodDataAccessor dataAccessor; private HotSpotMethodData methodData; public HotSpotProfilingInfoImpl(Compiler compiler, HotSpotMethodData methodData) { super(compiler); this.methodData = methodData; - setBCI(0); - } - - public boolean setBCI(int value) { - assert value >= 0 : "invalid BCI"; - - seek(0); - while (atValidData && currentBCI() < value) { - next(); - } - - return atValidData; + hintPosition = 0; + hintBCI = -1; } @Override - public int currentBCI() { - return dataAccessor.getBCI(methodData, position); - } - - @Override - public boolean isAtValidData() { - return atValidData; - } - - @Override - public boolean next() { - return seek(position + dataAccessor.getSize(methodData, position)); - } - - @Override - public RiResolvedType[] getTypes() { + public RiResolvedType[] getTypes(int bci) { + findBCI(bci); return dataAccessor.getTypes(methodData, position); } @Override - public double[] getTypeProbabilities() { + public double[] getTypeProbabilities(int bci) { + findBCI(bci); return dataAccessor.getTypeProbabilities(methodData, position); } @Override - public double getBranchTakenProbability() { + public double getBranchTakenProbability(int bci) { + findBCI(bci); return dataAccessor.getBranchTakenProbability(methodData, position); } @Override - public double[] getSwitchProbabilities() { + public double[] getSwitchProbabilities(int bci) { + findBCI(bci); return dataAccessor.getSwitchProbabilities(methodData, position); } @Override - public boolean hasExceptionOccurred() { - return dataAccessor.hasExceptionOccurred(methodData, position); + public boolean getImplicitExceptionSeen(int bci) { + findBCI(bci); + return dataAccessor.getImplicitExceptionSeen(methodData, position); + } + + @Override + public int getExecutionCount(int bci) { + findBCI(bci); + return dataAccessor.getExecutionCount(methodData, position); } - private boolean seek(int value) { - position = value; - dataAccessor = methodData.getDataAccessor(position); - return dataAccessor != null; + private void findBCI(int targetBCI) { + assert targetBCI >= 0 : "invalid BCI"; + + if (methodData.hasNormalData()) { + int currentPosition = targetBCI < hintBCI ? 0 : hintPosition; + HotSpotMethodDataAccessor currentAccessor; + while ((currentAccessor = methodData.getNormalData(currentPosition)) != null) { + int currentBCI = currentAccessor.getBCI(methodData, currentPosition); + if (currentBCI == targetBCI) { + normalDataFound(currentAccessor, currentPosition, currentBCI); + return; + } else if (currentBCI > targetBCI) { + break; + } + currentAccessor = methodData.getNormalData(currentPosition); + } + } + + if (methodData.hasExtraData()) { + int currentPosition = 0; + HotSpotMethodDataAccessor currentAccessor; + while ((currentAccessor = methodData.getExtraData(currentPosition)) != null) { + int currentBCI = currentAccessor.getBCI(methodData, currentPosition); + if (currentBCI == targetBCI) { + extraDataFound(currentAccessor, currentPosition); + return; + } + } + } + + noDataFound(); + } + + private void normalDataFound(HotSpotMethodDataAccessor data, int pos, int bci) { + setCurrentData(data, pos); + this.hintPosition = position; + this.hintBCI = bci; + } + + private void extraDataFound(HotSpotMethodDataAccessor data, int pos) { + setCurrentData(data, pos); + } + + private void noDataFound() { + setCurrentData(HotSpotMethodData.getNoDataAccessor(), -1); + } + + private void setCurrentData(HotSpotMethodDataAccessor dataAccessor, int position) { + this.dataAccessor = dataAccessor; + this.position = position; } } diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HotSpotMethodData.java --- a/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HotSpotMethodData.java Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HotSpotMethodData.java Fri Jan 20 18:24:17 2012 -0800 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -37,6 +37,7 @@ private static final long serialVersionUID = -8873133496591225071L; // TODO (ch) use same logic as in NodeClass? private static final Unsafe unsafe = Unsafe.getUnsafe(); + private static final HotSpotMethodDataAccessor NO_DATA_ACCESSOR = new NoDataAccessor(); private static final HotSpotMethodDataAccessor[] PROFILE_DATA_ACCESSORS = { null, new BitData(), new CounterData(), new JumpData(), new TypeCheckData(), new VirtualCallData(), new RetData(), @@ -44,22 +45,51 @@ }; private Object javaMirror; - private int dataSize; + private int normalDataSize; + private int extraDataSize; private HotSpotMethodData(Compiler compiler) { super(compiler); - javaMirror = null; - dataSize = 0; throw new IllegalStateException("this constructor is never actually called, because the objects are allocated from within the VM"); } - public HotSpotMethodDataAccessor getDataAccessor(int position) { - if (position < 0 || position >= dataSize) { + public boolean hasNormalData() { + return normalDataSize > 0; + } + + public boolean hasExtraData() { + return extraDataSize > 0; + } + + public boolean isWithinData(int position) { + return position >= 0 && position < normalDataSize + extraDataSize; + } + + public HotSpotMethodDataAccessor getNormalData(int position) { + if (position >= normalDataSize) { return null; } - int tag = AbstractMethodDataAccessor.readTag(this, position); - assert tag > 0 && tag < PROFILE_DATA_ACCESSORS.length : "illegal tag"; + HotSpotMethodDataAccessor result = getData(position, 0); + assert result != null : "NO_DATA tag is not allowed"; + return result; + } + + public HotSpotMethodDataAccessor getExtraData(int position) { + if (position >= extraDataSize) { + return null; + } + return getData(position, normalDataSize); + } + + public static HotSpotMethodDataAccessor getNoDataAccessor() { + return NO_DATA_ACCESSOR; + } + + private HotSpotMethodDataAccessor getData(int position, int displacement) { + assert position >= 0 : "out of bounds"; + int tag = AbstractMethodDataAccessor.readTag(this, displacement + position); + assert tag >= 0 && tag < PROFILE_DATA_ACCESSORS.length : "illegal tag"; return PROFILE_DATA_ACCESSORS[tag]; } @@ -78,11 +108,20 @@ return unsafe.getInt(javaMirror, fullOffset) & 0xFFFFFFFFL; } + private int readUnsignedIntAsSignedInt(int position, int offsetInCells) { + long value = readUnsignedInt(position, offsetInCells); + return truncateLongToInt(value); + } + private int readInt(int position, int offsetInCells) { long fullOffset = computeFullOffset(position, offsetInCells); return unsafe.getInt(javaMirror, fullOffset); } + private static int truncateLongToInt(long value) { + return value > Integer.MAX_VALUE ? Integer.MAX_VALUE : (int) value; + } + private static int computeFullOffset(int position, int offsetInCells) { HotSpotVMConfig config = getHotSpotVMConfig(); return config.methodDataDataOffset + position + offsetInCells * config.dataLayoutCellSize; @@ -94,6 +133,8 @@ } private abstract static class AbstractMethodDataAccessor implements HotSpotMethodDataAccessor { + private static final int IMPLICIT_EXCEPTIONS_MASK = 0x0E; + private final int tag; private final int staticCellCount; @@ -125,33 +166,39 @@ } @Override - public boolean hasExceptionOccurred(HotSpotMethodData data, int position) { - return false; + public boolean getImplicitExceptionSeen(HotSpotMethodData data, int position) { + // TODO (ch) might return true too often because flags are also used for deoptimization reasons + return (getFlags(data, position) & IMPLICIT_EXCEPTIONS_MASK) != 0; } @Override public RiResolvedType[] getTypes(HotSpotMethodData data, int position) { - throw new IllegalStateException("not supported by current method data"); + return null; } @Override public double[] getTypeProbabilities(HotSpotMethodData data, int position) { - throw new IllegalStateException("not supported by current method data"); + return null; } @Override public double getBranchTakenProbability(HotSpotMethodData data, int position) { - throw new IllegalStateException("not supported by current method data"); + return -1; } @Override public double[] getSwitchProbabilities(HotSpotMethodData data, int position) { - throw new IllegalStateException("not supported by current method data"); + return null; } @Override - public long getExecutionCount(HotSpotMethodData data, int position) { - throw new IllegalStateException("not supported by current method data"); + public int getExecutionCount(HotSpotMethodData data, int position) { + return -1; + } + + protected int getFlags(HotSpotMethodData data, int position) { + HotSpotVMConfig config = getHotSpotVMConfig(); + return data.readUnsignedByte(position, config.dataLayoutFlagsOffset); } protected int getDynamicCellCount(HotSpotMethodData data, int position) { @@ -159,9 +206,30 @@ } } + private static class NoDataAccessor extends AbstractMethodDataAccessor { + private static final int NO_DATA_TAG = 0; + private static final int NO_DATA_SIZE = 0; + + protected NoDataAccessor() { + super(NO_DATA_TAG, NO_DATA_SIZE); + } + + @Override + public int getBCI(HotSpotMethodData data, int position) { + return -1; + } + + + @Override + public boolean getImplicitExceptionSeen(HotSpotMethodData data, int position) { + return false; + } + } + private static class BitData extends AbstractMethodDataAccessor { private static final int BIT_DATA_TAG = 1; private static final int BIT_DATA_CELLS = 0; + private static final int BIT_DATA_NULL_SEEN_FLAG = 0x01; private BitData() { super(BIT_DATA_TAG, BIT_DATA_CELLS); @@ -170,6 +238,10 @@ protected BitData(int tag, int staticCellCount) { super(tag, staticCellCount); } + + public boolean getNullSeen(HotSpotMethodData data, int position) { + return (getFlags(data, position) & BIT_DATA_NULL_SEEN_FLAG) != 0; + } } private static class CounterData extends BitData { @@ -186,12 +258,12 @@ } @Override - public long getExecutionCount(HotSpotMethodData data, int position) { + public int getExecutionCount(HotSpotMethodData data, int position) { return getCounterValue(data, position); } - protected long getCounterValue(HotSpotMethodData data, int position) { - return data.readUnsignedInt(position, COUNTER_DATA_COUNT_OFFSET); + protected int getCounterValue(HotSpotMethodData data, int position) { + return data.readUnsignedIntAsSignedInt(position, COUNTER_DATA_COUNT_OFFSET); } } @@ -215,8 +287,8 @@ } @Override - public long getExecutionCount(HotSpotMethodData data, int position) { - return data.readUnsignedInt(position, TAKEN_COUNT_OFFSET); + public int getExecutionCount(HotSpotMethodData data, int position) { + return data.readUnsignedIntAsSignedInt(position, TAKEN_COUNT_OFFSET); } public int getDisplacement(HotSpotMethodData data, int position) { @@ -285,12 +357,8 @@ } @Override - public long getExecutionCount(HotSpotMethodData data, int position) { - throw new IllegalStateException("not supported by current method data"); - } - - public long getTypeCheckFailedCount(HotSpotMethodData data, int position) { - return super.getCounterValue(data, position); + public int getExecutionCount(HotSpotMethodData data, int position) { + return -1; } } @@ -303,7 +371,7 @@ } @Override - public long getExecutionCount(HotSpotMethodData data, int position) { + public int getExecutionCount(HotSpotMethodData data, int position) { HotSpotVMConfig config = getHotSpotVMConfig(); int typeProfileWidth = config.typeProfileWidth; @@ -312,7 +380,8 @@ total += data.readUnsignedInt(position, getCountOffset(i)); } - return total + getCounterValue(data, position); + total += getCounterValue(data, position); + return truncateLongToInt(total); } } @@ -399,12 +468,19 @@ for (int i = 0; i < length; i++) { result[i] = result[i] / total; } + + // default case is expected as last entry + if (length >= 2) { + double defaultCase = result[0]; + result[0] = result[length - 1]; + result[length - 1] = defaultCase; + } } return result; } @Override - public long getExecutionCount(HotSpotMethodData data, int position) { + public int getExecutionCount(HotSpotMethodData data, int position) { int length = getLength(data, position); long total = 0; @@ -413,7 +489,7 @@ total += data.readUnsignedInt(position, offset); } - return total; + return truncateLongToInt(total); } private static int getCountOffset(int index) { diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HotSpotMethodResolvedImpl.java --- a/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HotSpotMethodResolvedImpl.java Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.hotspot/src/com/oracle/max/graal/hotspot/ri/HotSpotMethodResolvedImpl.java Fri Jan 20 18:24:17 2012 -0800 @@ -220,26 +220,37 @@ TTY.println("profile info for %s", this); TTY.println("canBeStaticallyBound: " + canBeStaticallyBound()); TTY.println("invocationCount: " + invocationCount()); + RiProfilingInfo profilingInfo = this.profilingInfo(); for (int i = 0; i < codeSize(); i++) { - if (branchProbability(i) != -1) { - TTY.println(" branchProbability@%d: %f", i, branchProbability(i)); + if (profilingInfo.getExecutionCount(i) != -1) { + TTY.println(" executionCount@%d: %d", i, profilingInfo.getExecutionCount(i)); } - if (exceptionProbability(i) > 0) { - TTY.println(" exceptionProbability@%d: %d", i, exceptionProbability(i)); + + if (profilingInfo.getBranchTakenProbability(i) != -1) { + TTY.println(" branchProbability@%d: %f", i, profilingInfo.getBranchTakenProbability(i)); } - RiTypeProfile profile = typeProfile(i); - if (profile != null && profile.count > 0) { - TTY.print(" profile@%d: count: %d, morphism: %d", i, profile.count, profile.morphism); - if (profile.types != null) { - TTY.print(", types:"); - for (int i2 = 0; i2 < profile.types.length; i2++) { - TTY.print(" %s (%f)", profile.types[i2], profile.probabilities[i2]); - } + + double[] switchProbabilities = profilingInfo.getSwitchProbabilities(i); + if (switchProbabilities != null) { + TTY.println(" switchProbabilities@%d:"); + for (int j = 0; j < switchProbabilities.length; j++) { + TTY.print(" %f", switchProbabilities[j]); + } + } + + if (profilingInfo.getImplicitExceptionSeen(i)) { + TTY.println(" implicitExceptionSeen@%d: true", i); + } + + RiResolvedType[] types = profilingInfo.getTypes(i); + double[] typeProbabilities = profilingInfo.getTypeProbabilities(i); + if (types != null && typeProbabilities != null) { + assert types.length == typeProbabilities.length : "length must match"; + TTY.print(" types@%d:", i); + for (int j = 0; j < types.length; j++) { + TTY.print(" %s (%f)", types[j], typeProbabilities[j]); } TTY.println(); - if (exceptionProbability(i) > 0) { - TTY.println(" exceptionProbability@%d: %d", i, exceptionProbability(i)); - } } } } diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.java/src/com/oracle/max/graal/java/BlockMap.java --- a/graal/com.oracle.max.graal.java/src/com/oracle/max/graal/java/BlockMap.java Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.java/src/com/oracle/max/graal/java/BlockMap.java Fri Jan 20 18:24:17 2012 -0800 @@ -236,6 +236,7 @@ // mark the entrypoints of basic blocks and build lists of successors for // all bytecodes that end basic blocks (i.e. goto, ifs, switches, throw, jsr, returns, ret) byte[] code = method.code(); + RiProfilingInfo profilingInfo = method.profilingInfo(); Block current = null; int bci = 0; while (bci < code.length) { @@ -282,7 +283,7 @@ case IFNULL: // fall through case IFNONNULL: { current = null; - double probability = useBranchPrediction ? method.branchProbability(bci) : -1; + double probability = useBranchPrediction ? profilingInfo.getBranchTakenProbability(bci) : -1; Block b1 = probability == 0.0 ? new DeoptBlock(bci + Bytes.beS2(code, bci + 1)) : makeBlock(bci + Bytes.beS2(code, bci + 1)); Block b2 = probability == 1.0 ? new DeoptBlock(bci + 3) : makeBlock(bci + 3); @@ -351,7 +352,7 @@ break; } default: { - if (canTrap(opcode, bci)) { + if (canTrap(opcode, bci, profilingInfo)) { canTrap.set(bci); } } @@ -360,7 +361,7 @@ } } - public boolean canTrap(int opcode, int bci) { + private static boolean canTrap(int opcode, int bci, RiProfilingInfo profilingInfo) { switch (opcode) { case INVOKESTATIC: case INVOKESPECIAL: @@ -387,7 +388,7 @@ case PUTFIELD: case GETFIELD: { if (GraalOptions.AllowExplicitExceptionChecks) { - return method.exceptionProbability(bci) > 0; + return profilingInfo.getImplicitExceptionSeen(bci); } } } diff -r f7251c729b31 -r 271220b49abc graal/com.oracle.max.graal.java/src/com/oracle/max/graal/java/GraphBuilderPhase.java --- a/graal/com.oracle.max.graal.java/src/com/oracle/max/graal/java/GraphBuilderPhase.java Thu Jan 19 16:29:35 2012 -0800 +++ b/graal/com.oracle.max.graal.java/src/com/oracle/max/graal/java/GraphBuilderPhase.java Fri Jan 20 18:24:17 2012 -0800 @@ -71,6 +71,7 @@ private RiConstantPool constantPool; private RiExceptionHandler[] exceptionHandlers; private RiResolvedMethod method; + private RiProfilingInfo profilingInfo; private BytecodeStream stream; // the bytecode stream private final LogStream log; @@ -115,6 +116,7 @@ @Override protected void run(StructuredGraph graph) { method = graph.method(); + profilingInfo = method.profilingInfo(); assert method.code() != null : "method must contain bytecodes: " + method; this.stream = new BytecodeStream(method.code()); this.constantPool = method.getConstantPool(); @@ -322,7 +324,7 @@ assert bci == FrameState.BEFORE_BCI || bci == bci() : "invalid bci"; if (GraalOptions.UseExceptionProbability && method.invocationCount() > GraalOptions.MatureInvocationCount) { - if (bci != FrameState.BEFORE_BCI && exceptionObject == null && method.exceptionProbability(bci) == 0) { + if (bci != FrameState.BEFORE_BCI && exceptionObject == null && !profilingInfo.getImplicitExceptionSeen(bci)) { return null; } } @@ -603,7 +605,7 @@ private void ifNode(ValueNode x, Condition cond, ValueNode y) { assert !x.isDeleted() && !y.isDeleted(); - double probability = method.branchProbability(bci()); + double probability = profilingInfo.getBranchTakenProbability(bci()); if (probability < 0) { if (GraalOptions.TraceProbability) { TTY.println("missing probability in " + method + " at bci " + bci()); @@ -1132,7 +1134,7 @@ } private double[] switchProbability(int numberOfCases, int bci) { - double[] prob = method.switchProbability(bci); + double[] prob = profilingInfo.getSwitchProbabilities(bci); if (prob != null) { assert prob.length == numberOfCases; } else {