use of org.graalvm.compiler.nodes.extended.GuardingNode in project graal by oracle.
the class InstanceOfSnippets method instanceofSecondary.
/**
* A test against a restricted secondary type type.
*/
@Snippet
public static Object instanceofSecondary(KlassPointer hub, Object object, @VarargsParameter KlassPointer[] hints, @VarargsParameter boolean[] hintIsPositive, Object trueValue, Object falseValue, @ConstantParameter Counters counters) {
if (probability(NOT_FREQUENT_PROBABILITY, object == null)) {
counters.isNull.inc();
return falseValue;
}
GuardingNode anchorNode = SnippetAnchorNode.anchor();
KlassPointer objectHub = loadHubIntrinsic(PiNode.piCastNonNull(object, anchorNode));
// if we get an exact match: succeed immediately
ExplodeLoopNode.explodeLoop();
for (int i = 0; i < hints.length; i++) {
KlassPointer hintHub = hints[i];
boolean positive = hintIsPositive[i];
if (probability(NOT_FREQUENT_PROBABILITY, hintHub.equal(objectHub))) {
counters.hintsHit.inc();
return positive ? trueValue : falseValue;
}
}
counters.hintsMiss.inc();
if (!checkSecondarySubType(hub, objectHub, counters)) {
return falseValue;
}
return trueValue;
}
use of org.graalvm.compiler.nodes.extended.GuardingNode in project graal by oracle.
the class InstanceOfSnippets method isAssignableFrom.
@Snippet
public static Object isAssignableFrom(@NonNullParameter Class<?> thisClassNonNull, Class<?> otherClass, Object trueValue, Object falseValue, @ConstantParameter Counters counters) {
if (otherClass == null) {
DeoptimizeNode.deopt(DeoptimizationAction.InvalidateReprofile, DeoptimizationReason.NullCheckException);
return false;
}
GuardingNode anchorNode = SnippetAnchorNode.anchor();
Class<?> otherClassNonNull = PiNode.piCastNonNullClass(otherClass, anchorNode);
if (BranchProbabilityNode.probability(BranchProbabilityNode.NOT_LIKELY_PROBABILITY, thisClassNonNull == otherClassNonNull)) {
return trueValue;
}
KlassPointer thisHub = ClassGetHubNode.readClass(thisClassNonNull);
KlassPointer otherHub = ClassGetHubNode.readClass(otherClassNonNull);
if (BranchProbabilityNode.probability(BranchProbabilityNode.FAST_PATH_PROBABILITY, !thisHub.isNull())) {
if (BranchProbabilityNode.probability(BranchProbabilityNode.FAST_PATH_PROBABILITY, !otherHub.isNull())) {
GuardingNode guardNonNull = SnippetAnchorNode.anchor();
KlassPointer nonNullOtherHub = ClassGetHubNode.piCastNonNull(otherHub, guardNonNull);
if (TypeCheckSnippetUtils.checkUnknownSubType(thisHub, nonNullOtherHub, counters)) {
return trueValue;
}
}
}
// equal, return false.
return falseValue;
}
use of org.graalvm.compiler.nodes.extended.GuardingNode in project graal by oracle.
the class MethodHandleNode method maybeCastArgument.
/**
* Inserts a node to cast the argument at index to the given type if the given type is more
* concrete than the argument type.
*
* @param adder
* @param index of the argument to be cast
* @param type the type the argument should be cast to
*/
private static void maybeCastArgument(GraphAdder adder, ValueNode[] arguments, int index, JavaType type) {
ValueNode argument = arguments[index];
if (type instanceof ResolvedJavaType && !((ResolvedJavaType) type).isJavaLangObject()) {
Assumptions assumptions = adder.getAssumptions();
TypeReference targetType = TypeReference.create(assumptions, (ResolvedJavaType) type);
/*
* When an argument is a Word type, we can have a mismatch of primitive/object types
* here. Not inserting a PiNode is a safe fallback, and Word types need no additional
* type information anyway.
*/
if (targetType != null && !targetType.getType().isPrimitive() && !argument.getStackKind().isPrimitive()) {
ResolvedJavaType argumentType = StampTool.typeOrNull(argument.stamp(NodeView.DEFAULT));
if (argumentType == null || (argumentType.isAssignableFrom(targetType.getType()) && !argumentType.equals(targetType.getType()))) {
LogicNode inst = InstanceOfNode.createAllowNull(targetType, argument, null, null);
assert !inst.isAlive();
if (!inst.isTautology()) {
inst = adder.add(inst);
AnchoringNode guardAnchor = adder.getGuardAnchor();
DeoptimizationReason reason = DeoptimizationReason.ClassCastException;
DeoptimizationAction action = DeoptimizationAction.InvalidateRecompile;
JavaConstant speculation = JavaConstant.NULL_POINTER;
GuardingNode guard;
if (guardAnchor == null) {
FixedGuardNode fixedGuard = adder.add(new FixedGuardNode(inst, reason, action, speculation, false));
guard = fixedGuard;
} else {
GuardNode newGuard = adder.add(new GuardNode(inst, guardAnchor, reason, action, false, speculation));
adder.add(new ValueAnchorNode(newGuard));
guard = newGuard;
}
ValueNode valueNode = adder.add(PiNode.create(argument, StampFactory.object(targetType), guard.asNode()));
arguments[index] = valueNode;
}
}
}
}
}
use of org.graalvm.compiler.nodes.extended.GuardingNode in project graal by oracle.
the class PiNode method canonical.
public static ValueNode canonical(ValueNode object, Stamp stamp, GuardingNode guard) {
// Use most up to date stamp.
Stamp computedStamp = stamp.improveWith(object.stamp(NodeView.DEFAULT));
// The pi node does not give any additional information => skip it.
if (computedStamp.equals(object.stamp(NodeView.DEFAULT))) {
return object;
}
if (guard == null) {
// Try to merge the pi node with a load node.
if (object instanceof ReadNode && !object.hasMoreThanOneUsage()) {
ReadNode readNode = (ReadNode) object;
readNode.setStamp(readNode.stamp(NodeView.DEFAULT).improveWith(stamp));
return readNode;
}
} else {
for (Node n : guard.asNode().usages()) {
if (n instanceof PiNode) {
PiNode otherPi = (PiNode) n;
if (object == otherPi.object() && computedStamp.equals(otherPi.stamp(NodeView.DEFAULT))) {
/*
* Two PiNodes with the same guard and same result, so return the one with
* the more precise piStamp.
*/
Stamp newStamp = stamp.join(otherPi.piStamp);
if (newStamp.equals(otherPi.piStamp)) {
return otherPi;
}
}
}
}
}
return null;
}
use of org.graalvm.compiler.nodes.extended.GuardingNode in project graal by oracle.
the class StubUtil method verifyObject.
/**
* Verifies that a given object value is well formed if {@code -XX:+VerifyOops} is enabled.
*/
public static Object verifyObject(Object object) {
if (verifyOops(INJECTED_VMCONFIG)) {
Word verifyOopCounter = WordFactory.unsigned(verifyOopCounterAddress(INJECTED_VMCONFIG));
verifyOopCounter.writeInt(0, verifyOopCounter.readInt(0) + 1);
Pointer oop = Word.objectToTrackedPointer(object);
if (object != null) {
GuardingNode anchorNode = SnippetAnchorNode.anchor();
// make sure object is 'reasonable'
if (!oop.and(WordFactory.unsigned(verifyOopMask(INJECTED_VMCONFIG))).equal(WordFactory.unsigned(verifyOopBits(INJECTED_VMCONFIG)))) {
fatal("oop not in heap: %p", oop.rawValue());
}
KlassPointer klass = loadHubIntrinsic(PiNode.piCastNonNull(object, anchorNode));
if (klass.isNull()) {
fatal("klass for oop %p is null", oop.rawValue());
}
}
}
return object;
}
Aggregations