use of org.graalvm.compiler.nodes.DeoptimizeNode in project graal by oracle.
the class TruffleBoundaryPhase method run.
@Override
@SuppressWarnings("deprecation")
protected void run(StructuredGraph graph) {
for (Node n : graph.getNodes()) {
if (n instanceof InvokeWithExceptionNode) {
InvokeWithExceptionNode invoke = (InvokeWithExceptionNode) n;
ExceptionObjectNode exceptionObject = (ExceptionObjectNode) invoke.exceptionEdge();
FixedNode originalNext = exceptionObject.next();
if (!(originalNext instanceof DeoptimizeNode)) {
TruffleBoundary truffleBoundary = invoke.callTarget().targetMethod().getAnnotation(TruffleBoundary.class);
if (truffleBoundary != null) {
if (!truffleBoundary.throwsControlFlowException() && truffleBoundary.transferToInterpreterOnException()) {
addDeoptimizeNode(graph, originalNext);
}
}
}
}
}
}
use of org.graalvm.compiler.nodes.DeoptimizeNode in project graal by oracle.
the class BytecodeParser method inline.
private boolean inline(ResolvedJavaMethod targetMethod, ResolvedJavaMethod inlinedMethod, BytecodeProvider intrinsicBytecodeProvider, ValueNode[] args) {
IntrinsicContext intrinsic = this.intrinsicContext;
if (intrinsic == null && !graphBuilderConfig.insertFullInfopoints() && targetMethod.equals(inlinedMethod) && (targetMethod.getModifiers() & (STATIC | SYNCHRONIZED)) == 0 && tryFastInlineAccessor(args, targetMethod)) {
return true;
}
if (intrinsic != null && intrinsic.isCallToOriginal(targetMethod)) {
if (intrinsic.isCompilationRoot()) {
// A root compiled intrinsic needs to deoptimize
// if the slow path is taken. During frame state
// assignment, the deopt node will get its stateBefore
// from the start node of the intrinsic
append(new DeoptimizeNode(InvalidateRecompile, RuntimeConstraint));
printInlining(targetMethod, inlinedMethod, true, "compilation root (bytecode parsing)");
return true;
} else {
if (intrinsic.getOriginalMethod().isNative()) {
printInlining(targetMethod, inlinedMethod, false, "native method (bytecode parsing)");
return false;
}
if (canInlinePartialIntrinsicExit() && InlinePartialIntrinsicExitDuringParsing.getValue(options)) {
// Otherwise inline the original method. Any frame state created
// during the inlining will exclude frame(s) in the
// intrinsic method (see FrameStateBuilder.create(int bci)).
notifyBeforeInline(inlinedMethod);
printInlining(targetMethod, inlinedMethod, true, "partial intrinsic exit (bytecode parsing)");
parseAndInlineCallee(intrinsic.getOriginalMethod(), args, null);
notifyAfterInline(inlinedMethod);
return true;
} else {
printInlining(targetMethod, inlinedMethod, false, "partial intrinsic exit (bytecode parsing)");
return false;
}
}
} else {
boolean isIntrinsic = intrinsicBytecodeProvider != null;
if (intrinsic == null && isIntrinsic) {
assert !inlinedMethod.equals(targetMethod);
intrinsic = new IntrinsicContext(targetMethod, inlinedMethod, intrinsicBytecodeProvider, INLINE_DURING_PARSING);
}
if (inlinedMethod.hasBytecodes()) {
notifyBeforeInline(inlinedMethod);
printInlining(targetMethod, inlinedMethod, true, "inline method (bytecode parsing)");
parseAndInlineCallee(inlinedMethod, args, intrinsic);
notifyAfterInline(inlinedMethod);
} else {
printInlining(targetMethod, inlinedMethod, false, "no bytecodes (abstract or native) (bytecode parsing)");
return false;
}
}
return true;
}
use of org.graalvm.compiler.nodes.DeoptimizeNode in project graal by oracle.
the class BytecodeParser method handleException.
private AbstractBeginNode handleException(ValueNode exceptionObject, int bci, boolean deoptimizeOnly) {
assert bci == BytecodeFrame.BEFORE_BCI || bci == bci() : "invalid bci";
debug.log("Creating exception dispatch edges at %d, exception object=%s, exception seen=%s", bci, exceptionObject, (profilingInfo == null ? "" : profilingInfo.getExceptionSeen(bci)));
FrameStateBuilder dispatchState = frameState.copy();
dispatchState.clearStack();
AbstractBeginNode dispatchBegin;
if (exceptionObject == null) {
ExceptionObjectNode newExceptionObject = graph.add(new ExceptionObjectNode(metaAccess));
dispatchBegin = newExceptionObject;
dispatchState.push(JavaKind.Object, dispatchBegin);
dispatchState.setRethrowException(true);
newExceptionObject.setStateAfter(dispatchState.create(bci, newExceptionObject));
} else {
dispatchBegin = graph.add(new BeginNode());
dispatchState.push(JavaKind.Object, exceptionObject);
dispatchState.setRethrowException(true);
}
this.controlFlowSplit = true;
FixedWithNextNode finishedDispatch = finishInstruction(dispatchBegin, dispatchState);
if (deoptimizeOnly) {
DeoptimizeNode deoptimizeNode = graph.add(new DeoptimizeNode(DeoptimizationAction.None, DeoptimizationReason.TransferToInterpreter));
dispatchBegin.setNext(BeginNode.begin(deoptimizeNode));
} else {
createHandleExceptionTarget(finishedDispatch, bci, dispatchState);
}
return dispatchBegin;
}
use of org.graalvm.compiler.nodes.DeoptimizeNode in project graal by oracle.
the class BytecodeParser method genDynamicInvokeHelper.
private boolean genDynamicInvokeHelper(ResolvedJavaMethod target, int cpi, int opcode) {
assert opcode == INVOKEDYNAMIC || opcode == INVOKEVIRTUAL;
InvokeDynamicPlugin invokeDynamicPlugin = graphBuilderConfig.getPlugins().getInvokeDynamicPlugin();
if (opcode == INVOKEVIRTUAL && invokeDynamicPlugin != null && !invokeDynamicPlugin.isResolvedDynamicInvoke(this, cpi, opcode)) {
// regular invokevirtual, let caller handle it
return false;
}
if (GeneratePIC.getValue(options) && (invokeDynamicPlugin == null || !invokeDynamicPlugin.supportsDynamicInvoke(this, cpi, opcode))) {
// bail out if static compiler and no dynamic type support
append(new DeoptimizeNode(InvalidateRecompile, Unresolved));
return true;
}
JavaConstant appendix = constantPool.lookupAppendix(cpi, opcode);
ValueNode appendixNode = null;
if (appendix != null) {
if (invokeDynamicPlugin != null) {
invokeDynamicPlugin.recordDynamicMethod(this, cpi, opcode, target);
// Will perform runtime type checks and static initialization
FrameState stateBefore = frameState.create(bci(), getNonIntrinsicAncestor(), false, null, null);
appendixNode = invokeDynamicPlugin.genAppendixNode(this, cpi, opcode, appendix, stateBefore);
} else {
appendixNode = ConstantNode.forConstant(appendix, metaAccess, graph);
}
frameState.push(JavaKind.Object, appendixNode);
} else if (GeneratePIC.getValue(options)) {
// Need to emit runtime guard and perform static initialization.
// Not implemented yet.
append(new DeoptimizeNode(InvalidateRecompile, Unresolved));
return true;
}
boolean hasReceiver = (opcode == INVOKEDYNAMIC) ? false : !target.isStatic();
ValueNode[] args = frameState.popArguments(target.getSignature().getParameterCount(hasReceiver));
if (hasReceiver) {
appendInvoke(InvokeKind.Virtual, target, args);
} else {
appendInvoke(InvokeKind.Static, target, args);
}
return true;
}
use of org.graalvm.compiler.nodes.DeoptimizeNode in project graal by oracle.
the class BytecodeParser method handleUnresolvedInvoke.
/**
* @param javaMethod
* @param invokeKind
*/
protected void handleUnresolvedInvoke(JavaMethod javaMethod, InvokeKind invokeKind) {
assert !graphBuilderConfig.unresolvedIsError();
DeoptimizeNode deopt = append(new DeoptimizeNode(InvalidateRecompile, Unresolved));
deopt.updateNodeSourcePosition(() -> createBytecodePosition());
}
Aggregations