OLD | NEW |
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/intermediate_language.h" | 5 #include "vm/intermediate_language.h" |
6 | 6 |
7 #include "vm/bit_vector.h" | 7 #include "vm/bit_vector.h" |
8 #include "vm/dart_entry.h" | 8 #include "vm/dart_entry.h" |
9 #include "vm/flow_graph_builder.h" | 9 #include "vm/flow_graph_builder.h" |
10 #include "vm/flow_graph_compiler.h" | 10 #include "vm/flow_graph_compiler.h" |
(...skipping 949 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
960 if (HasTryIndex()) { | 960 if (HasTryIndex()) { |
961 compiler->AddExceptionHandler(try_index(), | 961 compiler->AddExceptionHandler(try_index(), |
962 compiler->assembler()->CodeSize()); | 962 compiler->assembler()->CodeSize()); |
963 } | 963 } |
964 } | 964 } |
965 | 965 |
966 | 966 |
967 LocationSummary* StoreInstanceFieldComp::MakeLocationSummary() const { | 967 LocationSummary* StoreInstanceFieldComp::MakeLocationSummary() const { |
968 const intptr_t kNumInputs = 2; | 968 const intptr_t kNumInputs = 2; |
969 const intptr_t num_temps = HasICData() ? 1 : 0; | 969 const intptr_t num_temps = HasICData() ? 1 : 0; |
970 LocationSummary* summary = new LocationSummary(kNumInputs, num_temps); | 970 LocationSummary* summary = |
| 971 new LocationSummary(kNumInputs, num_temps, LocationSummary::kNoCall); |
971 summary->set_in(0, Location::RequiresRegister()); | 972 summary->set_in(0, Location::RequiresRegister()); |
972 summary->set_in(1, Location::RequiresRegister()); | 973 summary->set_in(1, Location::RequiresRegister()); |
973 if (HasICData()) { | 974 if (HasICData()) { |
974 summary->set_temp(0, Location::RequiresRegister()); | 975 summary->set_temp(0, Location::RequiresRegister()); |
975 } | 976 } |
976 return summary; | 977 return summary; |
977 } | 978 } |
978 | 979 |
979 | 980 |
980 void StoreInstanceFieldComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 981 void StoreInstanceFieldComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1031 ASSERT(stack_trace()->IsUse()); | 1032 ASSERT(stack_trace()->IsUse()); |
1032 compiler->GenerateCallRuntime(cid(), | 1033 compiler->GenerateCallRuntime(cid(), |
1033 token_pos(), | 1034 token_pos(), |
1034 try_index(), | 1035 try_index(), |
1035 kReThrowRuntimeEntry); | 1036 kReThrowRuntimeEntry); |
1036 __ int3(); | 1037 __ int3(); |
1037 } | 1038 } |
1038 | 1039 |
1039 | 1040 |
1040 LocationSummary* GotoInstr::MakeLocationSummary() const { | 1041 LocationSummary* GotoInstr::MakeLocationSummary() const { |
1041 return new LocationSummary(0, 0); | 1042 return new LocationSummary(0, 0, LocationSummary::kNoCall); |
1042 } | 1043 } |
1043 | 1044 |
1044 | 1045 |
1045 void GotoInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 1046 void GotoInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
1046 // We can fall through if the successor is the next block in the list. | 1047 // We can fall through if the successor is the next block in the list. |
1047 // Otherwise, we need a jump. | 1048 // Otherwise, we need a jump. |
1048 if (!compiler->IsNextBlock(successor())) { | 1049 if (!compiler->IsNextBlock(successor())) { |
1049 __ jmp(compiler->GetBlockLabel(successor())); | 1050 __ jmp(compiler->GetBlockLabel(successor())); |
1050 } | 1051 } |
1051 } | 1052 } |
(...skipping 28 matching lines...) Expand all Loading... |
1080 // If the next block is the true successor we negate comparison and fall | 1081 // If the next block is the true successor we negate comparison and fall |
1081 // through to it. | 1082 // through to it. |
1082 ASSERT(compiler->IsNextBlock(true_successor())); | 1083 ASSERT(compiler->IsNextBlock(true_successor())); |
1083 Condition false_condition = NegateCondition(true_condition); | 1084 Condition false_condition = NegateCondition(true_condition); |
1084 __ j(false_condition, compiler->GetBlockLabel(false_successor())); | 1085 __ j(false_condition, compiler->GetBlockLabel(false_successor())); |
1085 } | 1086 } |
1086 } | 1087 } |
1087 | 1088 |
1088 | 1089 |
1089 LocationSummary* CurrentContextComp::MakeLocationSummary() const { | 1090 LocationSummary* CurrentContextComp::MakeLocationSummary() const { |
1090 return LocationSummary::Make(0, Location::RequiresRegister()); | 1091 return LocationSummary::Make(0, |
| 1092 Location::RequiresRegister(), |
| 1093 LocationSummary::kNoCall); |
1091 } | 1094 } |
1092 | 1095 |
1093 | 1096 |
1094 void CurrentContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 1097 void CurrentContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
1095 __ MoveRegister(locs()->out().reg(), CTX); | 1098 __ MoveRegister(locs()->out().reg(), CTX); |
1096 } | 1099 } |
1097 | 1100 |
1098 | 1101 |
1099 LocationSummary* StoreContextComp::MakeLocationSummary() const { | 1102 LocationSummary* StoreContextComp::MakeLocationSummary() const { |
1100 const intptr_t kNumInputs = 1; | 1103 const intptr_t kNumInputs = 1; |
1101 const intptr_t kNumTemps = 0; | 1104 const intptr_t kNumTemps = 0; |
1102 LocationSummary* summary = new LocationSummary(kNumInputs, kNumTemps); | 1105 LocationSummary* summary = |
| 1106 new LocationSummary(kNumInputs, kNumTemps, LocationSummary::kNoCall); |
1103 summary->set_in(0, Location::RegisterLocation(CTX)); | 1107 summary->set_in(0, Location::RegisterLocation(CTX)); |
1104 return summary; | 1108 return summary; |
1105 } | 1109 } |
1106 | 1110 |
1107 | 1111 |
1108 void StoreContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 1112 void StoreContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
1109 // Nothing to do. Context register were loaded by register allocator. | 1113 // Nothing to do. Context register were loaded by register allocator. |
1110 ASSERT(locs()->in(0).reg() == CTX); | 1114 ASSERT(locs()->in(0).reg() == CTX); |
1111 } | 1115 } |
1112 | 1116 |
1113 | 1117 |
1114 LocationSummary* StrictCompareComp::MakeLocationSummary() const { | 1118 LocationSummary* StrictCompareComp::MakeLocationSummary() const { |
1115 return LocationSummary::Make(2, Location::SameAsFirstInput()); | 1119 return LocationSummary::Make(2, |
| 1120 Location::SameAsFirstInput(), |
| 1121 LocationSummary::kNoCall); |
1116 } | 1122 } |
1117 | 1123 |
1118 | 1124 |
1119 void StrictCompareComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 1125 void StrictCompareComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
1120 Register left = locs()->in(0).reg(); | 1126 Register left = locs()->in(0).reg(); |
1121 Register right = locs()->in(1).reg(); | 1127 Register right = locs()->in(1).reg(); |
1122 | 1128 |
1123 ASSERT(kind() == Token::kEQ_STRICT || kind() == Token::kNE_STRICT); | 1129 ASSERT(kind() == Token::kEQ_STRICT || kind() == Token::kNE_STRICT); |
1124 Condition true_condition = (kind() == Token::kEQ_STRICT) ? EQUAL : NOT_EQUAL; | 1130 Condition true_condition = (kind() == Token::kEQ_STRICT) ? EQUAL : NOT_EQUAL; |
1125 __ CompareRegisters(left, right); | 1131 __ CompareRegisters(left, right); |
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1209 compiler->GenerateAssertAssignable(cid(), | 1215 compiler->GenerateAssertAssignable(cid(), |
1210 token_pos(), | 1216 token_pos(), |
1211 try_index(), | 1217 try_index(), |
1212 dst_type(), | 1218 dst_type(), |
1213 dst_name()); | 1219 dst_name()); |
1214 ASSERT(locs()->in(0).reg() == locs()->out().reg()); | 1220 ASSERT(locs()->in(0).reg() == locs()->out().reg()); |
1215 } | 1221 } |
1216 | 1222 |
1217 | 1223 |
1218 LocationSummary* StoreStaticFieldComp::MakeLocationSummary() const { | 1224 LocationSummary* StoreStaticFieldComp::MakeLocationSummary() const { |
1219 LocationSummary* locs = new LocationSummary(1, 1); | 1225 LocationSummary* locs = new LocationSummary(1, 1, LocationSummary::kNoCall); |
1220 locs->set_in(0, Location::RequiresRegister()); | 1226 locs->set_in(0, Location::RequiresRegister()); |
1221 locs->set_temp(0, Location::RequiresRegister()); | 1227 locs->set_temp(0, Location::RequiresRegister()); |
1222 locs->set_out(Location::SameAsFirstInput()); | 1228 locs->set_out(Location::SameAsFirstInput()); |
1223 return locs; | 1229 return locs; |
1224 } | 1230 } |
1225 | 1231 |
1226 | 1232 |
1227 void StoreStaticFieldComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 1233 void StoreStaticFieldComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
1228 Register value = locs()->in(0).reg(); | 1234 Register value = locs()->in(0).reg(); |
1229 Register temp = locs()->temp(0).reg(); | 1235 Register temp = locs()->temp(0).reg(); |
1230 ASSERT(locs()->out().reg() == value); | 1236 ASSERT(locs()->out().reg() == value); |
1231 | 1237 |
1232 __ LoadObject(temp, field()); | 1238 __ LoadObject(temp, field()); |
1233 __ StoreIntoObject(temp, FieldAddress(temp, Field::value_offset()), value); | 1239 __ StoreIntoObject(temp, FieldAddress(temp, Field::value_offset()), value); |
1234 } | 1240 } |
1235 | 1241 |
1236 | 1242 |
1237 LocationSummary* BooleanNegateComp::MakeLocationSummary() const { | 1243 LocationSummary* BooleanNegateComp::MakeLocationSummary() const { |
1238 return LocationSummary::Make(1, Location::RequiresRegister()); | 1244 return LocationSummary::Make(1, |
| 1245 Location::RequiresRegister(), |
| 1246 LocationSummary::kNoCall); |
1239 } | 1247 } |
1240 | 1248 |
1241 | 1249 |
1242 void BooleanNegateComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 1250 void BooleanNegateComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
1243 Register value = locs()->in(0).reg(); | 1251 Register value = locs()->in(0).reg(); |
1244 Register result = locs()->out().reg(); | 1252 Register result = locs()->out().reg(); |
1245 | 1253 |
1246 Label done; | 1254 Label done; |
1247 __ LoadObject(result, compiler->bool_true()); | 1255 __ LoadObject(result, compiler->bool_true()); |
1248 __ CompareRegisters(result, value); | 1256 __ CompareRegisters(result, value); |
1249 __ j(NOT_EQUAL, &done, Assembler::kNearJump); | 1257 __ j(NOT_EQUAL, &done, Assembler::kNearJump); |
1250 __ LoadObject(result, compiler->bool_false()); | 1258 __ LoadObject(result, compiler->bool_false()); |
1251 __ Bind(&done); | 1259 __ Bind(&done); |
1252 } | 1260 } |
1253 | 1261 |
1254 | 1262 |
1255 LocationSummary* ChainContextComp::MakeLocationSummary() const { | 1263 LocationSummary* ChainContextComp::MakeLocationSummary() const { |
1256 return LocationSummary::Make(1, Location::NoLocation()); | 1264 return LocationSummary::Make(1, |
| 1265 Location::NoLocation(), |
| 1266 LocationSummary::kNoCall); |
1257 } | 1267 } |
1258 | 1268 |
1259 | 1269 |
1260 void ChainContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 1270 void ChainContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
1261 Register context_value = locs()->in(0).reg(); | 1271 Register context_value = locs()->in(0).reg(); |
1262 | 1272 |
1263 // Chain the new context in context_value to its parent in CTX. | 1273 // Chain the new context in context_value to its parent in CTX. |
1264 __ StoreIntoObject(context_value, | 1274 __ StoreIntoObject(context_value, |
1265 FieldAddress(context_value, Context::parent_offset()), | 1275 FieldAddress(context_value, Context::parent_offset()), |
1266 CTX); | 1276 CTX); |
1267 // Set new context as current context. | 1277 // Set new context as current context. |
1268 __ MoveRegister(CTX, context_value); | 1278 __ MoveRegister(CTX, context_value); |
1269 } | 1279 } |
1270 | 1280 |
1271 | 1281 |
1272 LocationSummary* StoreVMFieldComp::MakeLocationSummary() const { | 1282 LocationSummary* StoreVMFieldComp::MakeLocationSummary() const { |
1273 return LocationSummary::Make(2, Location::SameAsFirstInput()); | 1283 return LocationSummary::Make(2, |
| 1284 Location::SameAsFirstInput(), |
| 1285 LocationSummary::kNoCall); |
1274 } | 1286 } |
1275 | 1287 |
1276 | 1288 |
1277 void StoreVMFieldComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 1289 void StoreVMFieldComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
1278 Register value_reg = locs()->in(0).reg(); | 1290 Register value_reg = locs()->in(0).reg(); |
1279 Register dest_reg = locs()->in(1).reg(); | 1291 Register dest_reg = locs()->in(1).reg(); |
1280 ASSERT(value_reg == locs()->out().reg()); | 1292 ASSERT(value_reg == locs()->out().reg()); |
1281 | 1293 |
1282 __ StoreIntoObject(dest_reg, FieldAddress(dest_reg, offset_in_bytes()), | 1294 __ StoreIntoObject(dest_reg, FieldAddress(dest_reg, offset_in_bytes()), |
1283 value_reg); | 1295 value_reg); |
(...skipping 29 matching lines...) Expand all Loading... |
1313 const ExternalLabel label(closure_function.ToCString(), stub.EntryPoint()); | 1325 const ExternalLabel label(closure_function.ToCString(), stub.EntryPoint()); |
1314 compiler->GenerateCall(token_pos(), try_index(), &label, | 1326 compiler->GenerateCall(token_pos(), try_index(), &label, |
1315 PcDescriptors::kOther); | 1327 PcDescriptors::kOther); |
1316 __ Drop(2); // Discard type arguments and receiver. | 1328 __ Drop(2); // Discard type arguments and receiver. |
1317 } | 1329 } |
1318 | 1330 |
1319 | 1331 |
1320 LocationSummary* PushArgumentInstr::MakeLocationSummary() const { | 1332 LocationSummary* PushArgumentInstr::MakeLocationSummary() const { |
1321 const intptr_t kNumInputs = 1; | 1333 const intptr_t kNumInputs = 1; |
1322 const intptr_t kNumTemps= 0; | 1334 const intptr_t kNumTemps= 0; |
1323 LocationSummary* locs = new LocationSummary(kNumInputs, kNumTemps); | 1335 LocationSummary* locs = |
| 1336 new LocationSummary(kNumInputs, kNumTemps, LocationSummary::kNoCall); |
1324 // TODO(fschneider): Use Any() once it is supported by all code generators. | 1337 // TODO(fschneider): Use Any() once it is supported by all code generators. |
1325 locs->set_in(0, Location::RequiresRegister()); | 1338 locs->set_in(0, Location::RequiresRegister()); |
1326 return locs; | 1339 return locs; |
1327 } | 1340 } |
1328 | 1341 |
1329 | 1342 |
1330 void PushArgumentInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 1343 void PushArgumentInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
1331 // In SSA mode, we need an explicit push. Nothing to do in non-SSA mode | 1344 // In SSA mode, we need an explicit push. Nothing to do in non-SSA mode |
1332 // where PushArgument is handled in FrameRegisterAllocator::AllocateRegisters. | 1345 // where PushArgument is handled in FrameRegisterAllocator::AllocateRegisters. |
1333 // Instead of popping the value it is left alone on the simulated frame | 1346 // Instead of popping the value it is left alone on the simulated frame |
1334 // and materialized on the physical stack before the call. | 1347 // and materialized on the physical stack before the call. |
1335 // TODO(fschneider): Avoid special-casing for SSA mode here. | 1348 // TODO(fschneider): Avoid special-casing for SSA mode here. |
1336 if (compiler->is_ssa()) { | 1349 if (compiler->is_ssa()) { |
1337 ASSERT(locs()->in(0).IsRegister()); | 1350 ASSERT(locs()->in(0).IsRegister()); |
1338 __ PushRegister(locs()->in(0).reg()); | 1351 __ PushRegister(locs()->in(0).reg()); |
1339 } | 1352 } |
1340 } | 1353 } |
1341 | 1354 |
1342 | 1355 |
1343 #undef __ | 1356 #undef __ |
1344 | 1357 |
1345 } // namespace dart | 1358 } // namespace dart |
OLD | NEW |