Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(95)

Side by Side Diff: runtime/vm/flow_graph_builder.cc

Issue 1589643002: Source positions for constructors and lots of async machinery (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 4 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « runtime/vm/flow_graph_builder.h ('k') | runtime/vm/flow_graph_builder_test.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 #include "vm/flow_graph_builder.h" 5 #include "vm/flow_graph_builder.h"
6 6
7 #include "lib/invocation_mirror.h" 7 #include "lib/invocation_mirror.h"
8 #include "vm/ast_printer.h" 8 #include "vm/ast_printer.h"
9 #include "vm/bit_vector.h" 9 #include "vm/bit_vector.h"
10 #include "vm/compiler.h" 10 #include "vm/compiler.h"
(...skipping 30 matching lines...) Expand all
41 "Trace type check elimination at compile time."); 41 "Trace type check elimination at compile time.");
42 42
43 DECLARE_FLAG(int, optimization_counter_threshold); 43 DECLARE_FLAG(int, optimization_counter_threshold);
44 DECLARE_FLAG(bool, profile_vm); 44 DECLARE_FLAG(bool, profile_vm);
45 DECLARE_FLAG(bool, warn_on_javascript_compatibility); 45 DECLARE_FLAG(bool, warn_on_javascript_compatibility);
46 DECLARE_FLAG(bool, use_field_guards); 46 DECLARE_FLAG(bool, use_field_guards);
47 47
48 // Quick access to the locally defined zone() method. 48 // Quick access to the locally defined zone() method.
49 #define Z (zone()) 49 #define Z (zone())
50 50
51 // Quick synthetic token position.
52 #define ST(token_pos) Token::ToSynthetic(token_pos)
53
51 // TODO(srdjan): Allow compiler to add constants as they are encountered in 54 // TODO(srdjan): Allow compiler to add constants as they are encountered in
52 // the compilation. 55 // the compilation.
53 const double kCommonDoubleConstants[] = 56 const double kCommonDoubleConstants[] =
54 {-1.0, -0.5, -0.1, 0.0, 0.1, 0.5, 1.0, 2.0, 4.0, 5.0, 57 {-1.0, -0.5, -0.1, 0.0, 0.1, 0.5, 1.0, 2.0, 4.0, 5.0,
55 10.0, 20.0, 30.0, 64.0, 255.0, NAN, 58 10.0, 20.0, 30.0, 64.0, 255.0, NAN,
56 // From dart:math 59 // From dart:math
57 2.718281828459045, 2.302585092994046, 0.6931471805599453, 60 2.718281828459045, 2.302585092994046, 0.6931471805599453,
58 1.4426950408889634, 0.4342944819032518, 3.1415926535897932, 61 1.4426950408889634, 0.4342944819032518, 3.1415926535897932,
59 0.7071067811865476, 1.4142135623730951}; 62 0.7071067811865476, 1.4142135623730951};
60 63
(...skipping 761 matching lines...) Expand 10 before | Expand all | Expand 10 after
822 825
823 PushArgumentInstr* EffectGraphVisitor::PushArgument(Value* value) { 826 PushArgumentInstr* EffectGraphVisitor::PushArgument(Value* value) {
824 owner_->add_args_pushed(1); 827 owner_->add_args_pushed(1);
825 PushArgumentInstr* result = new(Z) PushArgumentInstr(value); 828 PushArgumentInstr* result = new(Z) PushArgumentInstr(value);
826 AddInstruction(result); 829 AddInstruction(result);
827 return result; 830 return result;
828 } 831 }
829 832
830 833
831 Definition* EffectGraphVisitor::BuildStoreTemp(const LocalVariable& local, 834 Definition* EffectGraphVisitor::BuildStoreTemp(const LocalVariable& local,
832 Value* value) { 835 Value* value,
836 intptr_t token_pos) {
833 ASSERT(!local.is_captured()); 837 ASSERT(!local.is_captured());
834 return new(Z) StoreLocalInstr(local, value); 838 ASSERT(!Token::IsClassifying(token_pos));
839 return new(Z) StoreLocalInstr(local, value, ST(token_pos));
835 } 840 }
836 841
837 842
838 Definition* EffectGraphVisitor::BuildStoreExprTemp(Value* value) { 843 Definition* EffectGraphVisitor::BuildStoreExprTemp(Value* value,
844 intptr_t token_pos) {
839 return BuildStoreTemp(*owner()->parsed_function().expression_temp_var(), 845 return BuildStoreTemp(*owner()->parsed_function().expression_temp_var(),
840 value); 846 value,
847 token_pos);
841 } 848 }
842 849
843 850
844 Definition* EffectGraphVisitor::BuildLoadExprTemp() { 851 Definition* EffectGraphVisitor::BuildLoadExprTemp(intptr_t token_pos) {
845 return BuildLoadLocal(*owner()->parsed_function().expression_temp_var()); 852 ASSERT(!Token::IsClassifying(token_pos));
853 return BuildLoadLocal(*owner()->parsed_function().expression_temp_var(),
854 token_pos);
846 } 855 }
847 856
848 857
849 Definition* EffectGraphVisitor::BuildStoreLocal(const LocalVariable& local, 858 Definition* EffectGraphVisitor::BuildStoreLocal(const LocalVariable& local,
850 Value* value, 859 Value* value,
851 intptr_t token_pos) { 860 intptr_t token_pos) {
852 if (local.is_captured()) { 861 if (local.is_captured()) {
853 LocalVariable* tmp_var = EnterTempLocalScope(value); 862 LocalVariable* tmp_var = EnterTempLocalScope(value, token_pos);
854 intptr_t delta = 863 intptr_t delta =
855 owner()->context_level() - local.owner()->context_level(); 864 owner()->context_level() - local.owner()->context_level();
856 ASSERT(delta >= 0); 865 ASSERT(delta >= 0);
857 Value* context = Bind(BuildCurrentContext(token_pos)); 866 Value* context = Bind(BuildCurrentContext(token_pos));
858 while (delta-- > 0) { 867 while (delta-- > 0) {
859 context = Bind(new(Z) LoadFieldInstr( 868 context = Bind(new(Z) LoadFieldInstr(
860 context, Context::parent_offset(), Type::ZoneHandle(Z, Type::null()), 869 context, Context::parent_offset(), Type::ZoneHandle(Z, Type::null()),
861 token_pos)); 870 token_pos));
862 } 871 }
863 Value* tmp_val = Bind(new(Z) LoadLocalInstr(*tmp_var)); 872 Value* tmp_val = Bind(new(Z) LoadLocalInstr(*tmp_var, token_pos));
864 StoreInstanceFieldInstr* store = 873 StoreInstanceFieldInstr* store =
865 new(Z) StoreInstanceFieldInstr(Context::variable_offset(local.index()), 874 new(Z) StoreInstanceFieldInstr(Context::variable_offset(local.index()),
866 context, 875 context,
867 tmp_val, 876 tmp_val,
868 kEmitStoreBarrier, 877 kEmitStoreBarrier,
869 token_pos); 878 token_pos);
870 Do(store); 879 Do(store);
871 return ExitTempLocalScope(tmp_var); 880 return ExitTempLocalScope(tmp_var, token_pos);
872 } else { 881 } else {
873 return new(Z) StoreLocalInstr(local, value, token_pos); 882 return new(Z) StoreLocalInstr(local, value, token_pos);
874 } 883 }
875 } 884 }
876 885
877 886
878 Definition* EffectGraphVisitor::BuildLoadLocal(const LocalVariable& local, 887 Definition* EffectGraphVisitor::BuildLoadLocal(const LocalVariable& local,
879 intptr_t token_pos) { 888 intptr_t token_pos) {
880 if (local.IsConst()) { 889 if (local.IsConst()) {
881 return new(Z) ConstantInstr(*local.ConstValue(), token_pos); 890 return new(Z) ConstantInstr(*local.ConstValue(), token_pos);
(...skipping 14 matching lines...) Expand all
896 } else { 905 } else {
897 return new(Z) LoadLocalInstr(local, token_pos); 906 return new(Z) LoadLocalInstr(local, token_pos);
898 } 907 }
899 } 908 }
900 909
901 910
902 // Stores current context into the 'variable' 911 // Stores current context into the 'variable'
903 void EffectGraphVisitor::BuildSaveContext( 912 void EffectGraphVisitor::BuildSaveContext(
904 const LocalVariable& variable, 913 const LocalVariable& variable,
905 intptr_t token_pos) { 914 intptr_t token_pos) {
915 ASSERT(Token::IsSynthetic(token_pos) || Token::IsNoSource(token_pos));
906 Value* context = Bind(BuildCurrentContext(token_pos)); 916 Value* context = Bind(BuildCurrentContext(token_pos));
907 Do(BuildStoreLocal(variable, context, token_pos)); 917 Do(BuildStoreLocal(variable, context, token_pos));
908 } 918 }
909 919
910 920
911 // Loads context saved in 'context_variable' into the current context. 921 // Loads context saved in 'context_variable' into the current context.
912 void EffectGraphVisitor::BuildRestoreContext( 922 void EffectGraphVisitor::BuildRestoreContext(
913 const LocalVariable& variable, 923 const LocalVariable& variable,
914 intptr_t token_pos) { 924 intptr_t token_pos) {
915 Value* load_saved_context = Bind(BuildLoadLocal(variable, token_pos)); 925 Value* load_saved_context = Bind(BuildLoadLocal(variable, token_pos));
(...skipping 199 matching lines...) Expand 10 before | Expand all | Expand 10 after
1115 Append(for_value); 1125 Append(for_value);
1116 Value* return_value = for_value.value(); 1126 Value* return_value = for_value.value();
1117 1127
1118 // Call to stub that checks whether the debugger is in single 1128 // Call to stub that checks whether the debugger is in single
1119 // step mode. This call must happen before the contexts are 1129 // step mode. This call must happen before the contexts are
1120 // unchained so that captured variables can be inspected. 1130 // unchained so that captured variables can be inspected.
1121 // No debugger check is done in native functions or for return 1131 // No debugger check is done in native functions or for return
1122 // statements for which there is no associated source position. 1132 // statements for which there is no associated source position.
1123 const Function& function = owner()->function(); 1133 const Function& function = owner()->function();
1124 if (FLAG_support_debugger && 1134 if (FLAG_support_debugger &&
1125 (node->token_pos() >= 0) && !function.is_native()) { 1135 Token::IsDebugPause(node->token_pos()) && !function.is_native()) {
1126 AddInstruction(new(Z) DebugStepCheckInstr(node->token_pos(), 1136 AddInstruction(new(Z) DebugStepCheckInstr(node->token_pos(),
1127 RawPcDescriptors::kRuntimeCall)); 1137 RawPcDescriptors::kRuntimeCall));
1128 } 1138 }
1129 1139
1130 NestedContextAdjustment context_adjustment(owner(), owner()->context_level()); 1140 NestedContextAdjustment context_adjustment(owner(), owner()->context_level());
1131 1141
1132 if (node->inlined_finally_list_length() > 0) { 1142 if (node->inlined_finally_list_length() > 0) {
1133 LocalVariable* temp = owner()->parsed_function().finally_return_temp_var(); 1143 LocalVariable* temp = owner()->parsed_function().finally_return_temp_var();
1134 ASSERT(temp != NULL); 1144 ASSERT(temp != NULL);
1135 Do(BuildStoreLocal(*temp, return_value, node->token_pos())); 1145 Do(BuildStoreLocal(*temp, return_value, node->token_pos()));
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
1170 // been inlined (call: :async_completer.complete(return_value)). These 1180 // been inlined (call: :async_completer.complete(return_value)). These
1171 // returns end up returning null in the end. 1181 // returns end up returning null in the end.
1172 // 2) "Continuation" returns that should not complete the completer but return 1182 // 2) "Continuation" returns that should not complete the completer but return
1173 // the value. 1183 // the value.
1174 // 1184 //
1175 // We distinguish those kinds of nodes via is_regular_return(). 1185 // We distinguish those kinds of nodes via is_regular_return().
1176 // 1186 //
1177 if (function.IsAsyncClosure() && 1187 if (function.IsAsyncClosure() &&
1178 (node->return_type() == ReturnNode::kRegular)) { 1188 (node->return_type() == ReturnNode::kRegular)) {
1179 // Temporary store the computed return value. 1189 // Temporary store the computed return value.
1180 Do(BuildStoreExprTemp(return_value)); 1190 Do(BuildStoreExprTemp(return_value, node->token_pos()));
1181 1191
1182 LocalVariable* rcv_var = 1192 LocalVariable* rcv_var =
1183 node->scope()->LookupVariable(Symbols::AsyncCompleter(), false); 1193 node->scope()->LookupVariable(Symbols::AsyncCompleter(), false);
1184 ASSERT(rcv_var != NULL && rcv_var->is_captured()); 1194 ASSERT(rcv_var != NULL && rcv_var->is_captured());
1185 ZoneGrowableArray<PushArgumentInstr*>* arguments = 1195 ZoneGrowableArray<PushArgumentInstr*>* arguments =
1186 new(Z) ZoneGrowableArray<PushArgumentInstr*>(2); 1196 new(Z) ZoneGrowableArray<PushArgumentInstr*>(2);
1187 Value* rcv_value = Bind(BuildLoadLocal(*rcv_var, node->token_pos())); 1197 Value* rcv_value = Bind(BuildLoadLocal(*rcv_var, node->token_pos()));
1188 arguments->Add(PushArgument(rcv_value)); 1198 arguments->Add(PushArgument(rcv_value));
1189 Value* returned_value = Bind(BuildLoadExprTemp()); 1199 Value* returned_value = Bind(BuildLoadExprTemp(node->token_pos()));
1190 arguments->Add(PushArgument(returned_value)); 1200 arguments->Add(PushArgument(returned_value));
1191 InstanceCallInstr* call = new(Z) InstanceCallInstr( 1201 InstanceCallInstr* call = new(Z) InstanceCallInstr(
1192 node->token_pos(), 1202 node->token_pos(),
1193 Symbols::CompleterComplete(), 1203 Symbols::CompleterComplete(),
1194 Token::kILLEGAL, 1204 Token::kILLEGAL,
1195 arguments, 1205 arguments,
1196 Object::null_array(), 1206 Object::null_array(),
1197 1, 1207 1,
1198 owner()->ic_data_array()); 1208 owner()->ic_data_array());
1199 Do(call); 1209 Do(call);
1200 1210
1201 // Rebind the return value for the actual return call to be null. 1211 // Rebind the return value for the actual return call to be null.
1202 return_value = BuildNullValue(); 1212 return_value = BuildNullValue(node->token_pos());
1203 } 1213 }
1204 1214
1205 intptr_t current_context_level = owner()->context_level(); 1215 intptr_t current_context_level = owner()->context_level();
1206 ASSERT(current_context_level >= 0); 1216 ASSERT(current_context_level >= 0);
1207 if (HasContextScope()) { 1217 if (HasContextScope()) {
1208 UnchainContexts(current_context_level); 1218 UnchainContexts(current_context_level);
1209 } 1219 }
1210 1220
1211 AddReturnExit(node->token_pos(), return_value); 1221 AddReturnExit(node->token_pos(), return_value);
1212 1222
(...skipping 205 matching lines...) Expand 10 before | Expand all | Expand 10 after
1418 for_right.Bind(new(Z) AssertBooleanInstr(node->right()->token_pos(), 1428 for_right.Bind(new(Z) AssertBooleanInstr(node->right()->token_pos(),
1419 right_value)); 1429 right_value));
1420 } 1430 }
1421 Value* constant_true = for_right.Bind(new(Z) ConstantInstr(Bool::True())); 1431 Value* constant_true = for_right.Bind(new(Z) ConstantInstr(Bool::True()));
1422 Value* compare = 1432 Value* compare =
1423 for_right.Bind(new(Z) StrictCompareInstr(node->token_pos(), 1433 for_right.Bind(new(Z) StrictCompareInstr(node->token_pos(),
1424 Token::kEQ_STRICT, 1434 Token::kEQ_STRICT,
1425 right_value, 1435 right_value,
1426 constant_true, 1436 constant_true,
1427 false)); // No number check. 1437 false)); // No number check.
1428 for_right.Do(BuildStoreExprTemp(compare)); 1438 for_right.Do(BuildStoreExprTemp(compare, node->token_pos()));
1429 1439
1430 if (node->kind() == Token::kAND) { 1440 if (node->kind() == Token::kAND) {
1431 ValueGraphVisitor for_false(owner()); 1441 ValueGraphVisitor for_false(owner());
1432 Value* constant_false = 1442 Value* constant_false =
1433 for_false.Bind(new(Z) ConstantInstr(Bool::False())); 1443 for_false.Bind(new(Z) ConstantInstr(Bool::False()));
1434 for_false.Do(BuildStoreExprTemp(constant_false)); 1444 for_false.Do(BuildStoreExprTemp(constant_false, node->token_pos()));
1435 Join(for_test, for_right, for_false); 1445 Join(for_test, for_right, for_false);
1436 } else { 1446 } else {
1437 ASSERT(node->kind() == Token::kOR); 1447 ASSERT(node->kind() == Token::kOR);
1438 ValueGraphVisitor for_true(owner()); 1448 ValueGraphVisitor for_true(owner());
1439 Value* constant_true = for_true.Bind(new(Z) ConstantInstr(Bool::True())); 1449 Value* constant_true = for_true.Bind(new(Z) ConstantInstr(Bool::True()));
1440 for_true.Do(BuildStoreExprTemp(constant_true)); 1450 for_true.Do(BuildStoreExprTemp(constant_true, node->token_pos()));
1441 Join(for_test, for_true, for_right); 1451 Join(for_test, for_true, for_right);
1442 } 1452 }
1443 ReturnDefinition(BuildLoadExprTemp()); 1453 ReturnDefinition(BuildLoadExprTemp(node->token_pos()));
1444 return; 1454 return;
1445 } 1455 }
1446 1456
1447 EffectGraphVisitor::VisitBinaryOpNode(node); 1457 EffectGraphVisitor::VisitBinaryOpNode(node);
1448 } 1458 }
1449 1459
1450 1460
1451 static const String& BinaryOpAndMaskName(BinaryOpNode* node) { 1461 static const String& BinaryOpAndMaskName(BinaryOpNode* node) {
1452 if (node->kind() == Token::kSHL) { 1462 if (node->kind() == Token::kSHL) {
1453 return Library::PrivateCoreLibName(Symbols::_leftShiftWithMask32()); 1463 return Library::PrivateCoreLibName(Symbols::_leftShiftWithMask32());
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
1497 1507
1498 1508
1499 void EffectGraphVisitor::BuildTypecheckPushArguments( 1509 void EffectGraphVisitor::BuildTypecheckPushArguments(
1500 intptr_t token_pos, 1510 intptr_t token_pos,
1501 PushArgumentInstr** push_instantiator_type_arguments_result) { 1511 PushArgumentInstr** push_instantiator_type_arguments_result) {
1502 const Class& instantiator_class = Class::Handle( 1512 const Class& instantiator_class = Class::Handle(
1503 Z, owner()->function().Owner()); 1513 Z, owner()->function().Owner());
1504 // Since called only when type tested against is not instantiated. 1514 // Since called only when type tested against is not instantiated.
1505 ASSERT(instantiator_class.NumTypeParameters() > 0); 1515 ASSERT(instantiator_class.NumTypeParameters() > 0);
1506 Value* instantiator_type_arguments = NULL; 1516 Value* instantiator_type_arguments = NULL;
1507 Value* instantiator = BuildInstantiator(instantiator_class); 1517 Value* instantiator = BuildInstantiator(token_pos, instantiator_class);
1508 if (instantiator == NULL) { 1518 if (instantiator == NULL) {
1509 // No instantiator when inside factory. 1519 // No instantiator when inside factory.
1510 instantiator_type_arguments = 1520 instantiator_type_arguments =
1511 BuildInstantiatorTypeArguments(token_pos, instantiator_class, NULL); 1521 BuildInstantiatorTypeArguments(token_pos, instantiator_class, NULL);
1512 } else { 1522 } else {
1513 instantiator_type_arguments = BuildInstantiatorTypeArguments( 1523 instantiator_type_arguments = BuildInstantiatorTypeArguments(
1514 token_pos, instantiator_class, instantiator); 1524 token_pos, instantiator_class, instantiator);
1515 } 1525 }
1516 *push_instantiator_type_arguments_result = 1526 *push_instantiator_type_arguments_result =
1517 PushArgument(instantiator_type_arguments); 1527 PushArgument(instantiator_type_arguments);
1518 } 1528 }
1519 1529
1520 1530
1521 1531
1522 void EffectGraphVisitor::BuildTypecheckArguments( 1532 void EffectGraphVisitor::BuildTypecheckArguments(
1523 intptr_t token_pos, 1533 intptr_t token_pos,
1524 Value** instantiator_type_arguments_result) { 1534 Value** instantiator_type_arguments_result) {
1525 Value* instantiator = NULL; 1535 Value* instantiator = NULL;
1526 Value* instantiator_type_arguments = NULL; 1536 Value* instantiator_type_arguments = NULL;
1527 const Class& instantiator_class = Class::Handle( 1537 const Class& instantiator_class = Class::Handle(
1528 Z, owner()->function().Owner()); 1538 Z, owner()->function().Owner());
1529 // Since called only when type tested against is not instantiated. 1539 // Since called only when type tested against is not instantiated.
1530 ASSERT(instantiator_class.NumTypeParameters() > 0); 1540 ASSERT(instantiator_class.NumTypeParameters() > 0);
1531 instantiator = BuildInstantiator(instantiator_class); 1541 instantiator = BuildInstantiator(token_pos, instantiator_class);
1532 if (instantiator == NULL) { 1542 if (instantiator == NULL) {
1533 // No instantiator when inside factory. 1543 // No instantiator when inside factory.
1534 instantiator_type_arguments = 1544 instantiator_type_arguments =
1535 BuildInstantiatorTypeArguments(token_pos, instantiator_class, NULL); 1545 BuildInstantiatorTypeArguments(token_pos, instantiator_class, NULL);
1536 } else { 1546 } else {
1537 instantiator_type_arguments = BuildInstantiatorTypeArguments( 1547 instantiator_type_arguments = BuildInstantiatorTypeArguments(
1538 token_pos, instantiator_class, instantiator); 1548 token_pos, instantiator_class, instantiator);
1539 } 1549 }
1540 *instantiator_type_arguments_result = instantiator_type_arguments; 1550 *instantiator_type_arguments_result = instantiator_type_arguments;
1541 } 1551 }
1542 1552
1543 1553
1544 Value* EffectGraphVisitor::BuildNullValue() { 1554 Value* EffectGraphVisitor::BuildNullValue(intptr_t token_pos) {
1545 return Bind(new(Z) ConstantInstr(Object::ZoneHandle(Z, Object::null()))); 1555 return Bind(new(Z) ConstantInstr(Object::ZoneHandle(Z, Object::null()),
1556 token_pos));
1546 } 1557 }
1547 1558
1548 1559
1549 // Used for testing incoming arguments. 1560 // Used for testing incoming arguments.
1550 AssertAssignableInstr* EffectGraphVisitor::BuildAssertAssignable( 1561 AssertAssignableInstr* EffectGraphVisitor::BuildAssertAssignable(
1551 intptr_t token_pos, 1562 intptr_t token_pos,
1552 Value* value, 1563 Value* value,
1553 const AbstractType& dst_type, 1564 const AbstractType& dst_type,
1554 const String& dst_name) { 1565 const String& dst_name) {
1555 // Build the type check computation. 1566 // Build the type check computation.
1556 Value* instantiator_type_arguments = NULL; 1567 Value* instantiator_type_arguments = NULL;
1557 if (dst_type.IsInstantiated()) { 1568 if (dst_type.IsInstantiated()) {
1558 instantiator_type_arguments = BuildNullValue(); 1569 instantiator_type_arguments = BuildNullValue(token_pos);
1559 } else { 1570 } else {
1560 BuildTypecheckArguments(token_pos, &instantiator_type_arguments); 1571 BuildTypecheckArguments(token_pos, &instantiator_type_arguments);
1561 } 1572 }
1562 1573
1563 const intptr_t deopt_id = Thread::Current()->GetNextDeoptId(); 1574 const intptr_t deopt_id = Thread::Current()->GetNextDeoptId();
1564 return new(Z) AssertAssignableInstr(token_pos, 1575 return new(Z) AssertAssignableInstr(token_pos,
1565 value, 1576 value,
1566 instantiator_type_arguments, 1577 instantiator_type_arguments,
1567 dst_type, 1578 dst_type,
1568 dst_name, 1579 dst_name,
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after
1659 kNumArgsChecked, 1670 kNumArgsChecked,
1660 owner()->ic_data_array()); 1671 owner()->ic_data_array());
1661 ReturnDefinition(call); 1672 ReturnDefinition(call);
1662 return; 1673 return;
1663 } 1674 }
1664 } 1675 }
1665 1676
1666 PushArgumentInstr* push_left = PushArgument(for_left_value.value()); 1677 PushArgumentInstr* push_left = PushArgument(for_left_value.value());
1667 PushArgumentInstr* push_type_args = NULL; 1678 PushArgumentInstr* push_type_args = NULL;
1668 if (type.IsInstantiated()) { 1679 if (type.IsInstantiated()) {
1669 push_type_args = PushArgument(BuildNullValue()); 1680 push_type_args = PushArgument(BuildNullValue(node->token_pos()));
1670 } else { 1681 } else {
1671 BuildTypecheckPushArguments(node->token_pos(), &push_type_args); 1682 BuildTypecheckPushArguments(node->token_pos(), &push_type_args);
1672 } 1683 }
1673 ZoneGrowableArray<PushArgumentInstr*>* arguments = 1684 ZoneGrowableArray<PushArgumentInstr*>* arguments =
1674 new(Z) ZoneGrowableArray<PushArgumentInstr*>(4); 1685 new(Z) ZoneGrowableArray<PushArgumentInstr*>(4);
1675 arguments->Add(push_left); 1686 arguments->Add(push_left);
1676 arguments->Add(push_type_args); 1687 arguments->Add(push_type_args);
1677 ASSERT(!node->right()->AsTypeNode()->type().IsNull()); 1688 ASSERT(!node->right()->AsTypeNode()->type().IsNull());
1678 Value* type_const = Bind(new(Z) ConstantInstr(type)); 1689 Value* type_const = Bind(new(Z) ConstantInstr(type));
1679 arguments->Add(PushArgument(type_const)); 1690 arguments->Add(PushArgument(type_const));
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
1711 // Do not skip type check if javascript compatibility warning is required. 1722 // Do not skip type check if javascript compatibility warning is required.
1712 if (!FLAG_warn_on_javascript_compatibility || 1723 if (!FLAG_warn_on_javascript_compatibility ||
1713 !owner()->WarnOnJSIntegralNumTypeTest(node->left(), type)) { 1724 !owner()->WarnOnJSIntegralNumTypeTest(node->left(), type)) {
1714 ReturnValue(for_value.value()); 1725 ReturnValue(for_value.value());
1715 return; 1726 return;
1716 } 1727 }
1717 } 1728 }
1718 PushArgumentInstr* push_left = PushArgument(for_value.value()); 1729 PushArgumentInstr* push_left = PushArgument(for_value.value());
1719 PushArgumentInstr* push_type_args = NULL; 1730 PushArgumentInstr* push_type_args = NULL;
1720 if (type.IsInstantiated()) { 1731 if (type.IsInstantiated()) {
1721 push_type_args = PushArgument(BuildNullValue()); 1732 push_type_args = PushArgument(BuildNullValue(node->token_pos()));
1722 } else { 1733 } else {
1723 BuildTypecheckPushArguments(node->token_pos(), &push_type_args); 1734 BuildTypecheckPushArguments(node->token_pos(), &push_type_args);
1724 } 1735 }
1725 ZoneGrowableArray<PushArgumentInstr*>* arguments = 1736 ZoneGrowableArray<PushArgumentInstr*>* arguments =
1726 new(Z) ZoneGrowableArray<PushArgumentInstr*>(3); 1737 new(Z) ZoneGrowableArray<PushArgumentInstr*>(3);
1727 arguments->Add(push_left); 1738 arguments->Add(push_left);
1728 arguments->Add(push_type_args); 1739 arguments->Add(push_type_args);
1729 Value* type_arg = Bind(new(Z) ConstantInstr(type)); 1740 Value* type_arg = Bind(new(Z) ConstantInstr(type));
1730 arguments->Add(PushArgument(type_arg)); 1741 arguments->Add(PushArgument(type_arg));
1731 const intptr_t kNumArgsChecked = 1; 1742 const intptr_t kNumArgsChecked = 1;
(...skipping 178 matching lines...) Expand 10 before | Expand all | Expand 10 after
1910 } 1921 }
1911 1922
1912 1923
1913 void ValueGraphVisitor::VisitConditionalExprNode(ConditionalExprNode* node) { 1924 void ValueGraphVisitor::VisitConditionalExprNode(ConditionalExprNode* node) {
1914 TestGraphVisitor for_test(owner(), node->condition()->token_pos()); 1925 TestGraphVisitor for_test(owner(), node->condition()->token_pos());
1915 node->condition()->Visit(&for_test); 1926 node->condition()->Visit(&for_test);
1916 1927
1917 ValueGraphVisitor for_true(owner()); 1928 ValueGraphVisitor for_true(owner());
1918 node->true_expr()->Visit(&for_true); 1929 node->true_expr()->Visit(&for_true);
1919 ASSERT(for_true.is_open()); 1930 ASSERT(for_true.is_open());
1920 for_true.Do(BuildStoreExprTemp(for_true.value())); 1931 for_true.Do(BuildStoreExprTemp(for_true.value(),
1932 node->true_expr()->token_pos()));
1921 1933
1922 ValueGraphVisitor for_false(owner()); 1934 ValueGraphVisitor for_false(owner());
1923 node->false_expr()->Visit(&for_false); 1935 node->false_expr()->Visit(&for_false);
1924 ASSERT(for_false.is_open()); 1936 ASSERT(for_false.is_open());
1925 for_false.Do(BuildStoreExprTemp(for_false.value())); 1937 for_false.Do(BuildStoreExprTemp(for_false.value(),
1938 node->false_expr()->token_pos()));
1926 1939
1927 Join(for_test, for_true, for_false); 1940 Join(for_test, for_true, for_false);
1928 ReturnDefinition(BuildLoadExprTemp()); 1941 ReturnDefinition(BuildLoadExprTemp(node->token_pos()));
1929 } 1942 }
1930 1943
1931 1944
1932 // <Statement> ::= If { condition: <Expression> 1945 // <Statement> ::= If { condition: <Expression>
1933 // true_branch: <Sequence> 1946 // true_branch: <Sequence>
1934 // false_branch: <Sequence> } 1947 // false_branch: <Sequence> }
1935 void EffectGraphVisitor::VisitIfNode(IfNode* node) { 1948 void EffectGraphVisitor::VisitIfNode(IfNode* node) {
1936 TestGraphVisitor for_test(owner(), node->condition()->token_pos()); 1949 TestGraphVisitor for_test(owner(), node->condition()->token_pos());
1937 node->condition()->Visit(&for_test); 1950 node->condition()->Visit(&for_test);
1938 1951
(...skipping 327 matching lines...) Expand 10 before | Expand all | Expand 10 after
2266 void EffectGraphVisitor::VisitAwaitNode(AwaitNode* node) { 2279 void EffectGraphVisitor::VisitAwaitNode(AwaitNode* node) {
2267 // Await nodes are temporary during parsing. 2280 // Await nodes are temporary during parsing.
2268 UNREACHABLE(); 2281 UNREACHABLE();
2269 } 2282 }
2270 2283
2271 2284
2272 void EffectGraphVisitor::VisitAwaitMarkerNode(AwaitMarkerNode* node) { 2285 void EffectGraphVisitor::VisitAwaitMarkerNode(AwaitMarkerNode* node) {
2273 // We need to create a new await state which involves: 2286 // We need to create a new await state which involves:
2274 // * Increase the jump counter. Sanity check against the list of targets. 2287 // * Increase the jump counter. Sanity check against the list of targets.
2275 // * Save the current context for resuming. 2288 // * Save the current context for resuming.
2289 ASSERT(Token::IsSynthetic(node->token_pos()) ||
2290 Token::IsNoSource(node->token_pos()));
2276 ASSERT(node->async_scope() != NULL); 2291 ASSERT(node->async_scope() != NULL);
2277 ASSERT(node->await_scope() != NULL); 2292 ASSERT(node->await_scope() != NULL);
2278 LocalVariable* jump_var = node->async_scope()->LookupVariable( 2293 LocalVariable* jump_var = node->async_scope()->LookupVariable(
2279 Symbols::AwaitJumpVar(), false); 2294 Symbols::AwaitJumpVar(), false);
2280 LocalVariable* ctx_var = node->async_scope()->LookupVariable( 2295 LocalVariable* ctx_var = node->async_scope()->LookupVariable(
2281 Symbols::AwaitContextVar(), false); 2296 Symbols::AwaitContextVar(), false);
2282 ASSERT((jump_var != NULL) && jump_var->is_captured()); 2297 ASSERT((jump_var != NULL) && jump_var->is_captured());
2283 ASSERT((ctx_var != NULL) && ctx_var->is_captured()); 2298 ASSERT((ctx_var != NULL) && ctx_var->is_captured());
2284 const intptr_t jump_count = owner()->next_await_counter(); 2299 const intptr_t jump_count = owner()->next_await_counter();
2285 ASSERT(jump_count >= 0); 2300 ASSERT(jump_count >= 0);
2286 // Sanity check that we always add a JoinEntryInstr before adding a new 2301 // Sanity check that we always add a JoinEntryInstr before adding a new
2287 // state. 2302 // state.
2288 ASSERT(jump_count == owner()->await_joins()->length()); 2303 ASSERT(jump_count == owner()->await_joins()->length());
2289 // Store the counter in :await_jump_var. 2304 // Store the counter in :await_jump_var.
2290 Value* jump_val = Bind(new(Z) ConstantInstr( 2305 Value* jump_val = Bind(new(Z) ConstantInstr(
2291 Smi::ZoneHandle(Z, Smi::New(jump_count)))); 2306 Smi::ZoneHandle(Z, Smi::New(jump_count)), node->token_pos()));
2292 Do(BuildStoreLocal(*jump_var, jump_val)); 2307 Do(BuildStoreLocal(*jump_var, jump_val, node->token_pos()));
2293 // Save the current context for resuming. 2308 // Save the current context for resuming.
2294 BuildSaveContext(*ctx_var, node->token_pos()); 2309 BuildSaveContext(*ctx_var, node->token_pos());
2295 } 2310 }
2296 2311
2297 2312
2298 intptr_t EffectGraphVisitor::GetCurrentTempLocalIndex() const { 2313 intptr_t EffectGraphVisitor::GetCurrentTempLocalIndex() const {
2299 return kFirstLocalSlotFromFp 2314 return kFirstLocalSlotFromFp
2300 - owner()->num_stack_locals() 2315 - owner()->num_stack_locals()
2301 - owner()->num_copied_params() 2316 - owner()->num_copied_params()
2302 - owner()->args_pushed() 2317 - owner()->args_pushed()
2303 - owner()->temp_count() + 1; 2318 - owner()->temp_count() + 1;
2304 } 2319 }
2305 2320
2306 2321
2307 LocalVariable* EffectGraphVisitor::EnterTempLocalScope(Value* value) { 2322 LocalVariable* EffectGraphVisitor::EnterTempLocalScope(
2323 Value* value, intptr_t token_pos) {
2308 Do(new(Z) PushTempInstr(value)); 2324 Do(new(Z) PushTempInstr(value));
2309 owner()->AllocateTemp(); 2325 owner()->AllocateTemp();
2310 2326
2311 ASSERT(value->definition()->temp_index() == (owner()->temp_count() - 1)); 2327 ASSERT(value->definition()->temp_index() == (owner()->temp_count() - 1));
2312 intptr_t index = GetCurrentTempLocalIndex(); 2328 intptr_t index = GetCurrentTempLocalIndex();
2313 char name[64]; 2329 char name[64];
2314 OS::SNPrint(name, 64, ":tmp_local%" Pd, index); 2330 OS::SNPrint(name, 64, ":tmp_local%" Pd, index);
2315 LocalVariable* var = 2331 LocalVariable* var =
2316 new(Z) LocalVariable(Scanner::kNoSourcePos, 2332 new(Z) LocalVariable(Token::kNoSourcePos,
2317 String::ZoneHandle(Z, Symbols::New(name)), 2333 String::ZoneHandle(Z, Symbols::New(name)),
2318 *value->Type()->ToAbstractType()); 2334 *value->Type()->ToAbstractType());
2319 var->set_index(index); 2335 var->set_index(index);
2320 return var; 2336 return var;
2321 } 2337 }
2322 2338
2323 2339
2324 Definition* EffectGraphVisitor::ExitTempLocalScope(LocalVariable* var) { 2340 Definition* EffectGraphVisitor::ExitTempLocalScope(
2325 Value* tmp = Bind(new(Z) LoadLocalInstr(*var)); 2341 LocalVariable* var, intptr_t token_pos) {
2342 Value* tmp = Bind(new(Z) LoadLocalInstr(*var, token_pos));
2326 owner()->DeallocateTemps(1); 2343 owner()->DeallocateTemps(1);
2327 ASSERT(GetCurrentTempLocalIndex() == var->index()); 2344 ASSERT(GetCurrentTempLocalIndex() == var->index());
2328 return new(Z) DropTempsInstr(1, tmp); 2345 return new(Z) DropTempsInstr(1, tmp);
2329 } 2346 }
2330 2347
2331 2348
2332 void EffectGraphVisitor::BuildLetTempExpressions(LetNode* node) { 2349 void EffectGraphVisitor::BuildLetTempExpressions(LetNode* node) {
2333 intptr_t num_temps = node->num_temps(); 2350 intptr_t num_temps = node->num_temps();
2334 for (intptr_t i = 0; i < num_temps; ++i) { 2351 for (intptr_t i = 0; i < num_temps; ++i) {
2335 ValueGraphVisitor for_value(owner()); 2352 ValueGraphVisitor for_value(owner());
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
2393 TypeArguments::ZoneHandle(Z, node->type().arguments()); 2410 TypeArguments::ZoneHandle(Z, node->type().arguments());
2394 Value* element_type = BuildInstantiatedTypeArguments(node->token_pos(), 2411 Value* element_type = BuildInstantiatedTypeArguments(node->token_pos(),
2395 type_args); 2412 type_args);
2396 Value* num_elements = 2413 Value* num_elements =
2397 Bind(new(Z) ConstantInstr(Smi::ZoneHandle(Z, Smi::New(node->length())))); 2414 Bind(new(Z) ConstantInstr(Smi::ZoneHandle(Z, Smi::New(node->length()))));
2398 CreateArrayInstr* create = new(Z) CreateArrayInstr(node->token_pos(), 2415 CreateArrayInstr* create = new(Z) CreateArrayInstr(node->token_pos(),
2399 element_type, 2416 element_type,
2400 num_elements); 2417 num_elements);
2401 Value* array_val = Bind(create); 2418 Value* array_val = Bind(create);
2402 2419
2403 { LocalVariable* tmp_var = EnterTempLocalScope(array_val); 2420 { LocalVariable* tmp_var = EnterTempLocalScope(array_val, node->token_pos());
2404 const intptr_t class_id = kArrayCid; 2421 const intptr_t class_id = kArrayCid;
2405 const intptr_t deopt_id = Thread::kNoDeoptId; 2422 const intptr_t deopt_id = Thread::kNoDeoptId;
2406 for (int i = 0; i < node->length(); ++i) { 2423 for (int i = 0; i < node->length(); ++i) {
2407 Value* array = Bind(new(Z) LoadLocalInstr(*tmp_var)); 2424 Value* array = Bind(new(Z) LoadLocalInstr(*tmp_var, node->token_pos()));
2408 Value* index = 2425 Value* index =
2409 Bind(new(Z) ConstantInstr(Smi::ZoneHandle(Z, Smi::New(i)))); 2426 Bind(new(Z) ConstantInstr(Smi::ZoneHandle(Z, Smi::New(i)),
2427 node->token_pos()));
2410 ValueGraphVisitor for_value(owner()); 2428 ValueGraphVisitor for_value(owner());
2411 node->ElementAt(i)->Visit(&for_value); 2429 node->ElementAt(i)->Visit(&for_value);
2412 Append(for_value); 2430 Append(for_value);
2413 // No store barrier needed for constants. 2431 // No store barrier needed for constants.
2414 const StoreBarrierType emit_store_barrier = 2432 const StoreBarrierType emit_store_barrier =
2415 for_value.value()->BindsToConstant() 2433 for_value.value()->BindsToConstant()
2416 ? kNoStoreBarrier 2434 ? kNoStoreBarrier
2417 : kEmitStoreBarrier; 2435 : kEmitStoreBarrier;
2418 const intptr_t index_scale = Instance::ElementSizeFor(class_id); 2436 const intptr_t index_scale = Instance::ElementSizeFor(class_id);
2419 StoreIndexedInstr* store = new(Z) StoreIndexedInstr( 2437 StoreIndexedInstr* store = new(Z) StoreIndexedInstr(
2420 array, index, for_value.value(), emit_store_barrier, 2438 array, index, for_value.value(), emit_store_barrier,
2421 index_scale, class_id, deopt_id, node->token_pos()); 2439 index_scale, class_id, deopt_id, node->token_pos());
2422 Do(store); 2440 Do(store);
2423 } 2441 }
2424 ReturnDefinition(ExitTempLocalScope(tmp_var)); 2442 ReturnDefinition(ExitTempLocalScope(tmp_var, node->token_pos()));
2425 } 2443 }
2426 } 2444 }
2427 2445
2428 2446
2429 void EffectGraphVisitor::VisitStringInterpolateNode( 2447 void EffectGraphVisitor::VisitStringInterpolateNode(
2430 StringInterpolateNode* node) { 2448 StringInterpolateNode* node) {
2431 ValueGraphVisitor for_argument(owner()); 2449 ValueGraphVisitor for_argument(owner());
2432 ArrayNode* arguments = node->value(); 2450 ArrayNode* arguments = node->value();
2433 if (arguments->length() == 1) { 2451 if (arguments->length() == 1) {
2434 ZoneGrowableArray<PushArgumentInstr*>* values = 2452 ZoneGrowableArray<PushArgumentInstr*>* values =
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after
2520 instantiator_class, 2538 instantiator_class,
2521 NULL); 2539 NULL);
2522 arguments->Add(PushArgument(type_arguments)); 2540 arguments->Add(PushArgument(type_arguments));
2523 } 2541 }
2524 AllocateObjectInstr* alloc = new(Z) AllocateObjectInstr(node->token_pos(), 2542 AllocateObjectInstr* alloc = new(Z) AllocateObjectInstr(node->token_pos(),
2525 cls, 2543 cls,
2526 arguments); 2544 arguments);
2527 alloc->set_closure_function(function); 2545 alloc->set_closure_function(function);
2528 2546
2529 Value* closure_val = Bind(alloc); 2547 Value* closure_val = Bind(alloc);
2530 { LocalVariable* closure_tmp_var = EnterTempLocalScope(closure_val); 2548 { LocalVariable* closure_tmp_var =
2549 EnterTempLocalScope(closure_val, node->token_pos());
2531 // Store function. 2550 // Store function.
2532 Value* closure_tmp_val = Bind(new(Z) LoadLocalInstr(*closure_tmp_var)); 2551 Value* closure_tmp_val =
2552 Bind(new(Z) LoadLocalInstr(*closure_tmp_var, node->token_pos()));
2533 Value* func_val = 2553 Value* func_val =
2534 Bind(new(Z) ConstantInstr(Function::ZoneHandle(Z, function.raw()))); 2554 Bind(new(Z) ConstantInstr(Function::ZoneHandle(Z, function.raw())));
2535 Do(new(Z) StoreInstanceFieldInstr(Closure::function_offset(), 2555 Do(new(Z) StoreInstanceFieldInstr(Closure::function_offset(),
2536 closure_tmp_val, 2556 closure_tmp_val,
2537 func_val, 2557 func_val,
2538 kEmitStoreBarrier, 2558 kEmitStoreBarrier,
2539 node->token_pos())); 2559 node->token_pos()));
2540 if (is_implicit) { 2560 if (is_implicit) {
2541 // Create new context containing the receiver. 2561 // Create new context containing the receiver.
2542 const intptr_t kNumContextVariables = 1; // The receiver. 2562 const intptr_t kNumContextVariables = 1; // The receiver.
2543 Value* allocated_context = 2563 Value* allocated_context =
2544 Bind(new(Z) AllocateContextInstr(node->token_pos(), 2564 Bind(new(Z) AllocateContextInstr(node->token_pos(),
2545 kNumContextVariables)); 2565 kNumContextVariables));
2546 { LocalVariable* context_tmp_var = EnterTempLocalScope(allocated_context); 2566 { LocalVariable* context_tmp_var =
2567 EnterTempLocalScope(allocated_context, node->token_pos());
2547 // Store receiver in context. 2568 // Store receiver in context.
2548 Value* context_tmp_val = Bind(new(Z) LoadLocalInstr(*context_tmp_var)); 2569 Value* context_tmp_val =
2570 Bind(new(Z) LoadLocalInstr(*context_tmp_var, node->token_pos()));
2549 ValueGraphVisitor for_receiver(owner()); 2571 ValueGraphVisitor for_receiver(owner());
2550 node->receiver()->Visit(&for_receiver); 2572 node->receiver()->Visit(&for_receiver);
2551 Append(for_receiver); 2573 Append(for_receiver);
2552 Value* receiver = for_receiver.value(); 2574 Value* receiver = for_receiver.value();
2553 Do(new(Z) StoreInstanceFieldInstr(Context::variable_offset(0), 2575 Do(new(Z) StoreInstanceFieldInstr(Context::variable_offset(0),
2554 context_tmp_val, 2576 context_tmp_val,
2555 receiver, 2577 receiver,
2556 kEmitStoreBarrier, 2578 kEmitStoreBarrier,
2557 node->token_pos())); 2579 node->token_pos()));
2558 // Store new context in closure. 2580 // Store new context in closure.
2559 closure_tmp_val = Bind(new(Z) LoadLocalInstr(*closure_tmp_var)); 2581 closure_tmp_val =
2560 context_tmp_val = Bind(new(Z) LoadLocalInstr(*context_tmp_var)); 2582 Bind(new(Z) LoadLocalInstr(*closure_tmp_var, node->token_pos()));
2583 context_tmp_val =
2584 Bind(new(Z) LoadLocalInstr(*context_tmp_var, node->token_pos()));
2561 Do(new(Z) StoreInstanceFieldInstr(Closure::context_offset(), 2585 Do(new(Z) StoreInstanceFieldInstr(Closure::context_offset(),
2562 closure_tmp_val, 2586 closure_tmp_val,
2563 context_tmp_val, 2587 context_tmp_val,
2564 kEmitStoreBarrier, 2588 kEmitStoreBarrier,
2565 node->token_pos())); 2589 node->token_pos()));
2566 Do(ExitTempLocalScope(context_tmp_var)); 2590 Do(ExitTempLocalScope(context_tmp_var, node->token_pos()));
2567 } 2591 }
2568 } else { 2592 } else {
2569 // Store current context in closure. 2593 // Store current context in closure.
2570 closure_tmp_val = Bind( 2594 closure_tmp_val = Bind(
2571 new(Z) LoadLocalInstr(*closure_tmp_var, node->token_pos())); 2595 new(Z) LoadLocalInstr(*closure_tmp_var, node->token_pos()));
2572 Value* context = Bind(BuildCurrentContext(node->token_pos())); 2596 Value* context = Bind(BuildCurrentContext(node->token_pos()));
2573 Do(new(Z) StoreInstanceFieldInstr(Closure::context_offset(), 2597 Do(new(Z) StoreInstanceFieldInstr(Closure::context_offset(),
2574 closure_tmp_val, 2598 closure_tmp_val,
2575 context, 2599 context,
2576 kEmitStoreBarrier, 2600 kEmitStoreBarrier,
2577 node->token_pos())); 2601 node->token_pos()));
2578 } 2602 }
2579 ReturnDefinition(ExitTempLocalScope(closure_tmp_var)); 2603 ReturnDefinition(ExitTempLocalScope(closure_tmp_var, node->token_pos()));
2580 } 2604 }
2581 } 2605 }
2582 2606
2583 2607
2584 void EffectGraphVisitor::BuildPushArguments( 2608 void EffectGraphVisitor::BuildPushArguments(
2585 const ArgumentListNode& node, 2609 const ArgumentListNode& node,
2586 ZoneGrowableArray<PushArgumentInstr*>* values) { 2610 ZoneGrowableArray<PushArgumentInstr*>* values) {
2587 for (intptr_t i = 0; i < node.length(); ++i) { 2611 for (intptr_t i = 0; i < node.length(); ++i) {
2588 ValueGraphVisitor for_argument(owner()); 2612 ValueGraphVisitor for_argument(owner());
2589 node.NodeAt(i)->Visit(&for_argument); 2613 node.NodeAt(i)->Visit(&for_argument);
2590 Append(for_argument); 2614 Append(for_argument);
2591 PushArgumentInstr* push_arg = PushArgument(for_argument.value()); 2615 PushArgumentInstr* push_arg = PushArgument(for_argument.value());
2592 values->Add(push_arg); 2616 values->Add(push_arg);
2593 } 2617 }
2594 } 2618 }
2595 2619
2596 2620
2597 void EffectGraphVisitor::BuildInstanceCallConditional(InstanceCallNode* node) { 2621 void EffectGraphVisitor::BuildInstanceCallConditional(InstanceCallNode* node) {
2622 const intptr_t token_pos = node->token_pos();
2598 LocalVariable* temp_var = owner()->parsed_function().expression_temp_var(); 2623 LocalVariable* temp_var = owner()->parsed_function().expression_temp_var();
2599 LoadLocalNode* load_temp = 2624 LoadLocalNode* load_temp = new(Z) LoadLocalNode(token_pos, temp_var);
2600 new(Z) LoadLocalNode(Scanner::kNoSourcePos, temp_var);
2601 2625
2602 LiteralNode* null_constant = 2626 LiteralNode* null_constant =
2603 new(Z) LiteralNode(Scanner::kNoSourcePos, Object::null_instance()); 2627 new(Z) LiteralNode(ST(token_pos), Object::null_instance());
2604 ComparisonNode* check_is_null = 2628 ComparisonNode* check_is_null =
2605 new(Z) ComparisonNode(Scanner::kNoSourcePos, 2629 new(Z) ComparisonNode(ST(token_pos),
2606 Token::kEQ, 2630 Token::kEQ,
2607 load_temp, 2631 load_temp,
2608 null_constant); 2632 null_constant);
2609 TestGraphVisitor for_test(owner(), Scanner::kNoSourcePos); 2633 TestGraphVisitor for_test(owner(), ST(token_pos));
2610 check_is_null->Visit(&for_test); 2634 check_is_null->Visit(&for_test);
2611 2635
2612 EffectGraphVisitor for_true(owner()); 2636 EffectGraphVisitor for_true(owner());
2613 EffectGraphVisitor for_false(owner()); 2637 EffectGraphVisitor for_false(owner());
2614 2638
2615 StoreLocalNode* store_null = 2639 StoreLocalNode* store_null =
2616 new(Z) StoreLocalNode(Scanner::kNoSourcePos, temp_var, null_constant); 2640 new(Z) StoreLocalNode(ST(token_pos), temp_var, null_constant);
2617 store_null->Visit(&for_true); 2641 store_null->Visit(&for_true);
2618 2642
2619 InstanceCallNode* call = 2643 InstanceCallNode* call =
2620 new(Z) InstanceCallNode(node->token_pos(), 2644 new(Z) InstanceCallNode(token_pos,
2621 load_temp, 2645 load_temp,
2622 node->function_name(), 2646 node->function_name(),
2623 node->arguments()); 2647 node->arguments());
2624 StoreLocalNode* store_result = 2648 StoreLocalNode* store_result =
2625 new(Z) StoreLocalNode(Scanner::kNoSourcePos, temp_var, call); 2649 new(Z) StoreLocalNode(ST(token_pos), temp_var, call);
2626 store_result->Visit(&for_false); 2650 store_result->Visit(&for_false);
2627 2651
2628 Join(for_test, for_true, for_false); 2652 Join(for_test, for_true, for_false);
2629 } 2653 }
2630 2654
2631 2655
2632 void ValueGraphVisitor::VisitInstanceCallNode(InstanceCallNode* node) { 2656 void ValueGraphVisitor::VisitInstanceCallNode(InstanceCallNode* node) {
2633 if (node->is_conditional()) { 2657 if (node->is_conditional()) {
2634 ValueGraphVisitor for_receiver(owner()); 2658 ValueGraphVisitor for_receiver(owner());
2635 node->receiver()->Visit(&for_receiver); 2659 node->receiver()->Visit(&for_receiver);
2636 Append(for_receiver); 2660 Append(for_receiver);
2637 Do(BuildStoreExprTemp(for_receiver.value())); 2661 Do(BuildStoreExprTemp(for_receiver.value(), node->token_pos()));
2638 BuildInstanceCallConditional(node); 2662 BuildInstanceCallConditional(node);
2639 ReturnDefinition(BuildLoadExprTemp()); 2663 ReturnDefinition(BuildLoadExprTemp(node->token_pos()));
2640 } else { 2664 } else {
2641 EffectGraphVisitor::VisitInstanceCallNode(node); 2665 EffectGraphVisitor::VisitInstanceCallNode(node);
2642 } 2666 }
2643 } 2667 }
2644 2668
2645 2669
2646 void EffectGraphVisitor::VisitInstanceCallNode(InstanceCallNode* node) { 2670 void EffectGraphVisitor::VisitInstanceCallNode(InstanceCallNode* node) {
2647 ValueGraphVisitor for_receiver(owner()); 2671 ValueGraphVisitor for_receiver(owner());
2648 node->receiver()->Visit(&for_receiver); 2672 node->receiver()->Visit(&for_receiver);
2649 Append(for_receiver); 2673 Append(for_receiver);
2650 if (node->is_conditional()) { 2674 if (node->is_conditional()) {
2651 Do(BuildStoreExprTemp(for_receiver.value())); 2675 Do(BuildStoreExprTemp(for_receiver.value(), node->token_pos()));
2652 BuildInstanceCallConditional(node); 2676 BuildInstanceCallConditional(node);
2653 } else { 2677 } else {
2654 PushArgumentInstr* push_receiver = PushArgument(for_receiver.value()); 2678 PushArgumentInstr* push_receiver = PushArgument(for_receiver.value());
2655 ZoneGrowableArray<PushArgumentInstr*>* arguments = 2679 ZoneGrowableArray<PushArgumentInstr*>* arguments =
2656 new(Z) ZoneGrowableArray<PushArgumentInstr*>( 2680 new(Z) ZoneGrowableArray<PushArgumentInstr*>(
2657 node->arguments()->length() + 1); 2681 node->arguments()->length() + 1);
2658 arguments->Add(push_receiver); 2682 arguments->Add(push_receiver);
2659 2683
2660 BuildPushArguments(*node->arguments(), arguments); 2684 BuildPushArguments(*node->arguments(), arguments);
2661 InstanceCallInstr* call = new(Z) InstanceCallInstr( 2685 InstanceCallInstr* call = new(Z) InstanceCallInstr(
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
2723 ReturnDefinition(call); 2747 ReturnDefinition(call);
2724 } 2748 }
2725 2749
2726 2750
2727 void EffectGraphVisitor::BuildClosureCall( 2751 void EffectGraphVisitor::BuildClosureCall(
2728 ClosureCallNode* node, bool result_needed) { 2752 ClosureCallNode* node, bool result_needed) {
2729 ValueGraphVisitor for_closure(owner()); 2753 ValueGraphVisitor for_closure(owner());
2730 node->closure()->Visit(&for_closure); 2754 node->closure()->Visit(&for_closure);
2731 Append(for_closure); 2755 Append(for_closure);
2732 2756
2733 LocalVariable* tmp_var = EnterTempLocalScope(for_closure.value()); 2757 LocalVariable* tmp_var =
2758 EnterTempLocalScope(for_closure.value(), node->token_pos());
2734 2759
2735 ZoneGrowableArray<PushArgumentInstr*>* arguments = 2760 ZoneGrowableArray<PushArgumentInstr*>* arguments =
2736 new(Z) ZoneGrowableArray<PushArgumentInstr*>(node->arguments()->length()); 2761 new(Z) ZoneGrowableArray<PushArgumentInstr*>(node->arguments()->length());
2737 Value* closure_val = Bind(new(Z) LoadLocalInstr(*tmp_var)); 2762 Value* closure_val = Bind(new(Z) LoadLocalInstr(*tmp_var, node->token_pos()));
2738 PushArgumentInstr* push_closure = PushArgument(closure_val); 2763 PushArgumentInstr* push_closure = PushArgument(closure_val);
2739 arguments->Add(push_closure); 2764 arguments->Add(push_closure);
2740 BuildPushArguments(*node->arguments(), arguments); 2765 BuildPushArguments(*node->arguments(), arguments);
2741 2766
2742 closure_val = Bind(new(Z) LoadLocalInstr(*tmp_var)); 2767 closure_val = Bind(new(Z) LoadLocalInstr(*tmp_var, node->token_pos()));
2743 LoadFieldInstr* function_load = new(Z) LoadFieldInstr( 2768 LoadFieldInstr* function_load = new(Z) LoadFieldInstr(
2744 closure_val, 2769 closure_val,
2745 Closure::function_offset(), 2770 Closure::function_offset(),
2746 AbstractType::ZoneHandle(Z, AbstractType::null()), 2771 AbstractType::ZoneHandle(Z, AbstractType::null()),
2747 node->token_pos()); 2772 node->token_pos());
2748 function_load->set_is_immutable(true); 2773 function_load->set_is_immutable(true);
2749 Value* function_val = Bind(function_load); 2774 Value* function_val = Bind(function_load);
2750 2775
2751 Definition* closure_call = 2776 Definition* closure_call =
2752 new(Z) ClosureCallInstr(function_val, node, arguments); 2777 new(Z) ClosureCallInstr(function_val, node, arguments);
2753 if (result_needed) { 2778 if (result_needed) {
2754 Value* result = Bind(closure_call); 2779 Value* result = Bind(closure_call);
2755 Do(new(Z) StoreLocalInstr(*tmp_var, result)); 2780 Do(new(Z) StoreLocalInstr(*tmp_var, result, ST(node->token_pos())));
2756 } else { 2781 } else {
2757 Do(closure_call); 2782 Do(closure_call);
2758 } 2783 }
2759 ReturnDefinition(ExitTempLocalScope(tmp_var)); 2784 ReturnDefinition(ExitTempLocalScope(tmp_var, node->token_pos()));
2760 } 2785 }
2761 2786
2762 2787
2763 void EffectGraphVisitor::VisitClosureCallNode(ClosureCallNode* node) { 2788 void EffectGraphVisitor::VisitClosureCallNode(ClosureCallNode* node) {
2764 BuildClosureCall(node, false); 2789 BuildClosureCall(node, false);
2765 } 2790 }
2766 2791
2767 2792
2768 void ValueGraphVisitor::VisitClosureCallNode(ClosureCallNode* node) { 2793 void ValueGraphVisitor::VisitClosureCallNode(ClosureCallNode* node) {
2769 BuildClosureCall(node, true); 2794 BuildClosureCall(node, true);
(...skipping 109 matching lines...) Expand 10 before | Expand all | Expand 10 after
2879 // t_n+1 <- ctor-arg 2904 // t_n+1 <- ctor-arg
2880 // t_n+2... <- constructor arguments start here 2905 // t_n+2... <- constructor arguments start here
2881 // StaticCall(constructor, t_n+1, t_n+2, ...) 2906 // StaticCall(constructor, t_n+1, t_n+2, ...)
2882 // No need to preserve allocated value (simpler than in ValueGraphVisitor). 2907 // No need to preserve allocated value (simpler than in ValueGraphVisitor).
2883 Value* allocated_value = BuildObjectAllocation(node); 2908 Value* allocated_value = BuildObjectAllocation(node);
2884 PushArgumentInstr* push_allocated_value = PushArgument(allocated_value); 2909 PushArgumentInstr* push_allocated_value = PushArgument(allocated_value);
2885 BuildConstructorCall(node, push_allocated_value); 2910 BuildConstructorCall(node, push_allocated_value);
2886 } 2911 }
2887 2912
2888 2913
2889 Value* EffectGraphVisitor::BuildInstantiator(const Class& instantiator_class) { 2914 Value* EffectGraphVisitor::BuildInstantiator(intptr_t token_pos,
2915 const Class& instantiator_class) {
2890 ASSERT(instantiator_class.NumTypeParameters() > 0); 2916 ASSERT(instantiator_class.NumTypeParameters() > 0);
2891 Function& outer_function = Function::Handle(Z, owner()->function().raw()); 2917 Function& outer_function = Function::Handle(Z, owner()->function().raw());
2892 while (outer_function.IsLocalFunction()) { 2918 while (outer_function.IsLocalFunction()) {
2893 outer_function = outer_function.parent_function(); 2919 outer_function = outer_function.parent_function();
2894 } 2920 }
2895 if (outer_function.IsFactory()) { 2921 if (outer_function.IsFactory()) {
2896 return NULL; 2922 return NULL;
2897 } 2923 }
2898 2924
2899 LocalVariable* instantiator = owner()->parsed_function().instantiator(); 2925 LocalVariable* instantiator = owner()->parsed_function().instantiator();
2900 ASSERT(instantiator != NULL); 2926 ASSERT(instantiator != NULL);
2901 Value* result = Bind(BuildLoadLocal(*instantiator)); 2927 Value* result = Bind(BuildLoadLocal(*instantiator, token_pos));
2902 return result; 2928 return result;
2903 } 2929 }
2904 2930
2905 2931
2906 // 'expression_temp_var' may not be used inside this method if 'instantiator' 2932 // 'expression_temp_var' may not be used inside this method if 'instantiator'
2907 // is not NULL. 2933 // is not NULL.
2908 Value* EffectGraphVisitor::BuildInstantiatorTypeArguments( 2934 Value* EffectGraphVisitor::BuildInstantiatorTypeArguments(
2909 intptr_t token_pos, 2935 intptr_t token_pos,
2910 const Class& instantiator_class, 2936 const Class& instantiator_class,
2911 Value* instantiator) { 2937 Value* instantiator) {
(...skipping 15 matching lines...) Expand all
2927 Function& outer_function = Function::Handle(Z, owner()->function().raw()); 2953 Function& outer_function = Function::Handle(Z, owner()->function().raw());
2928 while (outer_function.IsLocalFunction()) { 2954 while (outer_function.IsLocalFunction()) {
2929 outer_function = outer_function.parent_function(); 2955 outer_function = outer_function.parent_function();
2930 } 2956 }
2931 if (outer_function.IsFactory()) { 2957 if (outer_function.IsFactory()) {
2932 // No instantiator for factories. 2958 // No instantiator for factories.
2933 ASSERT(instantiator == NULL); 2959 ASSERT(instantiator == NULL);
2934 LocalVariable* instantiator_var = 2960 LocalVariable* instantiator_var =
2935 owner()->parsed_function().instantiator(); 2961 owner()->parsed_function().instantiator();
2936 ASSERT(instantiator_var != NULL); 2962 ASSERT(instantiator_var != NULL);
2937 return Bind(BuildLoadLocal(*instantiator_var)); 2963 return Bind(BuildLoadLocal(*instantiator_var, token_pos));
2938 } 2964 }
2939 if (instantiator == NULL) { 2965 if (instantiator == NULL) {
2940 instantiator = BuildInstantiator(instantiator_class); 2966 instantiator = BuildInstantiator(token_pos, instantiator_class);
2941 } 2967 }
2942 // The instantiator is the receiver of the caller, which is not a factory. 2968 // The instantiator is the receiver of the caller, which is not a factory.
2943 // The receiver cannot be null; extract its TypeArguments object. 2969 // The receiver cannot be null; extract its TypeArguments object.
2944 // Note that in the factory case, the instantiator is the first parameter 2970 // Note that in the factory case, the instantiator is the first parameter
2945 // of the factory, i.e. already a TypeArguments object. 2971 // of the factory, i.e. already a TypeArguments object.
2946 intptr_t type_arguments_field_offset = 2972 intptr_t type_arguments_field_offset =
2947 instantiator_class.type_arguments_field_offset(); 2973 instantiator_class.type_arguments_field_offset();
2948 ASSERT(type_arguments_field_offset != Class::kNoTypeArguments); 2974 ASSERT(type_arguments_field_offset != Class::kNoTypeArguments);
2949 2975
2950 return Bind(new(Z) LoadFieldInstr( 2976 return Bind(new(Z) LoadFieldInstr(
2951 instantiator, 2977 instantiator,
2952 type_arguments_field_offset, 2978 type_arguments_field_offset,
2953 Type::ZoneHandle(Z, Type::null()), // Not an instance, no type. 2979 Type::ZoneHandle(Z, Type::null()), // Not an instance, no type.
2954 Scanner::kNoSourcePos)); 2980 token_pos));
2955 } 2981 }
2956 2982
2957 2983
2958 Value* EffectGraphVisitor::BuildInstantiatedTypeArguments( 2984 Value* EffectGraphVisitor::BuildInstantiatedTypeArguments(
2959 intptr_t token_pos, 2985 intptr_t token_pos,
2960 const TypeArguments& type_arguments) { 2986 const TypeArguments& type_arguments) {
2961 if (type_arguments.IsNull() || type_arguments.IsInstantiated()) { 2987 if (type_arguments.IsNull() || type_arguments.IsInstantiated()) {
2962 return Bind(new(Z) ConstantInstr(type_arguments)); 2988 return Bind(new(Z) ConstantInstr(type_arguments));
2963 } 2989 }
2964 // The type arguments are uninstantiated. 2990 // The type arguments are uninstantiated.
(...skipping 23 matching lines...) Expand all
2988 3014
2989 // t_n contains the allocated and initialized object. 3015 // t_n contains the allocated and initialized object.
2990 // t_n <- AllocateObject(class) 3016 // t_n <- AllocateObject(class)
2991 // t_n <- StoreLocal(temp, t_n); 3017 // t_n <- StoreLocal(temp, t_n);
2992 // t_n+1 <- ctor-arg 3018 // t_n+1 <- ctor-arg
2993 // t_n+2... <- constructor arguments start here 3019 // t_n+2... <- constructor arguments start here
2994 // StaticCall(constructor, t_n, t_n+1, ...) 3020 // StaticCall(constructor, t_n, t_n+1, ...)
2995 // tn <- LoadLocal(temp) 3021 // tn <- LoadLocal(temp)
2996 3022
2997 Value* allocate = BuildObjectAllocation(node); 3023 Value* allocate = BuildObjectAllocation(node);
2998 { LocalVariable* tmp_var = EnterTempLocalScope(allocate); 3024 { LocalVariable* tmp_var = EnterTempLocalScope(allocate, node->token_pos());
2999 Value* allocated_tmp = Bind(new(Z) LoadLocalInstr(*tmp_var)); 3025 Value* allocated_tmp =
3026 Bind(new(Z) LoadLocalInstr(*tmp_var, node->token_pos()));
3000 PushArgumentInstr* push_allocated_value = PushArgument(allocated_tmp); 3027 PushArgumentInstr* push_allocated_value = PushArgument(allocated_tmp);
3001 BuildConstructorCall(node, push_allocated_value); 3028 BuildConstructorCall(node, push_allocated_value);
3002 ReturnDefinition(ExitTempLocalScope(tmp_var)); 3029 ReturnDefinition(ExitTempLocalScope(tmp_var, node->token_pos()));
3003 } 3030 }
3004 } 3031 }
3005 3032
3006 3033
3007 3034
3008 void EffectGraphVisitor::BuildInstanceGetterConditional( 3035 void EffectGraphVisitor::BuildInstanceGetterConditional(
3009 InstanceGetterNode* node) { 3036 InstanceGetterNode* node) {
3037 const intptr_t token_pos = node->token_pos();
3010 LocalVariable* temp_var = owner()->parsed_function().expression_temp_var(); 3038 LocalVariable* temp_var = owner()->parsed_function().expression_temp_var();
3011 LoadLocalNode* load_temp = 3039 LoadLocalNode* load_temp = new(Z) LoadLocalNode(token_pos, temp_var);
3012 new(Z) LoadLocalNode(Scanner::kNoSourcePos, temp_var);
3013 3040
3014 LiteralNode* null_constant = 3041 LiteralNode* null_constant =
3015 new(Z) LiteralNode(Scanner::kNoSourcePos, Object::null_instance()); 3042 new(Z) LiteralNode(ST(token_pos), Object::null_instance());
3016 ComparisonNode* check_is_null = 3043 ComparisonNode* check_is_null =
3017 new(Z) ComparisonNode(Scanner::kNoSourcePos, 3044 new(Z) ComparisonNode(ST(token_pos),
3018 Token::kEQ, 3045 Token::kEQ,
3019 load_temp, 3046 load_temp,
3020 null_constant); 3047 null_constant);
3021 TestGraphVisitor for_test(owner(), Scanner::kNoSourcePos); 3048 TestGraphVisitor for_test(owner(), ST(token_pos));
3022 check_is_null->Visit(&for_test); 3049 check_is_null->Visit(&for_test);
3023 3050
3024 EffectGraphVisitor for_true(owner()); 3051 EffectGraphVisitor for_true(owner());
3025 EffectGraphVisitor for_false(owner()); 3052 EffectGraphVisitor for_false(owner());
3026 3053
3027 StoreLocalNode* store_null = 3054 StoreLocalNode* store_null =
3028 new(Z) StoreLocalNode(Scanner::kNoSourcePos, temp_var, null_constant); 3055 new(Z) StoreLocalNode(ST(token_pos), temp_var, null_constant);
3029 store_null->Visit(&for_true); 3056 store_null->Visit(&for_true);
3030 3057
3031 InstanceGetterNode* getter = 3058 InstanceGetterNode* getter = new(Z) InstanceGetterNode(token_pos,
3032 new(Z) InstanceGetterNode(node->token_pos(), 3059 load_temp,
3033 load_temp, 3060 node->field_name());
3034 node->field_name());
3035 StoreLocalNode* store_getter = 3061 StoreLocalNode* store_getter =
3036 new(Z) StoreLocalNode(Scanner::kNoSourcePos, temp_var, getter); 3062 new(Z) StoreLocalNode(ST(token_pos), temp_var, getter);
3037 store_getter->Visit(&for_false); 3063 store_getter->Visit(&for_false);
3038 3064
3039 Join(for_test, for_true, for_false); 3065 Join(for_test, for_true, for_false);
3040 } 3066 }
3041 3067
3042 3068
3043 void ValueGraphVisitor::VisitInstanceGetterNode(InstanceGetterNode* node) { 3069 void ValueGraphVisitor::VisitInstanceGetterNode(InstanceGetterNode* node) {
3044 if (node->is_conditional()) { 3070 if (node->is_conditional()) {
3045 ValueGraphVisitor for_receiver(owner()); 3071 ValueGraphVisitor for_receiver(owner());
3046 node->receiver()->Visit(&for_receiver); 3072 node->receiver()->Visit(&for_receiver);
3047 Append(for_receiver); 3073 Append(for_receiver);
3048 Do(BuildStoreExprTemp(for_receiver.value())); 3074 Do(BuildStoreExprTemp(for_receiver.value(), node->token_pos()));
3049 BuildInstanceGetterConditional(node); 3075 BuildInstanceGetterConditional(node);
3050 ReturnDefinition(BuildLoadExprTemp()); 3076 ReturnDefinition(BuildLoadExprTemp(node->token_pos()));
3051 } else { 3077 } else {
3052 EffectGraphVisitor::VisitInstanceGetterNode(node); 3078 EffectGraphVisitor::VisitInstanceGetterNode(node);
3053 } 3079 }
3054 } 3080 }
3055 3081
3056 3082
3057 void EffectGraphVisitor::VisitInstanceGetterNode(InstanceGetterNode* node) { 3083 void EffectGraphVisitor::VisitInstanceGetterNode(InstanceGetterNode* node) {
3058 ValueGraphVisitor for_receiver(owner()); 3084 ValueGraphVisitor for_receiver(owner());
3059 node->receiver()->Visit(&for_receiver); 3085 node->receiver()->Visit(&for_receiver);
3060 Append(for_receiver); 3086 Append(for_receiver);
3061 if (node->is_conditional()) { 3087 if (node->is_conditional()) {
3062 Do(BuildStoreExprTemp(for_receiver.value())); 3088 Do(BuildStoreExprTemp(for_receiver.value(), node->token_pos()));
3063 BuildInstanceGetterConditional(node); 3089 BuildInstanceGetterConditional(node);
3064 } else { 3090 } else {
3065 PushArgumentInstr* push_receiver = PushArgument(for_receiver.value()); 3091 PushArgumentInstr* push_receiver = PushArgument(for_receiver.value());
3066 ZoneGrowableArray<PushArgumentInstr*>* arguments = 3092 ZoneGrowableArray<PushArgumentInstr*>* arguments =
3067 new(Z) ZoneGrowableArray<PushArgumentInstr*>(1); 3093 new(Z) ZoneGrowableArray<PushArgumentInstr*>(1);
3068 arguments->Add(push_receiver); 3094 arguments->Add(push_receiver);
3069 const String& name = 3095 const String& name =
3070 String::ZoneHandle(Z, Field::GetterSymbol(node->field_name())); 3096 String::ZoneHandle(Z, Field::GetterSymbol(node->field_name()));
3071 InstanceCallInstr* call = new(Z) InstanceCallInstr( 3097 InstanceCallInstr* call = new(Z) InstanceCallInstr(
3072 node->token_pos(), 3098 node->token_pos(),
(...skipping 15 matching lines...) Expand all
3088 node->receiver()->Visit(&for_receiver); 3114 node->receiver()->Visit(&for_receiver);
3089 Append(for_receiver); 3115 Append(for_receiver);
3090 arguments->Add(PushArgument(for_receiver.value())); 3116 arguments->Add(PushArgument(for_receiver.value()));
3091 3117
3092 ValueGraphVisitor for_value(owner()); 3118 ValueGraphVisitor for_value(owner());
3093 node->value()->Visit(&for_value); 3119 node->value()->Visit(&for_value);
3094 Append(for_value); 3120 Append(for_value);
3095 3121
3096 Value* value = NULL; 3122 Value* value = NULL;
3097 if (result_is_needed) { 3123 if (result_is_needed) {
3098 value = Bind(BuildStoreExprTemp(for_value.value())); 3124 value = Bind(BuildStoreExprTemp(for_value.value(), node->token_pos()));
3099 } else { 3125 } else {
3100 value = for_value.value(); 3126 value = for_value.value();
3101 } 3127 }
3102 arguments->Add(PushArgument(value)); 3128 arguments->Add(PushArgument(value));
3103 } 3129 }
3104 3130
3105 3131
3106 void EffectGraphVisitor::VisitInstanceSetterNode(InstanceSetterNode* node) { 3132 void EffectGraphVisitor::VisitInstanceSetterNode(InstanceSetterNode* node) {
3133 const intptr_t token_pos = node->token_pos();
3107 if (node->is_conditional()) { 3134 if (node->is_conditional()) {
3108 ValueGraphVisitor for_receiver(owner()); 3135 ValueGraphVisitor for_receiver(owner());
3109 node->receiver()->Visit(&for_receiver); 3136 node->receiver()->Visit(&for_receiver);
3110 Append(for_receiver); 3137 Append(for_receiver);
3111 Do(BuildStoreExprTemp(for_receiver.value())); 3138 Do(BuildStoreExprTemp(for_receiver.value(), token_pos));
3112 3139
3113 LocalVariable* temp_var = owner()->parsed_function().expression_temp_var(); 3140 LocalVariable* temp_var = owner()->parsed_function().expression_temp_var();
3114 LoadLocalNode* load_temp = 3141 LoadLocalNode* load_temp =
3115 new(Z) LoadLocalNode(Scanner::kNoSourcePos, temp_var); 3142 new(Z) LoadLocalNode(ST(token_pos), temp_var);
3116 LiteralNode* null_constant = 3143 LiteralNode* null_constant =
3117 new(Z) LiteralNode(Scanner::kNoSourcePos, Object::null_instance()); 3144 new(Z) LiteralNode(ST(token_pos), Object::null_instance());
3118 ComparisonNode* check_is_null = 3145 ComparisonNode* check_is_null =
3119 new(Z) ComparisonNode(Scanner::kNoSourcePos, 3146 new(Z) ComparisonNode(ST(token_pos),
3120 Token::kEQ, 3147 Token::kEQ,
3121 load_temp, 3148 load_temp,
3122 null_constant); 3149 null_constant);
3123 TestGraphVisitor for_test(owner(), Scanner::kNoSourcePos); 3150 TestGraphVisitor for_test(owner(), ST(token_pos));
3124 check_is_null->Visit(&for_test); 3151 check_is_null->Visit(&for_test);
3125 3152
3126 EffectGraphVisitor for_true(owner()); 3153 EffectGraphVisitor for_true(owner());
3127 EffectGraphVisitor for_false(owner()); 3154 EffectGraphVisitor for_false(owner());
3128 3155
3129 InstanceSetterNode* setter = 3156 InstanceSetterNode* setter =
3130 new(Z) InstanceSetterNode(node->token_pos(), 3157 new(Z) InstanceSetterNode(token_pos,
3131 load_temp, 3158 load_temp,
3132 node->field_name(), 3159 node->field_name(),
3133 node->value()); 3160 node->value());
3134 setter->Visit(&for_false); 3161 setter->Visit(&for_false);
3135 Join(for_test, for_true, for_false); 3162 Join(for_test, for_true, for_false);
3136 return; 3163 return;
3137 } 3164 }
3138 ZoneGrowableArray<PushArgumentInstr*>* arguments = 3165 ZoneGrowableArray<PushArgumentInstr*>* arguments =
3139 new(Z) ZoneGrowableArray<PushArgumentInstr*>(2); 3166 new(Z) ZoneGrowableArray<PushArgumentInstr*>(2);
3140 BuildInstanceSetterArguments(node, arguments, kResultNotNeeded); 3167 BuildInstanceSetterArguments(node, arguments, kResultNotNeeded);
3141 const String& name = 3168 const String& name =
3142 String::ZoneHandle(Z, Field::SetterSymbol(node->field_name())); 3169 String::ZoneHandle(Z, Field::SetterSymbol(node->field_name()));
3143 const intptr_t kNumArgsChecked = 1; // Do not check value type. 3170 const intptr_t kNumArgsChecked = 1; // Do not check value type.
3144 InstanceCallInstr* call = new(Z) InstanceCallInstr(node->token_pos(), 3171 InstanceCallInstr* call = new(Z) InstanceCallInstr(token_pos,
3145 name, 3172 name,
3146 Token::kSET, 3173 Token::kSET,
3147 arguments, 3174 arguments,
3148 Object::null_array(), 3175 Object::null_array(),
3149 kNumArgsChecked, 3176 kNumArgsChecked,
3150 owner()->ic_data_array()); 3177 owner()->ic_data_array());
3151 ReturnDefinition(call); 3178 ReturnDefinition(call);
3152 } 3179 }
3153 3180
3154 3181
3155 void ValueGraphVisitor::VisitInstanceSetterNode(InstanceSetterNode* node) { 3182 void ValueGraphVisitor::VisitInstanceSetterNode(InstanceSetterNode* node) {
3183 const intptr_t token_pos = node->token_pos();
3156 if (node->is_conditional()) { 3184 if (node->is_conditional()) {
3157 ValueGraphVisitor for_receiver(owner()); 3185 ValueGraphVisitor for_receiver(owner());
3158 node->receiver()->Visit(&for_receiver); 3186 node->receiver()->Visit(&for_receiver);
3159 Append(for_receiver); 3187 Append(for_receiver);
3160 Do(BuildStoreExprTemp(for_receiver.value())); 3188 Do(BuildStoreExprTemp(for_receiver.value(), token_pos));
3161 3189
3162 LocalVariable* temp_var = owner()->parsed_function().expression_temp_var(); 3190 LocalVariable* temp_var = owner()->parsed_function().expression_temp_var();
3163 LoadLocalNode* load_temp = 3191 LoadLocalNode* load_temp =
3164 new(Z) LoadLocalNode(Scanner::kNoSourcePos, temp_var); 3192 new(Z) LoadLocalNode(ST(token_pos), temp_var);
3165 LiteralNode* null_constant = 3193 LiteralNode* null_constant =
3166 new(Z) LiteralNode(Scanner::kNoSourcePos, Object::null_instance()); 3194 new(Z) LiteralNode(ST(token_pos), Object::null_instance());
3167 ComparisonNode* check_is_null = 3195 ComparisonNode* check_is_null =
3168 new(Z) ComparisonNode(Scanner::kNoSourcePos, 3196 new(Z) ComparisonNode(ST(token_pos),
3169 Token::kEQ, 3197 Token::kEQ,
3170 load_temp, 3198 load_temp,
3171 null_constant); 3199 null_constant);
3172 TestGraphVisitor for_test(owner(), Scanner::kNoSourcePos); 3200 TestGraphVisitor for_test(owner(), ST(token_pos));
3173 check_is_null->Visit(&for_test); 3201 check_is_null->Visit(&for_test);
3174 3202
3175 ValueGraphVisitor for_true(owner()); 3203 ValueGraphVisitor for_true(owner());
3176 null_constant->Visit(&for_true); 3204 null_constant->Visit(&for_true);
3177 for_true.Do(BuildStoreExprTemp(for_true.value())); 3205 for_true.Do(BuildStoreExprTemp(for_true.value(), token_pos));
3178 3206
3179 ValueGraphVisitor for_false(owner()); 3207 ValueGraphVisitor for_false(owner());
3180 InstanceSetterNode* setter = 3208 InstanceSetterNode* setter =
3181 new(Z) InstanceSetterNode(node->token_pos(), 3209 new(Z) InstanceSetterNode(token_pos,
3182 load_temp, 3210 load_temp,
3183 node->field_name(), 3211 node->field_name(),
3184 node->value()); 3212 node->value());
3185 setter->Visit(&for_false); 3213 setter->Visit(&for_false);
3186 for_false.Do(BuildStoreExprTemp(for_false.value())); 3214 for_false.Do(BuildStoreExprTemp(for_false.value(), token_pos));
3187 3215
3188 Join(for_test, for_true, for_false); 3216 Join(for_test, for_true, for_false);
3189 ReturnDefinition(BuildLoadExprTemp()); 3217 ReturnDefinition(BuildLoadExprTemp(token_pos));
3190 return; 3218 return;
3191 } 3219 }
3192 ZoneGrowableArray<PushArgumentInstr*>* arguments = 3220 ZoneGrowableArray<PushArgumentInstr*>* arguments =
3193 new(Z) ZoneGrowableArray<PushArgumentInstr*>(2); 3221 new(Z) ZoneGrowableArray<PushArgumentInstr*>(2);
3194 BuildInstanceSetterArguments(node, arguments, kResultNeeded); 3222 BuildInstanceSetterArguments(node, arguments, kResultNeeded);
3195 const String& name = 3223 const String& name =
3196 String::ZoneHandle(Z, Field::SetterSymbol(node->field_name())); 3224 String::ZoneHandle(Z, Field::SetterSymbol(node->field_name()));
3197 const intptr_t kNumArgsChecked = 1; // Do not check value type. 3225 const intptr_t kNumArgsChecked = 1; // Do not check value type.
3198 Do(new(Z) InstanceCallInstr(node->token_pos(), 3226 Do(new(Z) InstanceCallInstr(token_pos,
3199 name, 3227 name,
3200 Token::kSET, 3228 Token::kSET,
3201 arguments, 3229 arguments,
3202 Object::null_array(), 3230 Object::null_array(),
3203 kNumArgsChecked, 3231 kNumArgsChecked,
3204 owner()->ic_data_array())); 3232 owner()->ic_data_array()));
3205 ReturnDefinition(BuildLoadExprTemp()); 3233 ReturnDefinition(BuildLoadExprTemp(token_pos));
3206 } 3234 }
3207 3235
3208 3236
3209 void EffectGraphVisitor::VisitStaticGetterNode(StaticGetterNode* node) { 3237 void EffectGraphVisitor::VisitStaticGetterNode(StaticGetterNode* node) {
3210 const String& getter_name = 3238 const String& getter_name =
3211 String::ZoneHandle(Z, Field::GetterSymbol(node->field_name())); 3239 String::ZoneHandle(Z, Field::GetterSymbol(node->field_name()));
3212 ZoneGrowableArray<PushArgumentInstr*>* arguments = 3240 ZoneGrowableArray<PushArgumentInstr*>* arguments =
3213 new(Z) ZoneGrowableArray<PushArgumentInstr*>(); 3241 new(Z) ZoneGrowableArray<PushArgumentInstr*>();
3214 Function& getter_function = Function::ZoneHandle(Z, Function::null()); 3242 Function& getter_function = Function::ZoneHandle(Z, Function::null());
3215 if (node->is_super_getter()) { 3243 if (node->is_super_getter()) {
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
3277 ReturnDefinition(call); 3305 ReturnDefinition(call);
3278 } 3306 }
3279 3307
3280 3308
3281 void EffectGraphVisitor::BuildStaticSetter(StaticSetterNode* node, 3309 void EffectGraphVisitor::BuildStaticSetter(StaticSetterNode* node,
3282 bool result_is_needed) { 3310 bool result_is_needed) {
3283 const String& setter_name = 3311 const String& setter_name =
3284 String::ZoneHandle(Z, Field::SetterSymbol(node->field_name())); 3312 String::ZoneHandle(Z, Field::SetterSymbol(node->field_name()));
3285 ZoneGrowableArray<PushArgumentInstr*>* arguments = 3313 ZoneGrowableArray<PushArgumentInstr*>* arguments =
3286 new(Z) ZoneGrowableArray<PushArgumentInstr*>(1); 3314 new(Z) ZoneGrowableArray<PushArgumentInstr*>(1);
3315 const intptr_t token_pos = node->token_pos();
3287 // A super setter is an instance setter whose setter function is 3316 // A super setter is an instance setter whose setter function is
3288 // resolved at compile time (in the caller instance getter's super class). 3317 // resolved at compile time (in the caller instance getter's super class).
3289 // Unlike a static getter, a super getter has a receiver parameter. 3318 // Unlike a static getter, a super getter has a receiver parameter.
3290 const bool is_super_setter = (node->receiver() != NULL); 3319 const bool is_super_setter = (node->receiver() != NULL);
3291 const Function& setter_function = node->function(); 3320 const Function& setter_function = node->function();
3292 StaticCallInstr* call; 3321 StaticCallInstr* call;
3293 if (setter_function.IsNull()) { 3322 if (setter_function.IsNull()) {
3294 if (is_super_setter) { 3323 if (is_super_setter) {
3295 ASSERT(node->receiver() != NULL); 3324 ASSERT(node->receiver() != NULL);
3296 // Resolve and call noSuchMethod. 3325 // Resolve and call noSuchMethod.
3297 ArgumentListNode* arguments = new(Z) ArgumentListNode(node->token_pos()); 3326 ArgumentListNode* arguments = new(Z) ArgumentListNode(token_pos);
3298 arguments->Add(node->receiver()); 3327 arguments->Add(node->receiver());
3299 arguments->Add(node->value()); 3328 arguments->Add(node->value());
3300 call = BuildStaticNoSuchMethodCall( 3329 call = BuildStaticNoSuchMethodCall(
3301 node->cls(), 3330 node->cls(),
3302 node->receiver(), 3331 node->receiver(),
3303 setter_name, 3332 setter_name,
3304 arguments, 3333 arguments,
3305 result_is_needed, // Save last arg if result is needed. 3334 result_is_needed, // Save last arg if result is needed.
3306 true); // Super invocation. 3335 true); // Super invocation.
3307 } else { 3336 } else {
3308 // Throw a NoSuchMethodError. 3337 // Throw a NoSuchMethodError.
3309 ArgumentListNode* arguments = new(Z) ArgumentListNode(node->token_pos()); 3338 ArgumentListNode* arguments = new(Z) ArgumentListNode(token_pos);
3310 arguments->Add(node->value()); 3339 arguments->Add(node->value());
3311 call = BuildThrowNoSuchMethodError( 3340 call = BuildThrowNoSuchMethodError(
3312 node->token_pos(), 3341 token_pos,
3313 node->cls(), 3342 node->cls(),
3314 setter_name, 3343 setter_name,
3315 arguments, // Argument is the value passed to the setter. 3344 arguments, // Argument is the value passed to the setter.
3316 InvocationMirror::EncodeType( 3345 InvocationMirror::EncodeType(
3317 node->cls().IsTopLevel() ? 3346 node->cls().IsTopLevel() ?
3318 InvocationMirror::kTopLevel : 3347 InvocationMirror::kTopLevel :
3319 InvocationMirror::kStatic, 3348 InvocationMirror::kStatic,
3320 InvocationMirror::kSetter)); 3349 InvocationMirror::kSetter));
3321 } 3350 }
3322 } else { 3351 } else {
3323 if (is_super_setter) { 3352 if (is_super_setter) {
3324 // Add receiver of instance getter. 3353 // Add receiver of instance getter.
3325 ValueGraphVisitor for_receiver(owner()); 3354 ValueGraphVisitor for_receiver(owner());
3326 node->receiver()->Visit(&for_receiver); 3355 node->receiver()->Visit(&for_receiver);
3327 Append(for_receiver); 3356 Append(for_receiver);
3328 arguments->Add(PushArgument(for_receiver.value())); 3357 arguments->Add(PushArgument(for_receiver.value()));
3329 } 3358 }
3330 ValueGraphVisitor for_value(owner()); 3359 ValueGraphVisitor for_value(owner());
3331 node->value()->Visit(&for_value); 3360 node->value()->Visit(&for_value);
3332 Append(for_value); 3361 Append(for_value);
3333 Value* value = NULL; 3362 Value* value = NULL;
3334 if (result_is_needed) { 3363 if (result_is_needed) {
3335 value = Bind(BuildStoreExprTemp(for_value.value())); 3364 value = Bind(BuildStoreExprTemp(for_value.value(), token_pos));
3336 } else { 3365 } else {
3337 value = for_value.value(); 3366 value = for_value.value();
3338 } 3367 }
3339 arguments->Add(PushArgument(value)); 3368 arguments->Add(PushArgument(value));
3340 3369
3341 call = new(Z) StaticCallInstr(node->token_pos(), 3370 call = new(Z) StaticCallInstr(token_pos,
3342 setter_function, 3371 setter_function,
3343 Object::null_array(), // No names. 3372 Object::null_array(), // No names.
3344 arguments, 3373 arguments,
3345 owner()->ic_data_array()); 3374 owner()->ic_data_array());
3346 } 3375 }
3347 if (result_is_needed) { 3376 if (result_is_needed) {
3348 Do(call); 3377 Do(call);
3349 ReturnDefinition(BuildLoadExprTemp()); 3378 ReturnDefinition(BuildLoadExprTemp(token_pos));
3350 } else { 3379 } else {
3351 ReturnDefinition(call); 3380 ReturnDefinition(call);
3352 } 3381 }
3353 } 3382 }
3354 3383
3355 3384
3356 void EffectGraphVisitor::VisitStaticSetterNode(StaticSetterNode* node) { 3385 void EffectGraphVisitor::VisitStaticSetterNode(StaticSetterNode* node) {
3357 BuildStaticSetter(node, false); // Result not needed. 3386 BuildStaticSetter(node, false); // Result not needed.
3358 } 3387 }
3359 3388
(...skipping 15 matching lines...) Expand all
3375 return TypedData::length_offset(); 3404 return TypedData::length_offset();
3376 case MethodRecognizer::kGrowableArrayLength: 3405 case MethodRecognizer::kGrowableArrayLength:
3377 return GrowableObjectArray::length_offset(); 3406 return GrowableObjectArray::length_offset();
3378 default: 3407 default:
3379 UNREACHABLE(); 3408 UNREACHABLE();
3380 return 0; 3409 return 0;
3381 } 3410 }
3382 } 3411 }
3383 3412
3384 3413
3385 LoadLocalInstr* EffectGraphVisitor::BuildLoadThisVar(LocalScope* scope) { 3414 LoadLocalInstr* EffectGraphVisitor::BuildLoadThisVar(
3415 LocalScope* scope, intptr_t token_pos) {
3386 LocalVariable* receiver_var = scope->LookupVariable(Symbols::This(), 3416 LocalVariable* receiver_var = scope->LookupVariable(Symbols::This(),
3387 true); // Test only. 3417 true); // Test only.
3388 return new(Z) LoadLocalInstr(*receiver_var); 3418 return new(Z) LoadLocalInstr(*receiver_var, token_pos);
3389 } 3419 }
3390 3420
3391 3421
3392 LoadFieldInstr* EffectGraphVisitor::BuildNativeGetter( 3422 LoadFieldInstr* EffectGraphVisitor::BuildNativeGetter(
3393 NativeBodyNode* node, 3423 NativeBodyNode* node,
3394 MethodRecognizer::Kind kind, 3424 MethodRecognizer::Kind kind,
3395 intptr_t offset, 3425 intptr_t offset,
3396 const Type& type, 3426 const Type& type,
3397 intptr_t class_id) { 3427 intptr_t class_id) {
3398 Value* receiver = Bind(BuildLoadThisVar(node->scope())); 3428 Value* receiver = Bind(BuildLoadThisVar(node->scope(), node->token_pos()));
3399 LoadFieldInstr* load = new(Z) LoadFieldInstr(receiver, 3429 LoadFieldInstr* load = new(Z) LoadFieldInstr(receiver,
3400 offset, 3430 offset,
3401 type, 3431 type,
3402 node->token_pos()); 3432 node->token_pos());
3403 load->set_result_cid(class_id); 3433 load->set_result_cid(class_id);
3404 load->set_recognized_kind(kind); 3434 load->set_recognized_kind(kind);
3405 return load; 3435 return load;
3406 } 3436 }
3407 3437
3408 3438
3409 ConstantInstr* EffectGraphVisitor::DoNativeSetterStoreValue( 3439 ConstantInstr* EffectGraphVisitor::DoNativeSetterStoreValue(
3410 NativeBodyNode* node, 3440 NativeBodyNode* node,
3411 intptr_t offset, 3441 intptr_t offset,
3412 StoreBarrierType emit_store_barrier) { 3442 StoreBarrierType emit_store_barrier) {
3413 Value* receiver = Bind(BuildLoadThisVar(node->scope())); 3443 Value* receiver = Bind(BuildLoadThisVar(node->scope(), node->token_pos()));
3414 LocalVariable* value_var = 3444 LocalVariable* value_var =
3415 node->scope()->LookupVariable(Symbols::Value(), true); 3445 node->scope()->LookupVariable(Symbols::Value(), true);
3416 Value* value = Bind(new(Z) LoadLocalInstr(*value_var)); 3446 Value* value = Bind(new(Z) LoadLocalInstr(*value_var, node->token_pos()));
3417 StoreInstanceFieldInstr* store = new(Z) StoreInstanceFieldInstr( 3447 StoreInstanceFieldInstr* store = new(Z) StoreInstanceFieldInstr(
3418 offset, 3448 offset,
3419 receiver, 3449 receiver,
3420 value, 3450 value,
3421 emit_store_barrier, 3451 emit_store_barrier,
3422 node->token_pos()); 3452 node->token_pos());
3423 Do(store); 3453 Do(store);
3424 return new(Z) ConstantInstr(Object::ZoneHandle(Z, Object::null())); 3454 return new(Z) ConstantInstr(Object::ZoneHandle(Z, Object::null()));
3425 } 3455 }
3426 3456
3427 3457
3428 void EffectGraphVisitor::VisitNativeBodyNode(NativeBodyNode* node) { 3458 void EffectGraphVisitor::VisitNativeBodyNode(NativeBodyNode* node) {
3429 const Function& function = owner()->function(); 3459 const Function& function = owner()->function();
3460 const intptr_t token_pos = node->token_pos();
3430 if (!function.IsClosureFunction()) { 3461 if (!function.IsClosureFunction()) {
3431 MethodRecognizer::Kind kind = MethodRecognizer::RecognizeKind(function); 3462 MethodRecognizer::Kind kind = MethodRecognizer::RecognizeKind(function);
3432 switch (kind) { 3463 switch (kind) {
3433 case MethodRecognizer::kObjectEquals: { 3464 case MethodRecognizer::kObjectEquals: {
3434 Value* receiver = Bind(BuildLoadThisVar(node->scope())); 3465 Value* receiver = Bind(BuildLoadThisVar(node->scope(), token_pos));
3435 LocalVariable* other_var = 3466 LocalVariable* other_var =
3436 node->scope()->LookupVariable(Symbols::Other(), 3467 node->scope()->LookupVariable(Symbols::Other(),
3437 true); // Test only. 3468 true); // Test only.
3438 Value* other = Bind(new(Z) LoadLocalInstr(*other_var)); 3469 Value* other = Bind(new(Z) LoadLocalInstr(*other_var, token_pos));
3439 // Receiver is not a number because numbers override equality. 3470 // Receiver is not a number because numbers override equality.
3440 const bool kNoNumberCheck = false; 3471 const bool kNoNumberCheck = false;
3441 StrictCompareInstr* compare = 3472 StrictCompareInstr* compare =
3442 new(Z) StrictCompareInstr(node->token_pos(), 3473 new(Z) StrictCompareInstr(token_pos,
3443 Token::kEQ_STRICT, 3474 Token::kEQ_STRICT,
3444 receiver, 3475 receiver,
3445 other, 3476 other,
3446 kNoNumberCheck); 3477 kNoNumberCheck);
3447 return ReturnDefinition(compare); 3478 return ReturnDefinition(compare);
3448 } 3479 }
3449 case MethodRecognizer::kStringBaseLength: 3480 case MethodRecognizer::kStringBaseLength:
3450 case MethodRecognizer::kStringBaseIsEmpty: { 3481 case MethodRecognizer::kStringBaseIsEmpty: {
3451 // Treat length loads as mutable (i.e. affected by side effects) to 3482 // Treat length loads as mutable (i.e. affected by side effects) to
3452 // avoid hoisting them since we can't hoist the preceding class-check. 3483 // avoid hoisting them since we can't hoist the preceding class-check.
3453 // This is because of externalization of strings that affects their 3484 // This is because of externalization of strings that affects their
3454 // class-id. 3485 // class-id.
3455 LoadFieldInstr* load = BuildNativeGetter( 3486 LoadFieldInstr* load = BuildNativeGetter(
3456 node, MethodRecognizer::kStringBaseLength, String::length_offset(), 3487 node, MethodRecognizer::kStringBaseLength, String::length_offset(),
3457 Type::ZoneHandle(Z, Type::SmiType()), kSmiCid); 3488 Type::ZoneHandle(Z, Type::SmiType()), kSmiCid);
3458 if (kind == MethodRecognizer::kStringBaseLength) { 3489 if (kind == MethodRecognizer::kStringBaseLength) {
3459 return ReturnDefinition(load); 3490 return ReturnDefinition(load);
3460 } 3491 }
3461 ASSERT(kind == MethodRecognizer::kStringBaseIsEmpty); 3492 ASSERT(kind == MethodRecognizer::kStringBaseIsEmpty);
3462 Value* zero_val = Bind(new(Z) ConstantInstr( 3493 Value* zero_val = Bind(new(Z) ConstantInstr(
3463 Smi::ZoneHandle(Z, Smi::New(0)))); 3494 Smi::ZoneHandle(Z, Smi::New(0))));
3464 Value* load_val = Bind(load); 3495 Value* load_val = Bind(load);
3465 StrictCompareInstr* compare = 3496 StrictCompareInstr* compare =
3466 new(Z) StrictCompareInstr(node->token_pos(), 3497 new(Z) StrictCompareInstr(token_pos,
3467 Token::kEQ_STRICT, 3498 Token::kEQ_STRICT,
3468 load_val, 3499 load_val,
3469 zero_val, 3500 zero_val,
3470 false); // No number check. 3501 false); // No number check.
3471 return ReturnDefinition(compare); 3502 return ReturnDefinition(compare);
3472 } 3503 }
3473 case MethodRecognizer::kGrowableArrayLength: 3504 case MethodRecognizer::kGrowableArrayLength:
3474 case MethodRecognizer::kObjectArrayLength: 3505 case MethodRecognizer::kObjectArrayLength:
3475 case MethodRecognizer::kImmutableArrayLength: 3506 case MethodRecognizer::kImmutableArrayLength:
3476 case MethodRecognizer::kTypedDataLength: { 3507 case MethodRecognizer::kTypedDataLength: {
3477 LoadFieldInstr* load = BuildNativeGetter( 3508 LoadFieldInstr* load = BuildNativeGetter(
3478 node, kind, OffsetForLengthGetter(kind), 3509 node, kind, OffsetForLengthGetter(kind),
3479 Type::ZoneHandle(Z, Type::SmiType()), kSmiCid); 3510 Type::ZoneHandle(Z, Type::SmiType()), kSmiCid);
3480 load->set_is_immutable(kind != MethodRecognizer::kGrowableArrayLength); 3511 load->set_is_immutable(kind != MethodRecognizer::kGrowableArrayLength);
3481 return ReturnDefinition(load); 3512 return ReturnDefinition(load);
3482 } 3513 }
3483 case MethodRecognizer::kClassIDgetID: { 3514 case MethodRecognizer::kClassIDgetID: {
3484 LocalVariable* value_var = 3515 LocalVariable* value_var =
3485 node->scope()->LookupVariable(Symbols::Value(), true); 3516 node->scope()->LookupVariable(Symbols::Value(), true);
3486 Value* value = Bind(new(Z) LoadLocalInstr(*value_var)); 3517 Value* value = Bind(new(Z) LoadLocalInstr(*value_var, token_pos));
3487 LoadClassIdInstr* load = new(Z) LoadClassIdInstr(value); 3518 LoadClassIdInstr* load = new(Z) LoadClassIdInstr(value);
3488 return ReturnDefinition(load); 3519 return ReturnDefinition(load);
3489 } 3520 }
3490 case MethodRecognizer::kGrowableArrayCapacity: { 3521 case MethodRecognizer::kGrowableArrayCapacity: {
3491 Value* receiver = Bind(BuildLoadThisVar(node->scope())); 3522 Value* receiver = Bind(BuildLoadThisVar(node->scope(), token_pos));
3492 LoadFieldInstr* data_load = new(Z) LoadFieldInstr( 3523 LoadFieldInstr* data_load = new(Z) LoadFieldInstr(
3493 receiver, 3524 receiver,
3494 Array::data_offset(), 3525 Array::data_offset(),
3495 Object::dynamic_type(), 3526 Object::dynamic_type(),
3496 node->token_pos()); 3527 node->token_pos());
3497 data_load->set_result_cid(kArrayCid); 3528 data_load->set_result_cid(kArrayCid);
3498 Value* data = Bind(data_load); 3529 Value* data = Bind(data_load);
3499 LoadFieldInstr* length_load = new(Z) LoadFieldInstr( 3530 LoadFieldInstr* length_load = new(Z) LoadFieldInstr(
3500 data, 3531 data,
3501 Array::length_offset(), 3532 Array::length_offset(),
3502 Type::ZoneHandle(Z, Type::SmiType()), 3533 Type::ZoneHandle(Z, Type::SmiType()),
3503 node->token_pos()); 3534 node->token_pos());
3504 length_load->set_result_cid(kSmiCid); 3535 length_load->set_result_cid(kSmiCid);
3505 length_load->set_recognized_kind(MethodRecognizer::kObjectArrayLength); 3536 length_load->set_recognized_kind(MethodRecognizer::kObjectArrayLength);
3506 return ReturnDefinition(length_load); 3537 return ReturnDefinition(length_load);
3507 } 3538 }
3508 case MethodRecognizer::kObjectArrayAllocate: { 3539 case MethodRecognizer::kObjectArrayAllocate: {
3509 LocalVariable* type_args_parameter = 3540 LocalVariable* type_args_parameter =
3510 node->scope()->LookupVariable(Symbols::TypeArgumentsParameter(), 3541 node->scope()->LookupVariable(Symbols::TypeArgumentsParameter(),
3511 true); 3542 true);
3512 Value* element_type = Bind(new(Z) LoadLocalInstr(*type_args_parameter)); 3543 Value* element_type =
3544 Bind(new(Z) LoadLocalInstr(*type_args_parameter, token_pos));
3513 LocalVariable* length_parameter = 3545 LocalVariable* length_parameter =
3514 node->scope()->LookupVariable(Symbols::Length(), true); 3546 node->scope()->LookupVariable(Symbols::Length(), true);
3515 Value* length = Bind(new(Z) LoadLocalInstr(*length_parameter)); 3547 Value* length =
3548 Bind(new(Z) LoadLocalInstr(*length_parameter, token_pos));
3516 CreateArrayInstr* create_array = 3549 CreateArrayInstr* create_array =
3517 new CreateArrayInstr(node->token_pos(), element_type, length); 3550 new CreateArrayInstr(token_pos, element_type, length);
3518 return ReturnDefinition(create_array); 3551 return ReturnDefinition(create_array);
3519 } 3552 }
3520 case MethodRecognizer::kBigint_getDigits: { 3553 case MethodRecognizer::kBigint_getDigits: {
3521 return ReturnDefinition(BuildNativeGetter( 3554 return ReturnDefinition(BuildNativeGetter(
3522 node, kind, Bigint::digits_offset(), 3555 node, kind, Bigint::digits_offset(),
3523 Object::dynamic_type(), 3556 Object::dynamic_type(),
3524 kTypedDataUint32ArrayCid)); 3557 kTypedDataUint32ArrayCid));
3525 } 3558 }
3526 case MethodRecognizer::kBigint_getUsed: { 3559 case MethodRecognizer::kBigint_getUsed: {
3527 return ReturnDefinition(BuildNativeGetter( 3560 return ReturnDefinition(BuildNativeGetter(
(...skipping 92 matching lines...) Expand 10 before | Expand all | Expand 10 after
3620 // If the right hand side is an expression that does not contain 3653 // If the right hand side is an expression that does not contain
3621 // a safe point for the debugger to stop, add an explicit stub 3654 // a safe point for the debugger to stop, add an explicit stub
3622 // call. Exception: don't do this when assigning to or from internal 3655 // call. Exception: don't do this when assigning to or from internal
3623 // variables, or for generated code that has no source position. 3656 // variables, or for generated code that has no source position.
3624 if (FLAG_support_debugger) { 3657 if (FLAG_support_debugger) {
3625 if ((node->value()->IsLiteralNode() || 3658 if ((node->value()->IsLiteralNode() ||
3626 (node->value()->IsLoadLocalNode() && 3659 (node->value()->IsLoadLocalNode() &&
3627 !node->value()->AsLoadLocalNode()->local().IsInternal()) || 3660 !node->value()->AsLoadLocalNode()->local().IsInternal()) ||
3628 node->value()->IsClosureNode()) && 3661 node->value()->IsClosureNode()) &&
3629 !node->local().IsInternal() && 3662 !node->local().IsInternal() &&
3630 (node->token_pos() >= 0)) { 3663 Token::IsDebugPause(node->token_pos())) {
3631 AddInstruction(new(Z) DebugStepCheckInstr( 3664 AddInstruction(new(Z) DebugStepCheckInstr(
3632 node->token_pos(), RawPcDescriptors::kRuntimeCall)); 3665 node->token_pos(), RawPcDescriptors::kRuntimeCall));
3633 } 3666 }
3634 } 3667 }
3635 3668
3636 ValueGraphVisitor for_value(owner()); 3669 ValueGraphVisitor for_value(owner());
3637 node->value()->Visit(&for_value); 3670 node->value()->Visit(&for_value);
3638 Append(for_value); 3671 Append(for_value);
3639 Value* store_value = for_value.value(); 3672 Value* store_value = for_value.value();
3640 if (Isolate::Current()->flags().type_checks()) { 3673 if (Isolate::Current()->flags().type_checks()) {
(...skipping 25 matching lines...) Expand all
3666 load->set_result_cid(node->field().guarded_cid()); 3699 load->set_result_cid(node->field().guarded_cid());
3667 } 3700 }
3668 FlowGraph::AddToGuardedFields(owner()->guarded_fields(), &node->field()); 3701 FlowGraph::AddToGuardedFields(owner()->guarded_fields(), &node->field());
3669 } 3702 }
3670 ReturnDefinition(load); 3703 ReturnDefinition(load);
3671 } 3704 }
3672 3705
3673 3706
3674 void EffectGraphVisitor::VisitStoreInstanceFieldNode( 3707 void EffectGraphVisitor::VisitStoreInstanceFieldNode(
3675 StoreInstanceFieldNode* node) { 3708 StoreInstanceFieldNode* node) {
3709 const intptr_t token_pos = node->token_pos();
3676 ValueGraphVisitor for_instance(owner()); 3710 ValueGraphVisitor for_instance(owner());
3677 node->instance()->Visit(&for_instance); 3711 node->instance()->Visit(&for_instance);
3678 Append(for_instance); 3712 Append(for_instance);
3679 ValueGraphVisitor for_value(owner()); 3713 ValueGraphVisitor for_value(owner());
3680 node->value()->Visit(&for_value); 3714 node->value()->Visit(&for_value);
3681 Append(for_value); 3715 Append(for_value);
3682 Value* store_value = for_value.value(); 3716 Value* store_value = for_value.value();
3683 if (Isolate::Current()->flags().type_checks()) { 3717 if (Isolate::Current()->flags().type_checks()) {
3684 const AbstractType& type = 3718 const AbstractType& type =
3685 AbstractType::ZoneHandle(Z, node->field().type()); 3719 AbstractType::ZoneHandle(Z, node->field().type());
3686 const String& dst_name = String::ZoneHandle(Z, node->field().name()); 3720 const String& dst_name = String::ZoneHandle(Z, node->field().name());
3687 store_value = BuildAssignableValue(node->value()->token_pos(), 3721 store_value = BuildAssignableValue(node->value()->token_pos(),
3688 store_value, 3722 store_value,
3689 type, 3723 type,
3690 dst_name); 3724 dst_name);
3691 } 3725 }
3692 3726
3693 if (FLAG_use_field_guards) { 3727 if (FLAG_use_field_guards) {
3694 store_value = Bind(BuildStoreExprTemp(store_value)); 3728 store_value = Bind(BuildStoreExprTemp(store_value, token_pos));
3695 GuardFieldClassInstr* guard_field_class = 3729 GuardFieldClassInstr* guard_field_class =
3696 new(Z) GuardFieldClassInstr(store_value, 3730 new(Z) GuardFieldClassInstr(store_value,
3697 node->field(), 3731 node->field(),
3698 thread()->GetNextDeoptId()); 3732 thread()->GetNextDeoptId());
3699 AddInstruction(guard_field_class); 3733 AddInstruction(guard_field_class);
3700 store_value = Bind(BuildLoadExprTemp()); 3734 store_value = Bind(BuildLoadExprTemp(token_pos));
3701 GuardFieldLengthInstr* guard_field_length = 3735 GuardFieldLengthInstr* guard_field_length =
3702 new(Z) GuardFieldLengthInstr(store_value, 3736 new(Z) GuardFieldLengthInstr(store_value,
3703 node->field(), 3737 node->field(),
3704 thread()->GetNextDeoptId()); 3738 thread()->GetNextDeoptId());
3705 AddInstruction(guard_field_length); 3739 AddInstruction(guard_field_length);
3706 store_value = Bind(BuildLoadExprTemp()); 3740 store_value = Bind(BuildLoadExprTemp(token_pos));
3707 } 3741 }
3708 StoreInstanceFieldInstr* store = 3742 StoreInstanceFieldInstr* store =
3709 new(Z) StoreInstanceFieldInstr(node->field(), 3743 new(Z) StoreInstanceFieldInstr(node->field(),
3710 for_instance.value(), 3744 for_instance.value(),
3711 store_value, 3745 store_value,
3712 kEmitStoreBarrier, 3746 kEmitStoreBarrier,
3713 node->token_pos()); 3747 token_pos);
3714 // Maybe initializing unboxed store. 3748 // Maybe initializing unboxed store.
3715 store->set_is_potential_unboxed_initialization(true); 3749 store->set_is_potential_unboxed_initialization(true);
3716 ReturnDefinition(store); 3750 ReturnDefinition(store);
3717 } 3751 }
3718 3752
3719 3753
3720 void EffectGraphVisitor::VisitLoadStaticFieldNode(LoadStaticFieldNode* node) { 3754 void EffectGraphVisitor::VisitLoadStaticFieldNode(LoadStaticFieldNode* node) {
3721 const intptr_t token_pos = node->token_pos(); 3755 const intptr_t token_pos = node->token_pos();
3722 if (node->field().is_const()) { 3756 if (node->field().is_const()) {
3723 ASSERT(node->field().StaticValue() != Object::sentinel().raw()); 3757 ASSERT(node->field().StaticValue() != Object::sentinel().raw());
(...skipping 12 matching lines...) Expand all
3736 3770
3737 Definition* EffectGraphVisitor::BuildStoreStaticField( 3771 Definition* EffectGraphVisitor::BuildStoreStaticField(
3738 StoreStaticFieldNode* node, 3772 StoreStaticFieldNode* node,
3739 bool result_is_needed, 3773 bool result_is_needed,
3740 intptr_t token_pos) { 3774 intptr_t token_pos) {
3741 ValueGraphVisitor for_value(owner()); 3775 ValueGraphVisitor for_value(owner());
3742 node->value()->Visit(&for_value); 3776 node->value()->Visit(&for_value);
3743 Append(for_value); 3777 Append(for_value);
3744 Value* store_value = NULL; 3778 Value* store_value = NULL;
3745 if (result_is_needed) { 3779 if (result_is_needed) {
3746 store_value = Bind(BuildStoreExprTemp(for_value.value())); 3780 store_value = Bind(BuildStoreExprTemp(for_value.value(), token_pos));
3747 } else { 3781 } else {
3748 store_value = for_value.value(); 3782 store_value = for_value.value();
3749 } 3783 }
3750 StoreStaticFieldInstr* store = 3784 StoreStaticFieldInstr* store =
3751 new(Z) StoreStaticFieldInstr(node->field(), store_value, token_pos); 3785 new(Z) StoreStaticFieldInstr(node->field(), store_value, token_pos);
3752 3786
3753 if (result_is_needed) { 3787 if (result_is_needed) {
3754 Do(store); 3788 Do(store);
3755 return BuildLoadExprTemp(); 3789 return BuildLoadExprTemp(token_pos);
3756 } else { 3790 } else {
3757 return store; 3791 return store;
3758 } 3792 }
3759 } 3793 }
3760 3794
3761 3795
3762 void EffectGraphVisitor::VisitStoreStaticFieldNode(StoreStaticFieldNode* node) { 3796 void EffectGraphVisitor::VisitStoreStaticFieldNode(StoreStaticFieldNode* node) {
3763 ReturnDefinition( 3797 ReturnDefinition(
3764 BuildStoreStaticField(node, kResultNotNeeded, node->token_pos())); 3798 BuildStoreStaticField(node, kResultNotNeeded, node->token_pos()));
3765 } 3799 }
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after
3828 owner()->ic_data_array()); 3862 owner()->ic_data_array());
3829 ReturnDefinition(load); 3863 ReturnDefinition(load);
3830 } 3864 }
3831 } 3865 }
3832 3866
3833 3867
3834 Definition* EffectGraphVisitor::BuildStoreIndexedValues( 3868 Definition* EffectGraphVisitor::BuildStoreIndexedValues(
3835 StoreIndexedNode* node, 3869 StoreIndexedNode* node,
3836 bool result_is_needed) { 3870 bool result_is_needed) {
3837 Function* super_function = NULL; 3871 Function* super_function = NULL;
3872 const intptr_t token_pos = node->token_pos();
3838 if (node->IsSuperStore()) { 3873 if (node->IsSuperStore()) {
3839 // Resolve the store indexed operator in the super class. 3874 // Resolve the store indexed operator in the super class.
3840 super_function = &Function::ZoneHandle( 3875 super_function = &Function::ZoneHandle(
3841 Z, Resolver::ResolveDynamicAnyArgs(node->super_class(), 3876 Z, Resolver::ResolveDynamicAnyArgs(node->super_class(),
3842 Symbols::AssignIndexToken())); 3877 Symbols::AssignIndexToken()));
3843 if (super_function->IsNull()) { 3878 if (super_function->IsNull()) {
3844 // Could not resolve super operator. Generate call noSuchMethod() of the 3879 // Could not resolve super operator. Generate call noSuchMethod() of the
3845 // super class instead. 3880 // super class instead.
3846 ArgumentListNode* arguments = new(Z) ArgumentListNode(node->token_pos()); 3881 ArgumentListNode* arguments = new(Z) ArgumentListNode(token_pos);
3847 arguments->Add(node->array()); 3882 arguments->Add(node->array());
3848 arguments->Add(node->index_expr()); 3883 arguments->Add(node->index_expr());
3849 arguments->Add(node->value()); 3884 arguments->Add(node->value());
3850 StaticCallInstr* call = BuildStaticNoSuchMethodCall( 3885 StaticCallInstr* call = BuildStaticNoSuchMethodCall(
3851 node->super_class(), 3886 node->super_class(),
3852 node->array(), 3887 node->array(),
3853 Symbols::AssignIndexToken(), 3888 Symbols::AssignIndexToken(),
3854 arguments, 3889 arguments,
3855 result_is_needed, // Save last arg if result is needed. 3890 result_is_needed, // Save last arg if result is needed.
3856 true); // Super invocation. 3891 true); // Super invocation.
3857 if (result_is_needed) { 3892 if (result_is_needed) {
3858 Do(call); 3893 Do(call);
3859 // BuildStaticNoSuchMethodCall stores the value in expression_temp. 3894 // BuildStaticNoSuchMethodCall stores the value in expression_temp.
3860 return BuildLoadExprTemp(); 3895 return BuildLoadExprTemp(token_pos);
3861 } else { 3896 } else {
3862 return call; 3897 return call;
3863 } 3898 }
3864 } 3899 }
3865 } 3900 }
3866 3901
3867 ZoneGrowableArray<PushArgumentInstr*>* arguments = 3902 ZoneGrowableArray<PushArgumentInstr*>* arguments =
3868 new(Z) ZoneGrowableArray<PushArgumentInstr*>(3); 3903 new(Z) ZoneGrowableArray<PushArgumentInstr*>(3);
3869 ValueGraphVisitor for_array(owner()); 3904 ValueGraphVisitor for_array(owner());
3870 node->array()->Visit(&for_array); 3905 node->array()->Visit(&for_array);
3871 Append(for_array); 3906 Append(for_array);
3872 arguments->Add(PushArgument(for_array.value())); 3907 arguments->Add(PushArgument(for_array.value()));
3873 3908
3874 ValueGraphVisitor for_index(owner()); 3909 ValueGraphVisitor for_index(owner());
3875 node->index_expr()->Visit(&for_index); 3910 node->index_expr()->Visit(&for_index);
3876 Append(for_index); 3911 Append(for_index);
3877 arguments->Add(PushArgument(for_index.value())); 3912 arguments->Add(PushArgument(for_index.value()));
3878 3913
3879 ValueGraphVisitor for_value(owner()); 3914 ValueGraphVisitor for_value(owner());
3880 node->value()->Visit(&for_value); 3915 node->value()->Visit(&for_value);
3881 Append(for_value); 3916 Append(for_value);
3882 Value* value = NULL; 3917 Value* value = NULL;
3883 if (result_is_needed) { 3918 if (result_is_needed) {
3884 value = Bind(BuildStoreExprTemp(for_value.value())); 3919 value = Bind(BuildStoreExprTemp(for_value.value(), token_pos));
3885 } else { 3920 } else {
3886 value = for_value.value(); 3921 value = for_value.value();
3887 } 3922 }
3888 arguments->Add(PushArgument(value)); 3923 arguments->Add(PushArgument(value));
3889 3924
3890 if (super_function != NULL) { 3925 if (super_function != NULL) {
3891 // Generate static call to super operator []=. 3926 // Generate static call to super operator []=.
3892 3927
3893 StaticCallInstr* store = 3928 StaticCallInstr* store =
3894 new(Z) StaticCallInstr(node->token_pos(), 3929 new(Z) StaticCallInstr(token_pos,
3895 *super_function, 3930 *super_function,
3896 Object::null_array(), 3931 Object::null_array(),
3897 arguments, 3932 arguments,
3898 owner()->ic_data_array()); 3933 owner()->ic_data_array());
3899 if (result_is_needed) { 3934 if (result_is_needed) {
3900 Do(store); 3935 Do(store);
3901 return BuildLoadExprTemp(); 3936 return BuildLoadExprTemp(token_pos);
3902 } else { 3937 } else {
3903 return store; 3938 return store;
3904 } 3939 }
3905 } else { 3940 } else {
3906 // Generate dynamic call to operator []=. 3941 // Generate dynamic call to operator []=.
3907 const intptr_t checked_argument_count = 2; // Do not check for value type. 3942 const intptr_t checked_argument_count = 2; // Do not check for value type.
3908 const String& name = 3943 const String& name =
3909 String::ZoneHandle(Z, Symbols::New(Token::Str(Token::kASSIGN_INDEX))); 3944 String::ZoneHandle(Z, Symbols::New(Token::Str(Token::kASSIGN_INDEX)));
3910 InstanceCallInstr* store = 3945 InstanceCallInstr* store =
3911 new(Z) InstanceCallInstr(node->token_pos(), 3946 new(Z) InstanceCallInstr(token_pos,
3912 name, 3947 name,
3913 Token::kASSIGN_INDEX, 3948 Token::kASSIGN_INDEX,
3914 arguments, 3949 arguments,
3915 Object::null_array(), 3950 Object::null_array(),
3916 checked_argument_count, 3951 checked_argument_count,
3917 owner()->ic_data_array()); 3952 owner()->ic_data_array());
3918 if (result_is_needed) { 3953 if (result_is_needed) {
3919 Do(store); 3954 Do(store);
3920 return BuildLoadExprTemp(); 3955 return BuildLoadExprTemp(token_pos);
3921 } else { 3956 } else {
3922 return store; 3957 return store;
3923 } 3958 }
3924 } 3959 }
3925 } 3960 }
3926 3961
3927 3962
3928 void EffectGraphVisitor::VisitStoreIndexedNode(StoreIndexedNode* node) { 3963 void EffectGraphVisitor::VisitStoreIndexedNode(StoreIndexedNode* node) {
3929 ReturnDefinition(BuildStoreIndexedValues(node, kResultNotNeeded)); 3964 ReturnDefinition(BuildStoreIndexedValues(node, kResultNotNeeded));
3930 } 3965 }
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
4001 ASSERT((node->label() == NULL) || !is_top_level_sequence); 4036 ASSERT((node->label() == NULL) || !is_top_level_sequence);
4002 NestedBlock nested_block(owner(), node); 4037 NestedBlock nested_block(owner(), node);
4003 4038
4004 if (num_context_variables > 0) { 4039 if (num_context_variables > 0) {
4005 // The local scope declares variables that are captured. 4040 // The local scope declares variables that are captured.
4006 // Allocate and chain a new context (Except don't chain when at the function 4041 // Allocate and chain a new context (Except don't chain when at the function
4007 // entry if the function does not capture any variables from outer scopes). 4042 // entry if the function does not capture any variables from outer scopes).
4008 Value* allocated_context = 4043 Value* allocated_context =
4009 Bind(new(Z) AllocateContextInstr(node->token_pos(), 4044 Bind(new(Z) AllocateContextInstr(node->token_pos(),
4010 num_context_variables)); 4045 num_context_variables));
4011 { LocalVariable* tmp_var = EnterTempLocalScope(allocated_context); 4046 { LocalVariable* tmp_var =
4047 EnterTempLocalScope(allocated_context, node->token_pos());
4012 if (!is_top_level_sequence || HasContextScope()) { 4048 if (!is_top_level_sequence || HasContextScope()) {
4013 ASSERT(is_top_level_sequence || 4049 ASSERT(is_top_level_sequence ||
4014 (nested_block.ContextLevel() == 4050 (nested_block.ContextLevel() ==
4015 nested_block.outer()->ContextLevel() + 1)); 4051 nested_block.outer()->ContextLevel() + 1));
4016 Value* tmp_val = Bind( 4052 Value* tmp_val = Bind(
4017 new(Z) LoadLocalInstr(*tmp_var, node->token_pos())); 4053 new(Z) LoadLocalInstr(*tmp_var, node->token_pos()));
4018 Value* parent_context = Bind(BuildCurrentContext(node->token_pos())); 4054 Value* parent_context = Bind(BuildCurrentContext(node->token_pos()));
4019 Do(new(Z) StoreInstanceFieldInstr(Context::parent_offset(), 4055 Do(new(Z) StoreInstanceFieldInstr(Context::parent_offset(),
4020 tmp_val, 4056 tmp_val,
4021 parent_context, 4057 parent_context,
4022 kEmitStoreBarrier, 4058 kEmitStoreBarrier,
4023 node->token_pos())); 4059 node->token_pos()));
4024 } 4060 }
4025 Do(BuildStoreContext( 4061 Do(BuildStoreContext(
4026 Bind(ExitTempLocalScope(tmp_var)), 4062 Bind(ExitTempLocalScope(tmp_var, node->token_pos())),
4027 node->token_pos())); 4063 node->token_pos()));
4028 } 4064 }
4029 4065
4030 // If this node_sequence is the body of the function being compiled, copy 4066 // If this node_sequence is the body of the function being compiled, copy
4031 // the captured parameters from the frame into the context. 4067 // the captured parameters from the frame into the context.
4032 if (is_top_level_sequence) { 4068 if (is_top_level_sequence) {
4033 ASSERT(scope->context_level() == 1); 4069 ASSERT(scope->context_level() == 1);
4034 const int num_params = function.NumParameters(); 4070 const int num_params = function.NumParameters();
4035 int param_frame_index = (num_params == function.num_fixed_parameters()) ? 4071 int param_frame_index = (num_params == function.num_fixed_parameters()) ?
4036 (kParamEndSlotFromFp + num_params) : kFirstLocalSlotFromFp; 4072 (kParamEndSlotFromFp + num_params) : kFirstLocalSlotFromFp;
4037 for (int pos = 0; pos < num_params; param_frame_index--, pos++) { 4073 for (int pos = 0; pos < num_params; param_frame_index--, pos++) {
4038 const LocalVariable& parameter = *scope->VariableAt(pos); 4074 const LocalVariable& parameter = *scope->VariableAt(pos);
4039 ASSERT(parameter.owner() == scope); 4075 ASSERT(parameter.owner() == scope);
4040 if (parameter.is_captured()) { 4076 if (parameter.is_captured()) {
4041 // Create a temporary local describing the original position. 4077 // Create a temporary local describing the original position.
4042 const String& temp_name = Symbols::TempParam(); 4078 const String& temp_name = Symbols::TempParam();
4043 LocalVariable* temp_local = new(Z) LocalVariable( 4079 LocalVariable* temp_local = new(Z) LocalVariable(
4044 Scanner::kNoSourcePos, // Token index. 4080 Token::kNoSourcePos, // Token index.
4045 temp_name, 4081 temp_name,
4046 Object::dynamic_type()); // Type. 4082 Object::dynamic_type()); // Type.
4047 temp_local->set_index(param_frame_index); 4083 temp_local->set_index(param_frame_index);
4048 4084
4049 // Mark this local as captured parameter so that the optimizer 4085 // Mark this local as captured parameter so that the optimizer
4050 // correctly handles these when compiling try-catch: Captured 4086 // correctly handles these when compiling try-catch: Captured
4051 // parameters are not in the stack environment, therefore they 4087 // parameters are not in the stack environment, therefore they
4052 // must be skipped when emitting sync-code in try-blocks. 4088 // must be skipped when emitting sync-code in try-blocks.
4053 temp_local->set_is_captured_parameter(true); 4089 temp_local->set_is_captured_parameter(true);
4054 4090
4055 // Copy parameter from local frame to current context. 4091 // Copy parameter from local frame to current context.
4056 Value* load = Bind(BuildLoadLocal(*temp_local)); 4092 Value* load = Bind(BuildLoadLocal(*temp_local, node->token_pos()));
4057 Do(BuildStoreLocal(parameter, load)); 4093 Do(BuildStoreLocal(parameter, load, ST(node->token_pos())));
4058 // Write NULL to the source location to detect buggy accesses and 4094 // Write NULL to the source location to detect buggy accesses and
4059 // allow GC of passed value if it gets overwritten by a new value in 4095 // allow GC of passed value if it gets overwritten by a new value in
4060 // the function. 4096 // the function.
4061 Value* null_constant = Bind(new(Z) ConstantInstr( 4097 Value* null_constant = Bind(new(Z) ConstantInstr(
4062 Object::ZoneHandle(Z, Object::null()))); 4098 Object::ZoneHandle(Z, Object::null())));
4063 Do(BuildStoreLocal(*temp_local, null_constant)); 4099 Do(BuildStoreLocal(*temp_local,
4100 null_constant,
4101 ST(node->token_pos())));
4064 } 4102 }
4065 } 4103 }
4066 } 4104 }
4067 } 4105 }
4068 4106
4069 if (FLAG_support_debugger && 4107 if (FLAG_support_debugger &&
4070 is_top_level_sequence && 4108 is_top_level_sequence &&
4071 function.is_debuggable()) { 4109 function.is_debuggable()) {
4072 // Place a debug check at method entry to ensure breaking on a method always 4110 // Place a debug check at method entry to ensure breaking on a method always
4073 // happens, even if there are no assignments/calls/runtimecalls in the first 4111 // happens, even if there are no assignments/calls/runtimecalls in the first
4074 // basic block. Place this check at the last parameter to ensure parameters 4112 // basic block. Place this check at the last parameter to ensure parameters
4075 // are in scope in the debugger at method entry. 4113 // are in scope in the debugger at method entry.
4076 const int num_params = function.NumParameters(); 4114 const int num_params = function.NumParameters();
4077 intptr_t check_pos = Scanner::kNoSourcePos; 4115 intptr_t check_pos = Token::kNoSourcePos;
4078 if (num_params > 0) { 4116 if (num_params > 0) {
4079 const LocalVariable& parameter = *scope->VariableAt(num_params - 1); 4117 const LocalVariable& parameter = *scope->VariableAt(num_params - 1);
4080 check_pos = parameter.token_pos(); 4118 check_pos = parameter.token_pos();
4081 } 4119 }
4082 if (check_pos < 0) { 4120 if (!Token::IsDebugPause(check_pos)) {
4083 // No parameters or synthetic parameters. 4121 // No parameters or synthetic parameters.
4084 check_pos = node->token_pos(); 4122 check_pos = node->token_pos();
4085 ASSERT(check_pos >= 0); 4123 ASSERT(Token::IsDebugPause(check_pos));
4086 } 4124 }
4087 AddInstruction(new(Z) DebugStepCheckInstr(check_pos, 4125 AddInstruction(new(Z) DebugStepCheckInstr(check_pos,
4088 RawPcDescriptors::kRuntimeCall)); 4126 RawPcDescriptors::kRuntimeCall));
4089 } 4127 }
4090 4128
4091 // This check may be deleted if the generated code is leaf. 4129 // This check may be deleted if the generated code is leaf.
4092 // Native functions don't need a stack check at entry. 4130 // Native functions don't need a stack check at entry.
4093 if (is_top_level_sequence && !function.is_native()) { 4131 if (is_top_level_sequence && !function.is_native()) {
4094 // Always allocate CheckOverflowInstr so that deopt-ids match regardless 4132 // Always allocate CheckOverflowInstr so that deopt-ids match regardless
4095 // if we inline or not. 4133 // if we inline or not.
(...skipping 19 matching lines...) Expand all
4115 // Skip type checking of receiver for instance functions and constructors. 4153 // Skip type checking of receiver for instance functions and constructors.
4116 pos = 1; 4154 pos = 1;
4117 } 4155 }
4118 while (pos < num_params) { 4156 while (pos < num_params) {
4119 const LocalVariable& parameter = *scope->VariableAt(pos); 4157 const LocalVariable& parameter = *scope->VariableAt(pos);
4120 ASSERT(parameter.owner() == scope); 4158 ASSERT(parameter.owner() == scope);
4121 if (!CanSkipTypeCheck(parameter.token_pos(), 4159 if (!CanSkipTypeCheck(parameter.token_pos(),
4122 NULL, 4160 NULL,
4123 parameter.type(), 4161 parameter.type(),
4124 parameter.name())) { 4162 parameter.name())) {
4125 Value* parameter_value = Bind(BuildLoadLocal(parameter)); 4163 Value* parameter_value =
4164 Bind(BuildLoadLocal(parameter, parameter.token_pos()));
4126 Do(BuildAssertAssignable(parameter.token_pos(), 4165 Do(BuildAssertAssignable(parameter.token_pos(),
4127 parameter_value, 4166 parameter_value,
4128 parameter.type(), 4167 parameter.type(),
4129 parameter.name())); 4168 parameter.name()));
4130 } 4169 }
4131 pos++; 4170 pos++;
4132 } 4171 }
4133 } 4172 }
4134 4173
4135 // Continuation part: 4174 // Continuation part:
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
4174 LocalScope* top_scope = node->scope(); 4213 LocalScope* top_scope = node->scope();
4175 LocalVariable* jump_var = top_scope->LookupVariable( 4214 LocalVariable* jump_var = top_scope->LookupVariable(
4176 Symbols::AwaitJumpVar(), false); 4215 Symbols::AwaitJumpVar(), false);
4177 ASSERT(jump_var != NULL && jump_var->is_captured()); 4216 ASSERT(jump_var != NULL && jump_var->is_captured());
4178 Instruction* saved_entry = entry_; 4217 Instruction* saved_entry = entry_;
4179 Instruction* saved_exit = exit_; 4218 Instruction* saved_exit = exit_;
4180 entry_ = NULL; 4219 entry_ = NULL;
4181 exit_ = NULL; 4220 exit_ = NULL;
4182 4221
4183 LoadLocalNode* load_jump_count = 4222 LoadLocalNode* load_jump_count =
4184 new(Z) LoadLocalNode(Scanner::kNoSourcePos, jump_var); 4223 new(Z) LoadLocalNode(node->token_pos(), jump_var);
4185 ComparisonNode* check_jump_count; 4224 ComparisonNode* check_jump_count;
4186 const intptr_t num_await_states = owner()->await_joins()->length(); 4225 const intptr_t num_await_states = owner()->await_joins()->length();
4187 4226
4188 LocalVariable* old_context = top_scope->LookupVariable( 4227 LocalVariable* old_context = top_scope->LookupVariable(
4189 Symbols::AwaitContextVar(), false); 4228 Symbols::AwaitContextVar(), false);
4190 for (intptr_t i = 0; i < num_await_states; i++) { 4229 for (intptr_t i = 0; i < num_await_states; i++) {
4191 check_jump_count = new(Z) ComparisonNode( 4230 check_jump_count = new(Z) ComparisonNode(
4192 Scanner::kNoSourcePos, 4231 ST(node->token_pos()),
4193 Token::kEQ, 4232 Token::kEQ,
4194 load_jump_count, 4233 load_jump_count,
4195 new(Z) LiteralNode( 4234 new(Z) LiteralNode(
4196 Scanner::kNoSourcePos, Smi::ZoneHandle(Z, Smi::New(i)))); 4235 ST(node->token_pos()), Smi::ZoneHandle(Z, Smi::New(i))));
4197 TestGraphVisitor for_test(owner(), Scanner::kNoSourcePos); 4236 TestGraphVisitor for_test(owner(), ST(node->token_pos()));
4198 check_jump_count->Visit(&for_test); 4237 check_jump_count->Visit(&for_test);
4199 EffectGraphVisitor for_true(owner()); 4238 EffectGraphVisitor for_true(owner());
4200 EffectGraphVisitor for_false(owner()); 4239 EffectGraphVisitor for_false(owner());
4201 4240
4202 // Build async jump or sync yield jump. 4241 // Build async jump or sync yield jump.
4203 ASSERT(function.IsAsyncClosure() || 4242 ASSERT(function.IsAsyncClosure() ||
4204 function.IsAsyncGenClosure() || 4243 function.IsAsyncGenClosure() ||
4205 function.IsSyncGenClosure()); 4244 function.IsSyncGenClosure());
4206 4245
4207 // Restore the saved continuation context, i.e. the context that was 4246 // Restore the saved continuation context, i.e. the context that was
4208 // saved into :await_ctx_var before the closure suspended. 4247 // saved into :await_ctx_var before the closure suspended.
4209 for_true.BuildRestoreContext(*old_context, Scanner::kNoSourcePos); 4248 for_true.BuildRestoreContext(*old_context, ST(node->token_pos()));
4210 4249
4211 // Goto saved join. 4250 // Goto saved join.
4212 for_true.Goto((*owner()->await_joins())[i]); 4251 for_true.Goto((*owner()->await_joins())[i]);
4213 4252
4214 Join(for_test, for_true, for_false); 4253 Join(for_test, for_true, for_false);
4215 if (i == 0) { 4254 if (i == 0) {
4216 // Manually link up the preamble start. 4255 // Manually link up the preamble start.
4217 preamble_start->previous()->set_next(for_test.entry()); 4256 preamble_start->previous()->set_next(for_test.entry());
4218 for_test.entry()->set_previous(preamble_start->previous()); 4257 for_test.entry()->set_previous(preamble_start->previous());
4219 } 4258 }
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
4257 4296
4258 4297
4259 void EffectGraphVisitor::VisitTryCatchNode(TryCatchNode* node) { 4298 void EffectGraphVisitor::VisitTryCatchNode(TryCatchNode* node) {
4260 InlineBailout("EffectGraphVisitor::VisitTryCatchNode (exception)"); 4299 InlineBailout("EffectGraphVisitor::VisitTryCatchNode (exception)");
4261 const intptr_t original_handler_index = owner()->try_index(); 4300 const intptr_t original_handler_index = owner()->try_index();
4262 const intptr_t try_handler_index = node->try_index(); 4301 const intptr_t try_handler_index = node->try_index();
4263 ASSERT(try_handler_index != original_handler_index); 4302 ASSERT(try_handler_index != original_handler_index);
4264 owner()->set_try_index(try_handler_index); 4303 owner()->set_try_index(try_handler_index);
4265 4304
4266 // Preserve current context into local variable ':saved_try_context_var'. 4305 // Preserve current context into local variable ':saved_try_context_var'.
4267 BuildSaveContext(node->context_var(), node->token_pos()); 4306 BuildSaveContext(node->context_var(), ST(node->token_pos()));
4268 4307
4269 EffectGraphVisitor for_try(owner()); 4308 EffectGraphVisitor for_try(owner());
4270 node->try_block()->Visit(&for_try); 4309 node->try_block()->Visit(&for_try);
4271 4310
4272 if (for_try.is_open()) { 4311 if (for_try.is_open()) {
4273 JoinEntryInstr* after_try = 4312 JoinEntryInstr* after_try =
4274 new(Z) JoinEntryInstr(owner()->AllocateBlockId(), 4313 new(Z) JoinEntryInstr(owner()->AllocateBlockId(),
4275 original_handler_index); 4314 original_handler_index);
4276 for_try.Goto(after_try); 4315 for_try.Goto(after_try);
4277 for_try.exit_ = after_try; 4316 for_try.exit_ = after_try;
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
4334 // Create a handler for the code in the catch block, containing the 4373 // Create a handler for the code in the catch block, containing the
4335 // code in the finally block. 4374 // code in the finally block.
4336 owner()->set_try_index(original_handler_index); 4375 owner()->set_try_index(original_handler_index);
4337 EffectGraphVisitor for_finally(owner()); 4376 EffectGraphVisitor for_finally(owner());
4338 for_finally.BuildRestoreContext(catch_block->context_var(), 4377 for_finally.BuildRestoreContext(catch_block->context_var(),
4339 finally_block->token_pos()); 4378 finally_block->token_pos());
4340 4379
4341 node->rethrow_clause()->Visit(&for_finally); 4380 node->rethrow_clause()->Visit(&for_finally);
4342 if (for_finally.is_open()) { 4381 if (for_finally.is_open()) {
4343 // Rethrow the exception. Manually build the graph for rethrow. 4382 // Rethrow the exception. Manually build the graph for rethrow.
4344 Value* exception = for_finally.Bind( 4383 Value* exception = for_finally.Bind(for_finally.BuildLoadLocal(
4345 for_finally.BuildLoadLocal(catch_block->rethrow_exception_var())); 4384 catch_block->rethrow_exception_var(), finally_block->token_pos()));
4346 for_finally.PushArgument(exception); 4385 for_finally.PushArgument(exception);
4347 Value* stacktrace = for_finally.Bind( 4386 Value* stacktrace = for_finally.Bind(for_finally.BuildLoadLocal(
4348 for_finally.BuildLoadLocal(catch_block->rethrow_stacktrace_var())); 4387 catch_block->rethrow_stacktrace_var(), finally_block->token_pos()));
4349 for_finally.PushArgument(stacktrace); 4388 for_finally.PushArgument(stacktrace);
4350 for_finally.AddInstruction( 4389 for_finally.AddInstruction(
4351 new(Z) ReThrowInstr(catch_block->token_pos(), catch_handler_index)); 4390 new(Z) ReThrowInstr(catch_block->token_pos(), catch_handler_index));
4352 for_finally.CloseFragment(); 4391 for_finally.CloseFragment();
4353 } 4392 }
4354 ASSERT(!for_finally.is_open()); 4393 ASSERT(!for_finally.is_open());
4355 4394
4356 const Array& types = Array::ZoneHandle(Z, Array::New(1, Heap::kOld)); 4395 const Array& types = Array::ZoneHandle(Z, Array::New(1, Heap::kOld));
4357 types.SetAt(0, Object::dynamic_type()); 4396 types.SetAt(0, Object::dynamic_type());
4358 CatchBlockEntryInstr* finally_entry = 4397 CatchBlockEntryInstr* finally_entry =
(...skipping 263 matching lines...) Expand 10 before | Expand all | Expand 10 after
4622 Script::Handle(function.script()), 4661 Script::Handle(function.script()),
4623 function.token_pos(), 4662 function.token_pos(),
4624 Report::AtLocation, 4663 Report::AtLocation,
4625 "FlowGraphBuilder Bailout: %s %s", 4664 "FlowGraphBuilder Bailout: %s %s",
4626 String::Handle(function.name()).ToCString(), 4665 String::Handle(function.name()).ToCString(),
4627 reason); 4666 reason);
4628 UNREACHABLE(); 4667 UNREACHABLE();
4629 } 4668 }
4630 4669
4631 } // namespace dart 4670 } // namespace dart
OLDNEW
« no previous file with comments | « runtime/vm/flow_graph_builder.h ('k') | runtime/vm/flow_graph_builder_test.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698