| Index: pkg/compiler/lib/src/ssa/codegen.dart
|
| diff --git a/pkg/compiler/lib/src/ssa/codegen.dart b/pkg/compiler/lib/src/ssa/codegen.dart
|
| index f2c4b9f74a5adc6883724663fb46c6b076a468f8..1e98bc8e9f5225157261d5b985bf87652f1eef26 100644
|
| --- a/pkg/compiler/lib/src/ssa/codegen.dart
|
| +++ b/pkg/compiler/lib/src/ssa/codegen.dart
|
| @@ -2858,15 +2858,15 @@ class SsaCodeGenerator implements HVisitor, HBlockInformationVisitor {
|
|
|
| void visitTypeInfoReadVariable(HTypeInfoReadVariable node) {
|
| TypeVariableElement element = node.variable.element;
|
| - ClassElement context = element.enclosingClass;
|
|
|
| int index = element.index;
|
| - use(node.inputs[0]);
|
| + HInstruction object = node.object;
|
| + use(object);
|
| js.Expression receiver = pop();
|
|
|
| - if (needsSubstitutionForTypeVariableAccess(context)) {
|
| + if (typeVariableAccessNeedsSubstitution(element, object.instructionType)) {
|
| js.Expression typeName =
|
| - js.quoteName(backend.namer.runtimeTypeName(context));
|
| + js.quoteName(backend.namer.runtimeTypeName(element.enclosingClass));
|
| Element helperElement = helpers.getRuntimeTypeArgument;
|
| registry.registerStaticUse(
|
| new StaticUse.staticInvoke(helperElement, CallStructure.THREE_ARGS));
|
| @@ -2910,12 +2910,25 @@ class SsaCodeGenerator implements HVisitor, HBlockInformationVisitor {
|
| }
|
| }
|
|
|
| - bool needsSubstitutionForTypeVariableAccess(ClassElement cls) {
|
| + bool typeVariableAccessNeedsSubstitution(
|
| + TypeVariableElement element, TypeMask receiverMask) {
|
| + ClassElement cls = element.enclosingClass;
|
| ClassWorld classWorld = compiler.closedWorld;
|
| +
|
| + // See if the receiver type narrows the set of classes to ones that can be
|
| + // indexed.
|
| + // TODO(sra): Currently the only convenient query is [singleClass]. We
|
| + // should iterate over all the concrete classes in [receiverMask].
|
| + ClassElement receiverClass = receiverMask.singleClass(classWorld);
|
| + if (receiverClass != null) {
|
| + if (backend.rti.isTrivialSubstitution(receiverClass, cls)) {
|
| + return false;
|
| + }
|
| + }
|
| +
|
| if (classWorld.isUsedAsMixin(cls)) return true;
|
|
|
| - return compiler.closedWorld.anyStrictSubclassOf(cls,
|
| - (ClassElement subclass) {
|
| + return classWorld.anyStrictSubclassOf(cls, (ClassElement subclass) {
|
| return !backend.rti.isTrivialSubstitution(subclass, cls);
|
| });
|
| }
|
|
|