Skip to content

Commit 7dbd7d8

Browse files
author
Christian Wimmer
committed
[GR-42250] Class constants should not make types reachable during bytecode parsing.
PullRequest: graal/13098
2 parents 64b4036 + 2b5717b commit 7dbd7d8

File tree

5 files changed

+37
-30
lines changed

5 files changed

+37
-30
lines changed

substratevm/src/com.oracle.graal.pointsto/src/com/oracle/graal/pointsto/flow/MethodTypeFlowBuilder.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -357,6 +357,8 @@ protected boolean ignoreConstant(ConstantNode cn) {
357357
if (((BytecodeExceptionNode) usage).getExceptionKind() != BytecodeExceptionKind.CLASS_CAST) {
358358
return false;
359359
}
360+
} else if (usage instanceof FrameState) {
361+
/* FrameState usages are only for debugging and not necessary for correctness. */
360362
} else {
361363
return false;
362364
}

substratevm/src/com.oracle.graal.pointsto/src/com/oracle/graal/pointsto/heap/ImageHeapScanner.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -378,6 +378,11 @@ protected ImageHeapConstant createImageHeapObject(JavaConstant constant, ScanRea
378378
return value;
379379
}));
380380
}
381+
382+
AnalysisType typeFromClassConstant = (AnalysisType) constantReflection.asJavaType(constant);
383+
if (typeFromClassConstant != null) {
384+
typeFromClassConstant.registerAsReachable();
385+
}
381386
}
382387

383388
/*

substratevm/src/com.oracle.graal.pointsto/src/com/oracle/graal/pointsto/results/StrengthenGraphs.java

Lines changed: 30 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -314,12 +314,9 @@ public void simplify(Node n, SimplifierTool tool) {
314314

315315
} else if (n instanceof ClassIsAssignableFromNode) {
316316
ClassIsAssignableFromNode node = (ClassIsAssignableFromNode) n;
317-
ValueNode thisClass = node.getThisClass();
318-
if (thisClass.isConstant()) {
319-
AnalysisType thisType = (AnalysisType) tool.getConstantReflection().asJavaType(thisClass.asConstant());
320-
if (!thisType.isReachable()) {
321-
node.replaceAndDelete(LogicConstantNode.contradiction(graph));
322-
}
317+
AnalysisType nonReachableType = asConstantNonReachableType(node.getThisClass(), tool);
318+
if (nonReachableType != null) {
319+
node.replaceAndDelete(LogicConstantNode.contradiction(graph));
323320
}
324321

325322
} else if (n instanceof BytecodeExceptionNode) {
@@ -330,14 +327,23 @@ public void simplify(Node n, SimplifierTool tool) {
330327
*/
331328
BytecodeExceptionNode node = (BytecodeExceptionNode) n;
332329
if (node.getExceptionKind() == BytecodeExceptionNode.BytecodeExceptionKind.CLASS_CAST) {
333-
ValueNode expectedClass = node.getArguments().get(1);
334-
if (expectedClass.isConstant()) {
335-
AnalysisType expectedType = (AnalysisType) tool.getConstantReflection().asJavaType(expectedClass.asConstant());
336-
if (expectedType != null && !expectedType.isReachable()) {
337-
String expectedName = getTypeName(expectedType);
338-
ConstantNode expectedConstant = ConstantNode.forConstant(tool.getConstantReflection().forString(expectedName), tool.getMetaAccess(), graph);
339-
node.getArguments().set(1, expectedConstant);
340-
}
330+
AnalysisType nonReachableType = asConstantNonReachableType(node.getArguments().get(1), tool);
331+
if (nonReachableType != null) {
332+
node.getArguments().set(1, ConstantNode.forConstant(tool.getConstantReflection().forString(getTypeName(nonReachableType)), tool.getMetaAccess(), graph));
333+
}
334+
}
335+
336+
} else if (n instanceof FrameState) {
337+
/*
338+
* We do not want a type to be reachable only to be used for debugging purposes in a
339+
* FrameState. We could just null out the frame slot, but to leave as much
340+
* information as possible we replace the java.lang.Class with the type name.
341+
*/
342+
FrameState node = (FrameState) n;
343+
for (int i = 0; i < node.values().size(); i++) {
344+
AnalysisType nonReachableType = asConstantNonReachableType(node.values().get(i), tool);
345+
if (nonReachableType != null) {
346+
node.values().set(i, ConstantNode.forConstant(tool.getConstantReflection().forString(getTypeName(nonReachableType)), tool.getMetaAccess(), graph));
341347
}
342348
}
343349

@@ -352,6 +358,16 @@ public void simplify(Node n, SimplifierTool tool) {
352358
}
353359
}
354360

361+
private AnalysisType asConstantNonReachableType(ValueNode value, CoreProviders providers) {
362+
if (value != null && value.isConstant()) {
363+
AnalysisType expectedType = (AnalysisType) providers.getConstantReflection().asJavaType(value.asConstant());
364+
if (expectedType != null && !expectedType.isReachable()) {
365+
return expectedType;
366+
}
367+
}
368+
return null;
369+
}
370+
355371
private void handleInvoke(Invoke invoke, SimplifierTool tool) {
356372
PointsToAnalysis pta = getAnalysis();
357373
FixedNode node = invoke.asFixedNode();

substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/ameta/AnalysisConstantReflectionProvider.java

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -37,10 +37,8 @@
3737
import com.oracle.graal.pointsto.heap.value.ValueSupplier;
3838
import com.oracle.graal.pointsto.infrastructure.UniverseMetaAccess;
3939
import com.oracle.graal.pointsto.meta.AnalysisField;
40-
import com.oracle.graal.pointsto.meta.AnalysisType;
4140
import com.oracle.graal.pointsto.meta.AnalysisUniverse;
4241
import com.oracle.graal.pointsto.meta.UninitializedStaticFieldValueReader;
43-
import com.oracle.svm.core.BuildPhaseProvider;
4442
import com.oracle.svm.core.RuntimeAssertionsSupport;
4543
import com.oracle.svm.core.annotate.InjectAccessors;
4644
import com.oracle.svm.core.graal.meta.SharedConstantReflectionProvider;
@@ -308,16 +306,6 @@ public JavaConstant asJavaClass(ResolvedJavaType type) {
308306
return SubstrateObjectConstant.forObject(getHostVM().dynamicHub(type));
309307
}
310308

311-
protected static void registerAsReachable(SVMHost hostVM, DynamicHub dynamicHub) {
312-
assert dynamicHub != null;
313-
/* Make sure that the DynamicHub of this type ends up in the native image. */
314-
AnalysisType valueType = hostVM.lookupType(dynamicHub);
315-
if (!valueType.isReachable() && BuildPhaseProvider.isAnalysisFinished()) {
316-
throw VMError.shouldNotReachHere("Registering type as reachable after analysis: " + valueType);
317-
}
318-
valueType.registerAsReachable();
319-
}
320-
321309
private SVMHost getHostVM() {
322310
return (SVMHost) universe.hostVM();
323311
}

substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/ameta/HostedDynamicHubFeature.java

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -49,12 +49,8 @@ private Object replace(Object source) {
4949
if (source instanceof Class) {
5050
Class<?> clazz = (Class<?>) source;
5151
DynamicHub dynamicHub = hostVM.dynamicHub(metaAccess.lookupJavaType(clazz));
52-
AnalysisConstantReflectionProvider.registerAsReachable(hostVM, dynamicHub);
5352
return dynamicHub;
5453
}
55-
if (source instanceof DynamicHub) {
56-
AnalysisConstantReflectionProvider.registerAsReachable(hostVM, (DynamicHub) source);
57-
}
5854
return source;
5955
}
6056
}

0 commit comments

Comments
 (0)