| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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 interface TreeElements { | 5 interface TreeElements { |
| 6 Element operator[](Node node); | 6 Element operator[](Node node); |
| 7 Selector getSelector(Send send); | 7 Selector getSelector(Send send); |
| 8 Type getType(TypeAnnotation annotation); | 8 Type getType(TypeAnnotation annotation); |
| 9 } | 9 } |
| 10 | 10 |
| (...skipping 444 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 455 warning(initialized[name], MessageKind.ALREADY_INITIALIZED, [name]); | 455 warning(initialized[name], MessageKind.ALREADY_INITIALIZED, [name]); |
| 456 } | 456 } |
| 457 initialized[name] = init; | 457 initialized[name] = init; |
| 458 // Resolve initializing value. | 458 // Resolve initializing value. |
| 459 visitor.visitInStaticContext(init.arguments.head); | 459 visitor.visitInStaticContext(init.arguments.head); |
| 460 } | 460 } |
| 461 | 461 |
| 462 Element resolveSuperOrThisForSend(FunctionElement constructor, | 462 Element resolveSuperOrThisForSend(FunctionElement constructor, |
| 463 FunctionExpression functionNode, | 463 FunctionExpression functionNode, |
| 464 Send call) { | 464 Send call) { |
| 465 // Resolve the arguments, and make sure the call gets a selector | 465 // Resolve the selector and the arguments. |
| 466 // by calling handleArguments. | |
| 467 ResolverTask resolver = visitor.compiler.resolver; | 466 ResolverTask resolver = visitor.compiler.resolver; |
| 468 visitor.inStaticContext( () => visitor.handleArguments(call) ); | 467 visitor.inStaticContext(() { |
| 468 visitor.resolveSelector(call); |
| 469 visitor.visitArguments(call.argumentsNode); |
| 470 }); |
| 469 Selector selector = visitor.mapping.getSelector(call); | 471 Selector selector = visitor.mapping.getSelector(call); |
| 470 bool isSuperCall = Initializers.isSuperConstructorCall(call); | 472 bool isSuperCall = Initializers.isSuperConstructorCall(call); |
| 471 SourceString constructorName = resolver.getConstructorName(call); | 473 SourceString constructorName = resolver.getConstructorName(call); |
| 472 Element result = resolveSuperOrThis( | 474 Element result = resolveSuperOrThis( |
| 473 constructor, isSuperCall, false, constructorName, selector, call); | 475 constructor, isSuperCall, false, constructorName, selector, call); |
| 474 visitor.useElement(call, result); | 476 visitor.useElement(call, result); |
| 475 return result; | 477 return result; |
| 476 } | 478 } |
| 477 | 479 |
| 478 void resolveImplicitSuperConstructorSend(FunctionElement constructor, | 480 void resolveImplicitSuperConstructorSend(FunctionElement constructor, |
| 479 FunctionExpression functionNode) { | 481 FunctionExpression functionNode) { |
| 480 // If the class has a super resolve the implicit super call. | 482 // If the class has a super resolve the implicit super call. |
| 481 ClassElement classElement = constructor.getEnclosingClass(); | 483 ClassElement classElement = constructor.getEnclosingClass(); |
| 482 ClassElement superClass = classElement.superclass; | 484 ClassElement superClass = classElement.superclass; |
| 483 if (classElement != visitor.compiler.objectClass) { | 485 if (classElement != visitor.compiler.objectClass) { |
| 484 assert(superClass !== null); | 486 assert(superClass !== null); |
| 485 assert(superClass.resolutionState == ClassElement.STATE_DONE); | 487 assert(superClass.resolutionState == ClassElement.STATE_DONE); |
| 488 SourceString name = const SourceString(''); |
| 489 Selector call = new Selector.call(name, classElement.getLibrary(), 0); |
| 486 var element = resolveSuperOrThis(constructor, true, true, | 490 var element = resolveSuperOrThis(constructor, true, true, |
| 487 const SourceString(''), | 491 name, call, functionNode); |
| 488 Selector.INVOCATION_0, functionNode); | |
| 489 visitor.world.registerStaticUse(element); | 492 visitor.world.registerStaticUse(element); |
| 490 } | 493 } |
| 491 } | 494 } |
| 492 | 495 |
| 493 Element resolveSuperOrThis(FunctionElement constructor, | 496 Element resolveSuperOrThis(FunctionElement constructor, |
| 494 bool isSuperCall, | 497 bool isSuperCall, |
| 495 bool isImplicitSuperCall, | 498 bool isImplicitSuperCall, |
| 496 SourceString constructorName, | 499 SourceString constructorName, |
| 497 Selector selector, | 500 Selector selector, |
| 498 Node diagnosticNode) { | 501 Node diagnosticNode) { |
| (...skipping 608 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1107 visit(node.thenPart); | 1110 visit(node.thenPart); |
| 1108 visit(node.elsePart); | 1111 visit(node.elsePart); |
| 1109 } | 1112 } |
| 1110 | 1113 |
| 1111 static bool isLogicalOperator(Identifier op) { | 1114 static bool isLogicalOperator(Identifier op) { |
| 1112 String str = op.source.stringValue; | 1115 String str = op.source.stringValue; |
| 1113 return (str === '&&' || str == '||' || str == '!'); | 1116 return (str === '&&' || str == '||' || str == '!'); |
| 1114 } | 1117 } |
| 1115 | 1118 |
| 1116 Element resolveSend(Send node) { | 1119 Element resolveSend(Send node) { |
| 1120 Selector selector = resolveSelector(node); |
| 1121 |
| 1117 if (node.receiver === null) { | 1122 if (node.receiver === null) { |
| 1118 return node.selector.accept(this); | 1123 return node.selector.accept(this); |
| 1119 } | 1124 } |
| 1125 |
| 1120 var oldCategory = allowedCategory; | 1126 var oldCategory = allowedCategory; |
| 1121 allowedCategory |= | 1127 allowedCategory |= |
| 1122 ElementCategory.CLASS | ElementCategory.PREFIX | ElementCategory.SUPER; | 1128 ElementCategory.CLASS | ElementCategory.PREFIX | ElementCategory.SUPER; |
| 1123 Element resolvedReceiver = visit(node.receiver); | 1129 Element resolvedReceiver = visit(node.receiver); |
| 1124 allowedCategory = oldCategory; | 1130 allowedCategory = oldCategory; |
| 1125 | 1131 |
| 1126 Element target; | 1132 Element target; |
| 1127 SourceString name = node.selector.asIdentifier().source; | 1133 SourceString name = node.selector.asIdentifier().source; |
| 1128 if (name.stringValue === 'this') { | 1134 if (name.stringValue === 'this') { |
| 1129 error(node.selector, MessageKind.GENERIC, ["expected an identifier"]); | 1135 error(node.selector, MessageKind.GENERIC, ["expected an identifier"]); |
| 1130 } else if (node.isSuperCall) { | 1136 } else if (node.isSuperCall) { |
| 1131 if (node.isOperator) { | 1137 if (node.isOperator) { |
| 1132 if (isUserDefinableOperator(name.stringValue)) { | 1138 if (isUserDefinableOperator(name.stringValue)) { |
| 1133 name = Elements.constructOperatorName(const SourceString('operator'), | 1139 name = selector.name; |
| 1134 name); | |
| 1135 } else { | 1140 } else { |
| 1136 error(node.selector, MessageKind.ILLEGAL_SUPER_SEND, [name]); | 1141 error(node.selector, MessageKind.ILLEGAL_SUPER_SEND, [name]); |
| 1137 } | 1142 } |
| 1138 } | 1143 } |
| 1139 if (!inInstanceContext) { | 1144 if (!inInstanceContext) { |
| 1140 error(node.receiver, MessageKind.NO_INSTANCE_AVAILABLE, [name]); | 1145 error(node.receiver, MessageKind.NO_INSTANCE_AVAILABLE, [name]); |
| 1141 return null; | 1146 return null; |
| 1142 } | 1147 } |
| 1143 if (currentClass.supertype === null) { | 1148 if (currentClass.supertype === null) { |
| 1144 // This is just to guard against internal errors, so no need | 1149 // This is just to guard against internal errors, so no need |
| (...skipping 26 matching lines...) Expand all Loading... |
| 1171 Type resolveTypeTest(Node argument) { | 1176 Type resolveTypeTest(Node argument) { |
| 1172 TypeAnnotation node = argument.asTypeAnnotation(); | 1177 TypeAnnotation node = argument.asTypeAnnotation(); |
| 1173 if (node === null) { | 1178 if (node === null) { |
| 1174 // node is of the form !Type. | 1179 // node is of the form !Type. |
| 1175 node = argument.asSend().receiver.asTypeAnnotation(); | 1180 node = argument.asSend().receiver.asTypeAnnotation(); |
| 1176 if (node === null) compiler.cancel("malformed send"); | 1181 if (node === null) compiler.cancel("malformed send"); |
| 1177 } | 1182 } |
| 1178 return resolveTypeRequired(node); | 1183 return resolveTypeRequired(node); |
| 1179 } | 1184 } |
| 1180 | 1185 |
| 1181 void handleArguments(Send node) { | 1186 static Selector computeSendSelector(Send node, LibraryElement library) { |
| 1182 int count = 0; | 1187 // First determine if this is part of an assignment. |
| 1183 List<SourceString> namedArguments = <SourceString>[]; | 1188 bool isSet = node is SendSet; |
| 1189 |
| 1190 if (node.isIndex) { |
| 1191 return isSet ? new Selector.indexSet() : new Selector.index(); |
| 1192 } |
| 1193 |
| 1194 if (node.isOperator) { |
| 1195 SourceString source = node.selector.asOperator().source; |
| 1196 switch (source.stringValue) { |
| 1197 case '!' : case '&&' : case '||': |
| 1198 case 'is' : case 'as' : |
| 1199 case '===': case '!==': |
| 1200 case '>>>': |
| 1201 return null; |
| 1202 } |
| 1203 return node.arguments.isEmpty() |
| 1204 ? new Selector.unaryOperator(source) |
| 1205 : new Selector.binaryOperator(source); |
| 1206 } |
| 1207 |
| 1208 Identifier identifier = node.selector.asIdentifier(); |
| 1209 if (node.isPropertyAccess) { |
| 1210 assert(!isSet); |
| 1211 return new Selector.getter(identifier.source, library); |
| 1212 } else if (isSet) { |
| 1213 return new Selector.setter(identifier.source, library); |
| 1214 } |
| 1215 |
| 1216 // Compute the arity and the list of named arguments. |
| 1217 int arity = 0; |
| 1218 List<SourceString> named = <SourceString>[]; |
| 1219 for (Link<Node> link = node.argumentsNode.nodes; |
| 1220 !link.isEmpty(); |
| 1221 link = link.tail) { |
| 1222 Expression argument = link.head; |
| 1223 if (argument.asNamedArgument() != null) { |
| 1224 named.add((argument as NamedArgument).name.source); |
| 1225 } |
| 1226 arity++; |
| 1227 } |
| 1228 |
| 1229 // If we're invoking a closure, we do not have an identifier. In |
| 1230 // that case, we create a wildcard selector that can call any |
| 1231 // method that may have been closurized. |
| 1232 return (identifier == null) |
| 1233 ? new Selector.callAny(arity, named) |
| 1234 : new Selector.call(identifier.source, library, arity, named); |
| 1235 } |
| 1236 |
| 1237 Selector resolveSelector(Send node) { |
| 1238 LibraryElement library = enclosingElement.getLibrary(); |
| 1239 Selector selector = computeSendSelector(node, library); |
| 1240 if (selector != null) mapping.setSelector(node, selector); |
| 1241 return selector; |
| 1242 } |
| 1243 |
| 1244 void visitArguments(NodeList list) { |
| 1184 bool seenNamedArgument = false; | 1245 bool seenNamedArgument = false; |
| 1185 for (Link<Node> link = node.argumentsNode.nodes; | 1246 for (Link<Node> link = list.nodes; !link.isEmpty(); link = link.tail) { |
| 1186 !link.isEmpty(); | |
| 1187 link = link.tail) { | |
| 1188 count++; | |
| 1189 Expression argument = link.head; | 1247 Expression argument = link.head; |
| 1190 visit(argument); | 1248 visit(argument); |
| 1191 if (argument.asNamedArgument() != null) { | 1249 if (argument.asNamedArgument() != null) { |
| 1192 seenNamedArgument = true; | 1250 seenNamedArgument = true; |
| 1193 NamedArgument named = argument; | |
| 1194 namedArguments.add(named.name.source); | |
| 1195 } else if (seenNamedArgument) { | 1251 } else if (seenNamedArgument) { |
| 1196 error(argument, MessageKind.INVALID_ARGUMENT_AFTER_NAMED); | 1252 error(argument, MessageKind.INVALID_ARGUMENT_AFTER_NAMED); |
| 1197 } | 1253 } |
| 1198 } | 1254 } |
| 1199 mapping.setSelector(node, new Selector.invocation(count, namedArguments)); | |
| 1200 } | 1255 } |
| 1201 | 1256 |
| 1202 visitSend(Send node) { | 1257 visitSend(Send node) { |
| 1203 Element target = resolveSend(node); | 1258 Element target = resolveSend(node); |
| 1204 if (node.isOperator) { | 1259 if (node.isOperator) { |
| 1205 Operator op = node.selector.asOperator(); | 1260 Operator op = node.selector.asOperator(); |
| 1206 if (op.source.stringValue === 'is' || op.source.stringValue === 'as') { | 1261 if (op.source.stringValue === 'is' || op.source.stringValue === 'as') { |
| 1207 resolveTypeTest(node.arguments.head); | 1262 resolveTypeTest(node.arguments.head); |
| 1208 assert(node.arguments.tail.isEmpty()); | 1263 assert(node.arguments.tail.isEmpty()); |
| 1209 mapping.setSelector(node, Selector.BINARY_OPERATOR); | |
| 1210 } else if (node.arguments.isEmpty()) { | 1264 } else if (node.arguments.isEmpty()) { |
| 1211 assert(op.token.kind !== PLUS_TOKEN); | 1265 assert(op.token.kind !== PLUS_TOKEN); |
| 1212 mapping.setSelector(node, Selector.UNARY_OPERATOR); | |
| 1213 } else { | 1266 } else { |
| 1214 visit(node.argumentsNode); | 1267 visit(node.argumentsNode); |
| 1215 mapping.setSelector(node, Selector.BINARY_OPERATOR); | |
| 1216 } | 1268 } |
| 1217 } else if (node.isIndex) { | 1269 } else if (node.isIndex) { |
| 1218 visit(node.argumentsNode); | 1270 visit(node.argumentsNode); |
| 1219 assert(node.arguments.tail.isEmpty()); | 1271 assert(node.arguments.tail.isEmpty()); |
| 1220 mapping.setSelector(node, Selector.INDEX); | |
| 1221 } else if (node.isPropertyAccess) { | 1272 } else if (node.isPropertyAccess) { |
| 1222 mapping.setSelector(node, Selector.GETTER); | 1273 // Nothing to do here. |
| 1223 } else { | 1274 } else { |
| 1224 handleArguments(node); | 1275 visitArguments(node.argumentsNode); |
| 1225 } | 1276 } |
| 1277 |
| 1226 if (target != null && target.kind == ElementKind.ABSTRACT_FIELD) { | 1278 if (target != null && target.kind == ElementKind.ABSTRACT_FIELD) { |
| 1227 AbstractFieldElement field = target; | 1279 AbstractFieldElement field = target; |
| 1228 target = field.getter; | 1280 target = field.getter; |
| 1229 } | 1281 } |
| 1230 if (node.isCall && | 1282 if (node.isCall && |
| 1231 (target === null || | 1283 (target === null || |
| 1232 target.isGetter() || | 1284 target.isGetter() || |
| 1233 Elements.isClosureSend(node, target))) { | 1285 Elements.isClosureSend(node, target))) { |
| 1286 Selector selector = mapping.getSelector(node); |
| 1287 Selector call = new Selector.call( |
| 1288 compiler.namer.CLOSURE_INVOCATION_NAME, |
| 1289 selector.library, |
| 1290 selector.argumentCount, |
| 1291 selector.namedArguments); |
| 1234 world.registerDynamicInvocation(compiler.namer.CLOSURE_INVOCATION_NAME, | 1292 world.registerDynamicInvocation(compiler.namer.CLOSURE_INVOCATION_NAME, |
| 1235 mapping.getSelector(node)); | 1293 call); |
| 1236 } | 1294 } |
| 1237 // TODO(ngeoffray): We should do the check in | 1295 // TODO(ngeoffray): We should do the check in |
| 1238 // visitExpressionStatement instead. | 1296 // visitExpressionStatement instead. |
| 1239 if (target === compiler.assertMethod && !node.isCall) { | 1297 if (target === compiler.assertMethod && !node.isCall) { |
| 1240 // We can only use assert by calling it. | 1298 // We can only use assert by calling it. |
| 1241 if (!inInstanceContext) { | 1299 if (!inInstanceContext) { |
| 1242 error(node, MessageKind.MISSING_ARGUMENTS_TO_ASSERT, [node]); | 1300 error(node, MessageKind.MISSING_ARGUMENTS_TO_ASSERT, [node]); |
| 1243 } | 1301 } |
| 1244 target = null; | 1302 target = null; |
| 1245 } | 1303 } |
| (...skipping 10 matching lines...) Expand all Loading... |
| 1256 Element getter = null; | 1314 Element getter = null; |
| 1257 if (target != null && target.kind == ElementKind.ABSTRACT_FIELD) { | 1315 if (target != null && target.kind == ElementKind.ABSTRACT_FIELD) { |
| 1258 AbstractFieldElement field = target; | 1316 AbstractFieldElement field = target; |
| 1259 setter = field.setter; | 1317 setter = field.setter; |
| 1260 getter = field.getter; | 1318 getter = field.getter; |
| 1261 } else { | 1319 } else { |
| 1262 setter = target; | 1320 setter = target; |
| 1263 getter = target; | 1321 getter = target; |
| 1264 } | 1322 } |
| 1265 // TODO(ngeoffray): Check if the target can be assigned. | 1323 // TODO(ngeoffray): Check if the target can be assigned. |
| 1266 Identifier op = node.assignmentOperator; | 1324 Identifier identifier = node.assignmentOperator; |
| 1267 bool needsGetter = op.source.stringValue !== '='; | 1325 bool compoundAssignment = identifier.source.stringValue !== '='; |
| 1268 Selector selector; | 1326 if (compoundAssignment) { |
| 1269 if (needsGetter) { | |
| 1270 if (node.isIndex) { | |
| 1271 selector = Selector.INDEX_AND_INDEX_SET; | |
| 1272 } else { | |
| 1273 selector = Selector.GETTER_AND_SETTER; | |
| 1274 } | |
| 1275 useElement(node.selector, getter); | 1327 useElement(node.selector, getter); |
| 1276 } else if (node.isIndex) { | |
| 1277 selector = Selector.INDEX_SET; | |
| 1278 } else { | |
| 1279 selector = Selector.SETTER; | |
| 1280 } | 1328 } |
| 1281 visit(node.argumentsNode); | 1329 visit(node.argumentsNode); |
| 1282 mapping.setSelector(node, selector); | |
| 1283 // TODO(ngeoffray): Warn if target is null and the send is | 1330 // TODO(ngeoffray): Warn if target is null and the send is |
| 1284 // unqualified. | 1331 // unqualified. |
| 1285 registerDynamicSend(node); | 1332 registerDynamicSend(node); |
| 1286 return useElement(node, setter); | 1333 return useElement(node, setter); |
| 1287 } | 1334 } |
| 1288 | 1335 |
| 1289 registerDynamicSend(Send node) { | 1336 registerDynamicSend(Send node) { |
| 1290 Identifier id = node.selector.asIdentifier(); | 1337 Identifier id = node.selector.asIdentifier(); |
| 1291 if (id === null) return; | 1338 if (id === null) return; |
| 1292 SourceString name = node.selector.asIdentifier().source; | 1339 SourceString name = node.selector.asIdentifier().source; |
| 1293 if (node.isIndex && !node.arguments.tail.isEmpty()) { | 1340 if (node.isIndex && node is SendSet) { |
| 1294 name = Elements.constructOperatorName( | 1341 name = Elements.constructOperatorName( |
| 1295 const SourceString('operator'), | 1342 const SourceString('operator'), |
| 1296 const SourceString('[]=')); | 1343 const SourceString('[]=')); |
| 1297 } else if (node.selector.asOperator() != null) { | 1344 } else if (node.selector.asOperator() != null) { |
| 1298 switch (name.stringValue) { | 1345 switch (name.stringValue) { |
| 1299 case '===': | 1346 case '===': |
| 1300 case '!==': | 1347 case '!==': |
| 1301 case '!': | 1348 case '!': |
| 1302 case '&&': | 1349 case '&&': |
| 1303 case '||': | 1350 case '||': |
| 1304 case 'is': | 1351 case 'is': |
| 1305 case 'as': | 1352 case 'as': |
| 1306 case '>>>': | 1353 case '>>>': |
| 1307 return null; | 1354 return null; |
| 1308 } | 1355 } |
| 1309 name = Elements.constructOperatorName( | 1356 name = Elements.constructOperatorName( |
| 1310 const SourceString('operator'), | 1357 const SourceString('operator'), |
| 1311 name, | 1358 name, |
| 1312 node.argumentsNode is Prefix); | 1359 node.argumentsNode is Prefix); |
| 1313 } | 1360 } |
| 1314 Selector selector = mapping.getSelector(node); | 1361 Selector selector = mapping.getSelector(node); |
| 1315 if (Selector.GETTER === selector) { | 1362 if (selector.isGetter()) { |
| 1316 world.registerDynamicGetter(name, selector); | 1363 world.registerDynamicGetter(name, selector); |
| 1317 } else if (Selector.SETTER === selector) { | 1364 } else if (selector.isSetter()) { |
| 1318 world.registerDynamicSetter(name, selector); | 1365 world.registerDynamicSetter(name, selector); |
| 1319 // Also register the getter for compound assignments. | 1366 // Also register the getter for compound assignments. |
| 1320 world.registerDynamicGetter(name, Selector.GETTER); | 1367 LibraryElement library = enclosingElement.getLibrary(); |
| 1368 Selector getter = new Selector.getter(name, library); |
| 1369 world.registerDynamicGetter(name, getter); |
| 1321 } else { | 1370 } else { |
| 1371 // TODO(kasperl): In case of an index-set selector, we |
| 1372 // should probably also register the corresponding |
| 1373 // index selector. |
| 1322 world.registerDynamicInvocation(name, selector); | 1374 world.registerDynamicInvocation(name, selector); |
| 1323 } | 1375 } |
| 1324 var interceptor = new Interceptors(compiler).getStaticInterceptor( | 1376 var interceptor = new Interceptors(compiler).getStaticInterceptor( |
| 1325 name, | 1377 name, |
| 1326 node.argumentCount()); | 1378 node.argumentCount()); |
| 1327 if (interceptor !== null) { | 1379 if (interceptor !== null) { |
| 1328 world.registerStaticUse(interceptor); | 1380 world.registerStaticUse(interceptor); |
| 1329 } | 1381 } |
| 1330 } | 1382 } |
| 1331 | 1383 |
| (...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1380 } | 1432 } |
| 1381 | 1433 |
| 1382 visitParenthesizedExpression(ParenthesizedExpression node) { | 1434 visitParenthesizedExpression(ParenthesizedExpression node) { |
| 1383 visit(node.expression); | 1435 visit(node.expression); |
| 1384 } | 1436 } |
| 1385 | 1437 |
| 1386 visitNewExpression(NewExpression node) { | 1438 visitNewExpression(NewExpression node) { |
| 1387 Node selector = node.send.selector; | 1439 Node selector = node.send.selector; |
| 1388 | 1440 |
| 1389 FunctionElement constructor = resolveConstructor(node); | 1441 FunctionElement constructor = resolveConstructor(node); |
| 1390 handleArguments(node.send); | 1442 resolveSelector(node.send); |
| 1443 visitArguments(node.send.argumentsNode); |
| 1391 if (constructor === null) return null; | 1444 if (constructor === null) return null; |
| 1392 // TODO(karlklose): handle optional arguments. | 1445 // TODO(karlklose): handle optional arguments. |
| 1393 if (node.send.argumentCount() != constructor.parameterCount(compiler)) { | 1446 if (node.send.argumentCount() != constructor.parameterCount(compiler)) { |
| 1394 // TODO(ngeoffray): resolution error with wrong number of | 1447 // TODO(ngeoffray): resolution error with wrong number of |
| 1395 // parameters. We cannot do this rigth now because of the | 1448 // parameters. We cannot do this rigth now because of the |
| 1396 // List constructor. | 1449 // List constructor. |
| 1397 } | 1450 } |
| 1398 useElement(node.send, constructor); | 1451 useElement(node.send, constructor); |
| 1399 compiler.withCurrentElement(constructor, () { | 1452 compiler.withCurrentElement(constructor, () { |
| 1400 FunctionExpression tree = constructor.parseNode(compiler); | 1453 FunctionExpression tree = constructor.parseNode(compiler); |
| (...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1469 | 1522 |
| 1470 visitConditional(Conditional node) { | 1523 visitConditional(Conditional node) { |
| 1471 node.visitChildren(this); | 1524 node.visitChildren(this); |
| 1472 } | 1525 } |
| 1473 | 1526 |
| 1474 visitStringInterpolation(StringInterpolation node) { | 1527 visitStringInterpolation(StringInterpolation node) { |
| 1475 node.visitChildren(this); | 1528 node.visitChildren(this); |
| 1476 } | 1529 } |
| 1477 | 1530 |
| 1478 visitStringInterpolationPart(StringInterpolationPart node) { | 1531 visitStringInterpolationPart(StringInterpolationPart node) { |
| 1479 world.registerDynamicInvocation( | 1532 SourceString name = const SourceString('toString'); |
| 1480 const SourceString('toString'), Selector.INVOCATION_0); | 1533 LibraryElement library = enclosingElement.getLibrary(); |
| 1534 Selector selector = new Selector.call(name, library, 0); |
| 1535 world.registerDynamicInvocation(name, selector); |
| 1481 node.visitChildren(this); | 1536 node.visitChildren(this); |
| 1482 } | 1537 } |
| 1483 | 1538 |
| 1484 visitBreakStatement(BreakStatement node) { | 1539 visitBreakStatement(BreakStatement node) { |
| 1485 TargetElement target; | 1540 TargetElement target; |
| 1486 if (node.target === null) { | 1541 if (node.target === null) { |
| 1487 target = statementScope.currentBreakTarget(); | 1542 target = statementScope.currentBreakTarget(); |
| 1488 if (target === null) { | 1543 if (target === null) { |
| 1489 error(node, MessageKind.NO_BREAK_TARGET); | 1544 error(node, MessageKind.NO_BREAK_TARGET); |
| 1490 return; | 1545 return; |
| (...skipping 910 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2401 TopScope(LibraryElement library) : super(null, library); | 2456 TopScope(LibraryElement library) : super(null, library); |
| 2402 Element lookup(SourceString name) { | 2457 Element lookup(SourceString name) { |
| 2403 return library.find(name); | 2458 return library.find(name); |
| 2404 } | 2459 } |
| 2405 | 2460 |
| 2406 Element add(Element newElement) { | 2461 Element add(Element newElement) { |
| 2407 throw "Cannot add an element in the top scope"; | 2462 throw "Cannot add an element in the top scope"; |
| 2408 } | 2463 } |
| 2409 String toString() => '$element'; | 2464 String toString() => '$element'; |
| 2410 } | 2465 } |
| OLD | NEW |