OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/compiler/linkage.h" | 5 #include "src/compiler/linkage.h" |
6 #include "src/compiler/register-allocator.h" | 6 #include "src/compiler/register-allocator.h" |
7 #include "src/string-stream.h" | 7 #include "src/string-stream.h" |
8 | 8 |
9 namespace v8 { | 9 namespace v8 { |
10 namespace internal { | 10 namespace internal { |
(...skipping 575 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
586 RegisterAllocator::RegisterAllocator(const RegisterConfiguration* config, | 586 RegisterAllocator::RegisterAllocator(const RegisterConfiguration* config, |
587 Zone* zone, Frame* frame, | 587 Zone* zone, Frame* frame, |
588 InstructionSequence* code, | 588 InstructionSequence* code, |
589 const char* debug_name) | 589 const char* debug_name) |
590 : local_zone_(zone), | 590 : local_zone_(zone), |
591 frame_(frame), | 591 frame_(frame), |
592 code_(code), | 592 code_(code), |
593 debug_name_(debug_name), | 593 debug_name_(debug_name), |
594 config_(config), | 594 config_(config), |
595 operand_cache_(new (code_zone()) InstructionOperandCache()), | 595 operand_cache_(new (code_zone()) InstructionOperandCache()), |
596 phi_map_(PhiMap::key_compare(), PhiMap::allocator_type(local_zone())), | 596 phi_map_(local_zone()), |
597 live_in_sets_(code->InstructionBlockCount(), nullptr, local_zone()), | 597 live_in_sets_(code->InstructionBlockCount(), nullptr, local_zone()), |
598 live_ranges_(code->VirtualRegisterCount() * 2, nullptr, local_zone()), | 598 live_ranges_(code->VirtualRegisterCount() * 2, nullptr, local_zone()), |
599 fixed_live_ranges_(this->config()->num_general_registers(), nullptr, | 599 fixed_live_ranges_(this->config()->num_general_registers(), nullptr, |
600 local_zone()), | 600 local_zone()), |
601 fixed_double_live_ranges_(this->config()->num_double_registers(), nullptr, | 601 fixed_double_live_ranges_(this->config()->num_double_registers(), nullptr, |
602 local_zone()), | 602 local_zone()), |
603 unhandled_live_ranges_(local_zone()), | 603 unhandled_live_ranges_(local_zone()), |
604 active_live_ranges_(local_zone()), | 604 active_live_ranges_(local_zone()), |
605 inactive_live_ranges_(local_zone()), | 605 inactive_live_ranges_(local_zone()), |
606 spill_ranges_(local_zone()), | 606 spill_ranges_(local_zone()), |
(...skipping 758 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1365 nullptr); | 1365 nullptr); |
1366 Define(curr_position, temp, nullptr); | 1366 Define(curr_position, temp, nullptr); |
1367 } | 1367 } |
1368 } | 1368 } |
1369 } | 1369 } |
1370 } | 1370 } |
1371 | 1371 |
1372 | 1372 |
1373 void RegisterAllocator::ResolvePhis(const InstructionBlock* block) { | 1373 void RegisterAllocator::ResolvePhis(const InstructionBlock* block) { |
1374 for (auto phi : block->phis()) { | 1374 for (auto phi : block->phis()) { |
1375 auto res = phi_map_.insert( | 1375 int phi_vreg = phi->virtual_register(); |
1376 std::make_pair(phi->virtual_register(), PhiMapValue(phi, block))); | 1376 auto res = |
| 1377 phi_map_.insert(std::make_pair(phi_vreg, PhiMapValue(phi, block))); |
1377 DCHECK(res.second); | 1378 DCHECK(res.second); |
1378 USE(res); | 1379 USE(res); |
1379 auto output = phi->output(); | 1380 auto& output = phi->output(); |
1380 int phi_vreg = phi->virtual_register(); | |
1381 if (!FLAG_turbo_delay_ssa_decon) { | 1381 if (!FLAG_turbo_delay_ssa_decon) { |
1382 for (size_t i = 0; i < phi->operands().size(); ++i) { | 1382 for (size_t i = 0; i < phi->operands().size(); ++i) { |
1383 InstructionBlock* cur_block = | 1383 InstructionBlock* cur_block = |
1384 code()->InstructionBlockAt(block->predecessors()[i]); | 1384 code()->InstructionBlockAt(block->predecessors()[i]); |
1385 AddGapMove(cur_block->last_instruction_index() - 1, GapInstruction::END, | 1385 AddGapMove(cur_block->last_instruction_index() - 1, GapInstruction::END, |
1386 phi->inputs()[i], output); | 1386 &phi->inputs()[i], &output); |
1387 DCHECK(!InstructionAt(cur_block->last_instruction_index()) | 1387 DCHECK(!InstructionAt(cur_block->last_instruction_index()) |
1388 ->HasPointerMap()); | 1388 ->HasPointerMap()); |
1389 } | 1389 } |
1390 } | 1390 } |
1391 auto live_range = LiveRangeFor(phi_vreg); | 1391 auto live_range = LiveRangeFor(phi_vreg); |
1392 int gap_index = block->first_instruction_index(); | 1392 int gap_index = block->first_instruction_index(); |
1393 live_range->SpillAtDefinition(local_zone(), gap_index, output); | 1393 live_range->SpillAtDefinition(local_zone(), gap_index, &output); |
1394 live_range->SetSpillStartIndex(gap_index); | 1394 live_range->SetSpillStartIndex(gap_index); |
1395 // We use the phi-ness of some nodes in some later heuristics. | 1395 // We use the phi-ness of some nodes in some later heuristics. |
1396 live_range->set_is_phi(true); | 1396 live_range->set_is_phi(true); |
1397 live_range->set_is_non_loop_phi(!block->IsLoopHeader()); | 1397 live_range->set_is_non_loop_phi(!block->IsLoopHeader()); |
1398 } | 1398 } |
1399 } | 1399 } |
1400 | 1400 |
1401 | 1401 |
1402 void RegisterAllocator::MeetRegisterConstraints() { | 1402 void RegisterAllocator::MeetRegisterConstraints() { |
1403 for (auto block : code()->instruction_blocks()) { | 1403 for (auto block : code()->instruction_blocks()) { |
(...skipping 211 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1615 LiveRangeFinder finder(*this); | 1615 LiveRangeFinder finder(*this); |
1616 for (auto block : code()->instruction_blocks()) { | 1616 for (auto block : code()->instruction_blocks()) { |
1617 if (CanEagerlyResolveControlFlow(block)) continue; | 1617 if (CanEagerlyResolveControlFlow(block)) continue; |
1618 if (FLAG_turbo_delay_ssa_decon) { | 1618 if (FLAG_turbo_delay_ssa_decon) { |
1619 // resolve phis | 1619 // resolve phis |
1620 for (auto phi : block->phis()) { | 1620 for (auto phi : block->phis()) { |
1621 auto* block_bound = | 1621 auto* block_bound = |
1622 finder.ArrayFor(phi->virtual_register())->FindSucc(block); | 1622 finder.ArrayFor(phi->virtual_register())->FindSucc(block); |
1623 auto phi_output = | 1623 auto phi_output = |
1624 block_bound->range_->GetAssignedOperand(operand_cache()); | 1624 block_bound->range_->GetAssignedOperand(operand_cache()); |
1625 phi->output()->ConvertTo(phi_output->kind(), phi_output->index()); | 1625 phi->output().ConvertTo(phi_output->kind(), phi_output->index()); |
1626 size_t pred_index = 0; | 1626 size_t pred_index = 0; |
1627 for (auto pred : block->predecessors()) { | 1627 for (auto pred : block->predecessors()) { |
1628 const InstructionBlock* pred_block = code()->InstructionBlockAt(pred); | 1628 const InstructionBlock* pred_block = code()->InstructionBlockAt(pred); |
1629 auto* pred_bound = finder.ArrayFor(phi->operands()[pred_index]) | 1629 auto* pred_bound = finder.ArrayFor(phi->operands()[pred_index]) |
1630 ->FindPred(pred_block); | 1630 ->FindPred(pred_block); |
1631 auto pred_op = | 1631 auto pred_op = |
1632 pred_bound->range_->GetAssignedOperand(operand_cache()); | 1632 pred_bound->range_->GetAssignedOperand(operand_cache()); |
1633 phi->inputs()[pred_index] = pred_op; | 1633 phi->inputs()[pred_index] = *pred_op; |
1634 ResolveControlFlow(block, phi_output, pred_block, pred_op); | 1634 ResolveControlFlow(block, phi_output, pred_block, pred_op); |
1635 pred_index++; | 1635 pred_index++; |
1636 } | 1636 } |
1637 } | 1637 } |
1638 } | 1638 } |
1639 auto live = live_in_sets_[block->rpo_number().ToInt()]; | 1639 auto live = live_in_sets_[block->rpo_number().ToInt()]; |
1640 BitVector::Iterator iterator(live); | 1640 BitVector::Iterator iterator(live); |
1641 while (!iterator.Done()) { | 1641 while (!iterator.Done()) { |
1642 auto* array = finder.ArrayFor(iterator.Current()); | 1642 auto* array = finder.ArrayFor(iterator.Current()); |
1643 for (auto pred : block->predecessors()) { | 1643 for (auto pred : block->predecessors()) { |
(...skipping 860 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2504 } else { | 2504 } else { |
2505 DCHECK(range->Kind() == GENERAL_REGISTERS); | 2505 DCHECK(range->Kind() == GENERAL_REGISTERS); |
2506 assigned_registers_->Add(reg); | 2506 assigned_registers_->Add(reg); |
2507 } | 2507 } |
2508 range->set_assigned_register(reg, operand_cache()); | 2508 range->set_assigned_register(reg, operand_cache()); |
2509 } | 2509 } |
2510 | 2510 |
2511 } // namespace compiler | 2511 } // namespace compiler |
2512 } // namespace internal | 2512 } // namespace internal |
2513 } // namespace v8 | 2513 } // namespace v8 |
OLD | NEW |