| OLD | NEW |
| 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 import 'package:kernel/ast.dart' as ir; | 5 import 'package:kernel/ast.dart' as ir; |
| 6 | 6 |
| 7 import '../closure.dart'; | 7 import '../closure.dart'; |
| 8 import '../common.dart'; | 8 import '../common.dart'; |
| 9 import '../common/codegen.dart' show CodegenRegistry, CodegenWorkItem; | 9 import '../common/codegen.dart' show CodegenRegistry, CodegenWorkItem; |
| 10 import '../common/names.dart'; | 10 import '../common/names.dart'; |
| (...skipping 205 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 216 if (typeBuilder.checkOrTrustTypes) { | 216 if (typeBuilder.checkOrTrustTypes) { |
| 217 return typeBuilder.potentiallyCheckOrTrustType( | 217 return typeBuilder.potentiallyCheckOrTrustType( |
| 218 value, compiler.coreTypes.boolType, | 218 value, compiler.coreTypes.boolType, |
| 219 kind: HTypeConversion.BOOLEAN_CONVERSION_CHECK); | 219 kind: HTypeConversion.BOOLEAN_CONVERSION_CHECK); |
| 220 } | 220 } |
| 221 HInstruction result = new HBoolify(value, commonMasks.boolType); | 221 HInstruction result = new HBoolify(value, commonMasks.boolType); |
| 222 add(result); | 222 add(result); |
| 223 return result; | 223 return result; |
| 224 } | 224 } |
| 225 | 225 |
| 226 void _addClassTypeVariablesIfNeeded(ir.Member constructor) { |
| 227 var enclosing = astAdapter.getElement(constructor).enclosingElement; |
| 228 if (backend.classNeedsRti(enclosing)) { |
| 229 enclosing.typeVariables.forEach((TypeVariableType typeVariable) { |
| 230 HParameterValue param = |
| 231 addParameter(typeVariable.element, commonMasks.nonNullType); |
| 232 localsHandler.directLocals[ |
| 233 localsHandler.getTypeVariableAsLocal(typeVariable)] = param; |
| 234 }); |
| 235 } |
| 236 } |
| 237 |
| 226 /// Builds generative constructors. | 238 /// Builds generative constructors. |
| 227 /// | 239 /// |
| 228 /// Generative constructors are built in two stages. | 240 /// Generative constructors are built in two stages. |
| 229 /// | 241 /// |
| 230 /// First, the field values for every instance field for every class in the | 242 /// First, the field values for every instance field for every class in the |
| 231 /// class hierarchy are collected. Then, create a function body that sets | 243 /// class hierarchy are collected. Then, create a function body that sets |
| 232 /// all of the instance fields to the collected values and call the | 244 /// all of the instance fields to the collected values and call the |
| 233 /// constructor bodies for all constructors in the hierarchy. | 245 /// constructor bodies for all constructors in the hierarchy. |
| 234 void buildConstructor(ir.Constructor constructor) { | 246 void buildConstructor(ir.Constructor constructor) { |
| 235 openFunction(); | 247 openFunction(); |
| 248 _addClassTypeVariablesIfNeeded(constructor); |
| 236 | 249 |
| 237 // Collect field values for the current class. | 250 // Collect field values for the current class. |
| 238 // TODO(het): Does kernel always put field initializers in the constructor | 251 // TODO(het): Does kernel always put field initializers in the constructor |
| 239 // initializer list? If so then this is unnecessary... | 252 // initializer list? If so then this is unnecessary... |
| 240 Map<ir.Field, HInstruction> fieldValues = | 253 Map<ir.Field, HInstruction> fieldValues = |
| 241 _collectFieldValues(constructor.enclosingClass); | 254 _collectFieldValues(constructor.enclosingClass); |
| 242 | 255 |
| 243 _buildInitializers(constructor, fieldValues); | 256 _buildInitializers(constructor, fieldValues); |
| 244 | 257 |
| 245 final constructorArguments = <HInstruction>[]; | 258 final constructorArguments = <HInstruction>[]; |
| (...skipping 146 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 392 HInstruction original, DartType type, int kind) { | 405 HInstruction original, DartType type, int kind) { |
| 393 HInstruction reifiedType = buildFunctionType(type); | 406 HInstruction reifiedType = buildFunctionType(type); |
| 394 return new HTypeConversion.viaMethodOnType( | 407 return new HTypeConversion.viaMethodOnType( |
| 395 type, kind, original.instructionType, reifiedType, original); | 408 type, kind, original.instructionType, reifiedType, original); |
| 396 } | 409 } |
| 397 | 410 |
| 398 /// Builds a SSA graph for FunctionNodes, found in FunctionExpressions and | 411 /// Builds a SSA graph for FunctionNodes, found in FunctionExpressions and |
| 399 /// Procedures. | 412 /// Procedures. |
| 400 void buildFunctionNode(ir.FunctionNode functionNode) { | 413 void buildFunctionNode(ir.FunctionNode functionNode) { |
| 401 openFunction(); | 414 openFunction(); |
| 415 if (functionNode.parent is ir.Procedure && |
| 416 (functionNode.parent as ir.Procedure).kind == |
| 417 ir.ProcedureKind.Factory) { |
| 418 _addClassTypeVariablesIfNeeded(functionNode.parent); |
| 419 } |
| 402 functionNode.body.accept(this); | 420 functionNode.body.accept(this); |
| 403 closeFunction(); | 421 closeFunction(); |
| 404 } | 422 } |
| 405 | 423 |
| 406 void addImplicitInstantiation(DartType type) { | 424 void addImplicitInstantiation(DartType type) { |
| 407 if (type != null) { | 425 if (type != null) { |
| 408 currentImplicitInstantiations.add(type); | 426 currentImplicitInstantiations.add(type); |
| 409 } | 427 } |
| 410 } | 428 } |
| 411 | 429 |
| (...skipping 1523 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1935 } | 1953 } |
| 1936 | 1954 |
| 1937 @override | 1955 @override |
| 1938 void visitIsExpression(ir.IsExpression isExpression) { | 1956 void visitIsExpression(ir.IsExpression isExpression) { |
| 1939 isExpression.operand.accept(this); | 1957 isExpression.operand.accept(this); |
| 1940 HInstruction expression = pop(); | 1958 HInstruction expression = pop(); |
| 1941 push(buildIsNode(isExpression, isExpression.type, expression)); | 1959 push(buildIsNode(isExpression, isExpression.type, expression)); |
| 1942 } | 1960 } |
| 1943 | 1961 |
| 1944 HInstruction buildIsNode( | 1962 HInstruction buildIsNode( |
| 1945 ir.Node node, ir.DartType dart_type, HInstruction expression) { | 1963 ir.Node node, ir.DartType type, HInstruction expression) { |
| 1946 // TODO(sra): Convert the type testing logic here to use ir.DartType. | 1964 // Note: The call to "unalias" this type like in the original SSA builder is |
| 1947 DartType type = astAdapter.getDartType(dart_type); | 1965 // unnecessary in kernel because Kernel has no notion of typedef. |
| 1948 | 1966 // TODO(efortuna): Add test for this. |
| 1949 type = localsHandler.substInContext(type).unaliased; | 1967 DartType typeValue = localsHandler.substInContext( |
| 1950 | 1968 astAdapter.getDartType(type)); |
| 1951 if (type is MethodTypeVariableType) { | 1969 if (type is ir.InvalidType) { |
| 1952 return graph.addConstantBool(true, closedWorld); | 1970 generateTypeError(node, (typeValue.element as ErroneousElement).message); |
| 1971 return new HIs.compound( |
| 1972 typeValue, expression, pop(), commonMasks.boolType); |
| 1953 } | 1973 } |
| 1954 | 1974 |
| 1955 if (type is MalformedType) { | 1975 if (type is ir.FunctionType) { |
| 1956 ErroneousElement element = type.element; | 1976 List arguments = [buildFunctionType(typeValue), expression]; |
| 1957 generateTypeError(node, element.message); | 1977 _pushDynamicInvocation(node, null, arguments, |
| 1958 return new HIs.compound(type, expression, pop(), commonMasks.boolType); | 1978 selector: new Selector.call( |
| 1979 new PrivateName('_isTest', backend.helpers.jsHelperLibrary), |
| 1980 CallStructure.ONE_ARG)); |
| 1981 return new HIs.compound( |
| 1982 typeValue, expression, pop(), commonMasks.boolType); |
| 1959 } | 1983 } |
| 1960 | 1984 |
| 1961 if (type.isFunctionType) { | 1985 if (type is ir.TypeParameterType) { |
| 1962 List arguments = <HInstruction>[buildFunctionType(type), expression]; | 1986 HInstruction runtimeType = |
| 1963 _pushDynamicInvocation(node, commonMasks.boolType, arguments, | 1987 typeBuilder.addTypeVariableReference(typeValue, sourceElement); |
| 1964 selector: new Selector.call( | 1988 _pushStaticInvocation(astAdapter.checkSubtypeOfRuntimeType, |
| 1965 new PrivateName('_isTest', astAdapter.jsHelperLibrary), | 1989 <HInstruction>[expression, runtimeType], commonMasks.boolType); |
| 1966 CallStructure.ONE_ARG)); | 1990 return new HIs.variable( |
| 1967 return new HIs.compound(type, expression, pop(), commonMasks.boolType); | 1991 typeValue, expression, pop(), commonMasks.boolType); |
| 1968 } | 1992 } |
| 1969 | 1993 |
| 1970 if (type.isTypeVariable) { | 1994 if (_isInterfaceWithNoDynamicTypes(type)) { |
| 1971 HInstruction runtimeType = | 1995 HInstruction representations = typeBuilder |
| 1972 typeBuilder.addTypeVariableReference(type, sourceElement); | 1996 .buildTypeArgumentRepresentations(typeValue, sourceElement); |
| 1973 _pushStaticInvocation(astAdapter.checkSubtypeOfRuntimeType, | 1997 add(representations); |
| 1974 <HInstruction>[expression, runtimeType], commonMasks.boolType); | 1998 ClassElement element = typeValue.element; |
| 1975 return new HIs.variable(type, expression, pop(), commonMasks.boolType); | 1999 js.Name operator = backend.namer.operatorIs(element); |
| 2000 HInstruction isFieldName = |
| 2001 graph.addConstantStringFromName(operator, closedWorld); |
| 2002 HInstruction asFieldName = closedWorld.hasAnyStrictSubtype(element) |
| 2003 ? graph.addConstantStringFromName( |
| 2004 backend.namer.substitutionName(element), closedWorld) |
| 2005 : graph.addConstantNull(closedWorld); |
| 2006 List<HInstruction> inputs = <HInstruction>[ |
| 2007 expression, |
| 2008 isFieldName, |
| 2009 representations, |
| 2010 asFieldName |
| 2011 ]; |
| 2012 _pushStaticInvocation( |
| 2013 astAdapter.checkSubtype, inputs, commonMasks.boolType); |
| 2014 return new HIs.compound( |
| 2015 typeValue, expression, pop(), commonMasks.boolType); |
| 1976 } | 2016 } |
| 1977 | 2017 |
| 1978 // TODO(sra): Type with type parameters. | 2018 if (backend.hasDirectCheckFor(typeValue)) { |
| 2019 return new HIs.direct(typeValue, expression, commonMasks.boolType); |
| 2020 } |
| 2021 // The interceptor is not always needed. It is removed by optimization |
| 2022 // when the receiver type or tested type permit. |
| 2023 return new HIs.raw(typeValue, expression, _interceptorFor(expression), |
| 2024 commonMasks.boolType); |
| 2025 } |
| 1979 | 2026 |
| 1980 if (backend.hasDirectCheckFor(type)) { | 2027 bool _isInterfaceWithNoDynamicTypes(ir.DartType type) { |
| 1981 return new HIs.direct(type, expression, commonMasks.boolType); | 2028 bool isMethodTypeVariableType(ir.DartType typeArgType) { |
| 2029 return (typeArgType is ir.TypeParameterType && |
| 2030 typeArgType.parameter.parent is ir.FunctionNode); |
| 1982 } | 2031 } |
| 1983 | 2032 |
| 1984 // The interceptor is not always needed. It is removed by optimization | 2033 return type is ir.InterfaceType && |
| 1985 // when the receiver type or tested type permit. | 2034 (type as ir.InterfaceType).typeArguments.any( |
| 1986 HInterceptor interceptor = _interceptorFor(expression); | 2035 (ir.DartType typeArgType) => |
| 1987 return new HIs.raw(type, expression, interceptor, commonMasks.boolType); | 2036 typeArgType is! ir.DynamicType && |
| 2037 typeArgType is! ir.InvalidType && |
| 2038 !isMethodTypeVariableType(type)); |
| 1988 } | 2039 } |
| 1989 | 2040 |
| 1990 @override | 2041 @override |
| 1991 void visitThrow(ir.Throw throwNode) { | 2042 void visitThrow(ir.Throw throwNode) { |
| 1992 _visitThrowExpression(throwNode.expression); | 2043 _visitThrowExpression(throwNode.expression); |
| 1993 if (isReachable) { | 2044 if (isReachable) { |
| 1994 push(new HThrowExpression(pop(), null)); | 2045 push(new HThrowExpression(pop(), null)); |
| 1995 isReachable = false; | 2046 isReachable = false; |
| 1996 } | 2047 } |
| 1997 } | 2048 } |
| (...skipping 281 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2279 kernelBuilder.open(exitBlock); | 2330 kernelBuilder.open(exitBlock); |
| 2280 enterBlock.setBlockFlow( | 2331 enterBlock.setBlockFlow( |
| 2281 new HTryBlockInformation( | 2332 new HTryBlockInformation( |
| 2282 kernelBuilder.wrapStatementGraph(bodyGraph), | 2333 kernelBuilder.wrapStatementGraph(bodyGraph), |
| 2283 exception, | 2334 exception, |
| 2284 kernelBuilder.wrapStatementGraph(catchGraph), | 2335 kernelBuilder.wrapStatementGraph(catchGraph), |
| 2285 kernelBuilder.wrapStatementGraph(finallyGraph)), | 2336 kernelBuilder.wrapStatementGraph(finallyGraph)), |
| 2286 exitBlock); | 2337 exitBlock); |
| 2287 } | 2338 } |
| 2288 } | 2339 } |
| OLD | NEW |