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 | 4 |
5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_XXX. | 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_XXX. |
6 | 6 |
7 #include "vm/flow_graph_compiler.h" | 7 #include "vm/flow_graph_compiler.h" |
8 | 8 |
9 #include "vm/cha.h" | 9 #include "vm/cha.h" |
10 #include "vm/dart_entry.h" | 10 #include "vm/dart_entry.h" |
(...skipping 13 matching lines...) Expand all Loading... |
24 namespace dart { | 24 namespace dart { |
25 | 25 |
26 DECLARE_FLAG(bool, code_comments); | 26 DECLARE_FLAG(bool, code_comments); |
27 DECLARE_FLAG(bool, enable_type_checks); | 27 DECLARE_FLAG(bool, enable_type_checks); |
28 DECLARE_FLAG(bool, intrinsify); | 28 DECLARE_FLAG(bool, intrinsify); |
29 DECLARE_FLAG(bool, propagate_ic_data); | 29 DECLARE_FLAG(bool, propagate_ic_data); |
30 DECLARE_FLAG(bool, report_usage_count); | 30 DECLARE_FLAG(bool, report_usage_count); |
31 DECLARE_FLAG(int, optimization_counter_threshold); | 31 DECLARE_FLAG(int, optimization_counter_threshold); |
32 DECLARE_FLAG(bool, use_cha); | 32 DECLARE_FLAG(bool, use_cha); |
33 DECLARE_FLAG(bool, use_osr); | 33 DECLARE_FLAG(bool, use_osr); |
34 | 34 DEFINE_FLAG(bool, enable_simd_inline, true, |
| 35 "Enable inlining of SIMD related method calls."); |
35 | 36 |
36 // Assign locations to incoming arguments, i.e., values pushed above spill slots | 37 // Assign locations to incoming arguments, i.e., values pushed above spill slots |
37 // with PushArgument. Recursively allocates from outermost to innermost | 38 // with PushArgument. Recursively allocates from outermost to innermost |
38 // environment. | 39 // environment. |
39 void CompilerDeoptInfo::AllocateIncomingParametersRecursive( | 40 void CompilerDeoptInfo::AllocateIncomingParametersRecursive( |
40 Environment* env, | 41 Environment* env, |
41 intptr_t* stack_height) { | 42 intptr_t* stack_height) { |
42 if (env == NULL) return; | 43 if (env == NULL) return; |
43 AllocateIncomingParametersRecursive(env->outer(), stack_height); | 44 AllocateIncomingParametersRecursive(env->outer(), stack_height); |
44 for (Environment::ShallowIterator it(env); !it.Done(); it.Advance()) { | 45 for (Environment::ShallowIterator it(env); !it.Done(); it.Advance()) { |
(...skipping 403 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
448 pending_deoptimization_env_); | 449 pending_deoptimization_env_); |
449 info->set_pc_offset(assembler()->CodeSize()); | 450 info->set_pc_offset(assembler()->CodeSize()); |
450 deopt_infos_.Add(info); | 451 deopt_infos_.Add(info); |
451 } | 452 } |
452 | 453 |
453 | 454 |
454 // This function must be in sync with FlowGraphCompiler::SaveLiveRegisters | 455 // This function must be in sync with FlowGraphCompiler::SaveLiveRegisters |
455 // and FlowGraphCompiler::SlowPathEnvironmentFor. | 456 // and FlowGraphCompiler::SlowPathEnvironmentFor. |
456 void FlowGraphCompiler::RecordSafepoint(LocationSummary* locs) { | 457 void FlowGraphCompiler::RecordSafepoint(LocationSummary* locs) { |
457 if (is_optimizing()) { | 458 if (is_optimizing()) { |
| 459 RegisterSet* registers = locs->live_registers(); |
| 460 ASSERT(registers != NULL); |
| 461 const intptr_t kFpuRegisterSpillFactor = |
| 462 kFpuRegisterSize / kWordSize; |
| 463 const intptr_t live_registers_size = registers->CpuRegisterCount() + |
| 464 (registers->FpuRegisterCount() * kFpuRegisterSpillFactor); |
458 BitmapBuilder* bitmap = locs->stack_bitmap(); | 465 BitmapBuilder* bitmap = locs->stack_bitmap(); |
459 ASSERT(bitmap != NULL); | 466 ASSERT(bitmap != NULL); |
460 ASSERT(bitmap->Length() <= StackSize()); | 467 // An instruction may have two safepoints in deferred code. The |
461 // Pad the bitmap out to describe all the spill slots. | 468 // call to RecordSafepoint has the side-effect of appending the live |
| 469 // registers to the bitmap. This is why the second call to RecordSafepoint |
| 470 // with the same instruction (and same location summary) sees a bitmap that |
| 471 // is larger that StackSize(). It will never be larger than StackSize() + |
| 472 // live_registers_size. |
| 473 ASSERT(bitmap->Length() <= (StackSize() + live_registers_size)); |
| 474 // The first safepoint will grow the bitmap to be the size of StackSize() |
| 475 // but the second safepoint will truncate the bitmap and append the |
| 476 // live registers to it again. The bitmap produced by both calls will |
| 477 // be the same. |
462 bitmap->SetLength(StackSize()); | 478 bitmap->SetLength(StackSize()); |
463 | 479 |
464 // Mark the bits in the stack map in the same order we push registers in | 480 // Mark the bits in the stack map in the same order we push registers in |
465 // slow path code (see FlowGraphCompiler::SaveLiveRegisters). | 481 // slow path code (see FlowGraphCompiler::SaveLiveRegisters). |
466 // | 482 // |
467 // Slow path code can have registers at the safepoint. | 483 // Slow path code can have registers at the safepoint. |
468 if (!locs->always_calls()) { | 484 if (!locs->always_calls()) { |
469 RegisterSet* regs = locs->live_registers(); | 485 RegisterSet* regs = locs->live_registers(); |
470 if (regs->FpuRegisterCount() > 0) { | 486 if (regs->FpuRegisterCount() > 0) { |
471 // Denote FPU registers with 0 bits in the stackmap. Based on the | 487 // Denote FPU registers with 0 bits in the stackmap. Based on the |
472 // assumption that there are normally few live FPU registers, this | 488 // assumption that there are normally few live FPU registers, this |
473 // encoding is simpler and roughly as compact as storing a separate | 489 // encoding is simpler and roughly as compact as storing a separate |
474 // count of FPU registers. | 490 // count of FPU registers. |
475 // | 491 // |
476 // FPU registers have the highest register number at the highest | 492 // FPU registers have the highest register number at the highest |
477 // address (i.e., first in the stackmap). | 493 // address (i.e., first in the stackmap). |
478 const intptr_t kFpuRegisterSpillFactor = | |
479 kFpuRegisterSize / kWordSize; | |
480 for (intptr_t i = kNumberOfFpuRegisters - 1; i >= 0; --i) { | 494 for (intptr_t i = kNumberOfFpuRegisters - 1; i >= 0; --i) { |
481 FpuRegister reg = static_cast<FpuRegister>(i); | 495 FpuRegister reg = static_cast<FpuRegister>(i); |
482 if (regs->ContainsFpuRegister(reg)) { | 496 if (regs->ContainsFpuRegister(reg)) { |
483 for (intptr_t j = 0; j < kFpuRegisterSpillFactor; ++j) { | 497 for (intptr_t j = 0; j < kFpuRegisterSpillFactor; ++j) { |
484 bitmap->Set(bitmap->Length(), false); | 498 bitmap->Set(bitmap->Length(), false); |
485 } | 499 } |
486 } | 500 } |
487 } | 501 } |
488 } | 502 } |
489 // General purpose registers have the lowest register number at the | 503 // General purpose registers have the lowest register number at the |
(...skipping 776 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1266 | 1280 |
1267 for (int i = 0; i < len; i++) { | 1281 for (int i = 0; i < len; i++) { |
1268 sorted->Add(CidTarget(ic_data.GetReceiverClassIdAt(i), | 1282 sorted->Add(CidTarget(ic_data.GetReceiverClassIdAt(i), |
1269 &Function::ZoneHandle(ic_data.GetTargetAt(i)), | 1283 &Function::ZoneHandle(ic_data.GetTargetAt(i)), |
1270 ic_data.GetCountAt(i))); | 1284 ic_data.GetCountAt(i))); |
1271 } | 1285 } |
1272 sorted->Sort(HighestCountFirst); | 1286 sorted->Sort(HighestCountFirst); |
1273 } | 1287 } |
1274 | 1288 |
1275 } // namespace dart | 1289 } // namespace dart |
OLD | NEW |