| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, 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 #ifndef DART_PRECOMPILED_RUNTIME | 4 #ifndef DART_PRECOMPILED_RUNTIME |
| 5 #include "vm/jit_optimizer.h" | 5 #include "vm/jit_optimizer.h" |
| 6 | 6 |
| 7 #include "vm/bit_vector.h" | 7 #include "vm/bit_vector.h" |
| 8 #include "vm/branch_optimizer.h" | 8 #include "vm/branch_optimizer.h" |
| 9 #include "vm/cha.h" | 9 #include "vm/cha.h" |
| 10 #include "vm/compiler.h" | 10 #include "vm/compiler.h" |
| (...skipping 1241 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1252 if (call->ArgumentCount() == 2) { | 1252 if (call->ArgumentCount() == 2) { |
| 1253 instantiator_type_args = flow_graph()->constant_null(); | 1253 instantiator_type_args = flow_graph()->constant_null(); |
| 1254 function_type_args = flow_graph()->constant_null(); | 1254 function_type_args = flow_graph()->constant_null(); |
| 1255 ASSERT(call->MatchesCoreName(Symbols::_simpleInstanceOf())); | 1255 ASSERT(call->MatchesCoreName(Symbols::_simpleInstanceOf())); |
| 1256 type = AbstractType::Cast(call->ArgumentAt(1)->AsConstant()->value()).raw(); | 1256 type = AbstractType::Cast(call->ArgumentAt(1)->AsConstant()->value()).raw(); |
| 1257 } else { | 1257 } else { |
| 1258 instantiator_type_args = call->ArgumentAt(1); | 1258 instantiator_type_args = call->ArgumentAt(1); |
| 1259 function_type_args = call->ArgumentAt(2); | 1259 function_type_args = call->ArgumentAt(2); |
| 1260 type = AbstractType::Cast(call->ArgumentAt(3)->AsConstant()->value()).raw(); | 1260 type = AbstractType::Cast(call->ArgumentAt(3)->AsConstant()->value()).raw(); |
| 1261 } | 1261 } |
| 1262 | |
| 1263 if (TypeCheckAsClassEquality(type)) { | |
| 1264 LoadClassIdInstr* left_cid = new (Z) LoadClassIdInstr(new (Z) Value(left)); | |
| 1265 InsertBefore(call, left_cid, NULL, FlowGraph::kValue); | |
| 1266 const intptr_t type_cid = Class::Handle(Z, type.type_class()).id(); | |
| 1267 ConstantInstr* cid = | |
| 1268 flow_graph()->GetConstant(Smi::Handle(Z, Smi::New(type_cid))); | |
| 1269 | |
| 1270 StrictCompareInstr* check_cid = new (Z) StrictCompareInstr( | |
| 1271 call->token_pos(), Token::kEQ_STRICT, new (Z) Value(left_cid), | |
| 1272 new (Z) Value(cid), /* number_check = */ false, Thread::kNoDeoptId); | |
| 1273 ReplaceCall(call, check_cid); | |
| 1274 return; | |
| 1275 } | |
| 1276 | |
| 1277 const ICData& unary_checks = | 1262 const ICData& unary_checks = |
| 1278 ICData::ZoneHandle(Z, call->ic_data()->AsUnaryClassChecks()); | 1263 ICData::ZoneHandle(Z, call->ic_data()->AsUnaryClassChecks()); |
| 1279 const intptr_t number_of_checks = unary_checks.NumberOfChecks(); | 1264 const intptr_t number_of_checks = unary_checks.NumberOfChecks(); |
| 1280 if ((number_of_checks > 0) && | 1265 if ((number_of_checks > 0) && |
| 1281 (number_of_checks <= FLAG_max_polymorphic_checks)) { | 1266 (number_of_checks <= FLAG_max_polymorphic_checks)) { |
| 1282 ZoneGrowableArray<intptr_t>* results = | 1267 ZoneGrowableArray<intptr_t>* results = |
| 1283 new (Z) ZoneGrowableArray<intptr_t>(number_of_checks * 2); | 1268 new (Z) ZoneGrowableArray<intptr_t>(number_of_checks * 2); |
| 1284 Bool& as_bool = | 1269 Bool& as_bool = |
| 1285 Bool::ZoneHandle(Z, InstanceOfAsBool(unary_checks, type, results)); | 1270 Bool::ZoneHandle(Z, InstanceOfAsBool(unary_checks, type, results)); |
| 1286 if (as_bool.IsNull()) { | 1271 if (as_bool.IsNull()) { |
| (...skipping 17 matching lines...) Expand all Loading... |
| 1304 push->ReplaceUsesWith(push->value()->definition()); | 1289 push->ReplaceUsesWith(push->value()->definition()); |
| 1305 push->RemoveFromGraph(); | 1290 push->RemoveFromGraph(); |
| 1306 } | 1291 } |
| 1307 call->ReplaceUsesWith(bool_const); | 1292 call->ReplaceUsesWith(bool_const); |
| 1308 ASSERT(current_iterator()->Current() == call); | 1293 ASSERT(current_iterator()->Current() == call); |
| 1309 current_iterator()->RemoveCurrentFromGraph(); | 1294 current_iterator()->RemoveCurrentFromGraph(); |
| 1310 return; | 1295 return; |
| 1311 } | 1296 } |
| 1312 } | 1297 } |
| 1313 | 1298 |
| 1299 if (TypeCheckAsClassEquality(type)) { |
| 1300 LoadClassIdInstr* left_cid = new (Z) LoadClassIdInstr(new (Z) Value(left)); |
| 1301 InsertBefore(call, left_cid, NULL, FlowGraph::kValue); |
| 1302 const intptr_t type_cid = Class::Handle(Z, type.type_class()).id(); |
| 1303 ConstantInstr* cid = |
| 1304 flow_graph()->GetConstant(Smi::Handle(Z, Smi::New(type_cid))); |
| 1305 |
| 1306 StrictCompareInstr* check_cid = new (Z) StrictCompareInstr( |
| 1307 call->token_pos(), Token::kEQ_STRICT, new (Z) Value(left_cid), |
| 1308 new (Z) Value(cid), /* number_check = */ false, Thread::kNoDeoptId); |
| 1309 ReplaceCall(call, check_cid); |
| 1310 return; |
| 1311 } |
| 1312 |
| 1314 InstanceOfInstr* instance_of = new (Z) InstanceOfInstr( | 1313 InstanceOfInstr* instance_of = new (Z) InstanceOfInstr( |
| 1315 call->token_pos(), new (Z) Value(left), | 1314 call->token_pos(), new (Z) Value(left), |
| 1316 new (Z) Value(instantiator_type_args), new (Z) Value(function_type_args), | 1315 new (Z) Value(instantiator_type_args), new (Z) Value(function_type_args), |
| 1317 type, call->deopt_id()); | 1316 type, call->deopt_id()); |
| 1318 ReplaceCall(call, instance_of); | 1317 ReplaceCall(call, instance_of); |
| 1319 } | 1318 } |
| 1320 | 1319 |
| 1321 | 1320 |
| 1322 // TODO(srdjan): Apply optimizations as in ReplaceWithInstanceOf (TestCids). | 1321 // TODO(srdjan): Apply optimizations as in ReplaceWithInstanceOf (TestCids). |
| 1323 void JitOptimizer::ReplaceWithTypeCast(InstanceCallInstr* call) { | 1322 void JitOptimizer::ReplaceWithTypeCast(InstanceCallInstr* call) { |
| (...skipping 395 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1719 // Discard the environment from the original instruction because the store | 1718 // Discard the environment from the original instruction because the store |
| 1720 // can't deoptimize. | 1719 // can't deoptimize. |
| 1721 instr->RemoveEnvironment(); | 1720 instr->RemoveEnvironment(); |
| 1722 ReplaceCall(instr, store); | 1721 ReplaceCall(instr, store); |
| 1723 return true; | 1722 return true; |
| 1724 } | 1723 } |
| 1725 | 1724 |
| 1726 | 1725 |
| 1727 } // namespace dart | 1726 } // namespace dart |
| 1728 #endif // DART_PRECOMPILED_RUNTIME | 1727 #endif // DART_PRECOMPILED_RUNTIME |
| OLD | NEW |