• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2016 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "src/compiler/backend/ppc/unwinding-info-writer-ppc.h"
6 #include "src/compiler/backend/instruction.h"
7 
8 namespace v8 {
9 namespace internal {
10 namespace compiler {
BeginInstructionBlock(int pc_offset,const InstructionBlock * block)11 void UnwindingInfoWriter::BeginInstructionBlock(int pc_offset,
12                                                 const InstructionBlock* block) {
13   if (!enabled()) return;
14 
15   block_will_exit_ = false;
16 
17   DCHECK_LT(block->rpo_number().ToInt(),
18             static_cast<int>(block_initial_states_.size()));
19   const BlockInitialState* initial_state =
20       block_initial_states_[block->rpo_number().ToInt()];
21   if (!initial_state) return;
22   if (initial_state->saved_lr_ != saved_lr_) {
23     eh_frame_writer_.AdvanceLocation(pc_offset);
24     if (initial_state->saved_lr_) {
25       eh_frame_writer_.RecordRegisterSavedToStack(kLrDwarfCode,
26                                                   kSystemPointerSize);
27       eh_frame_writer_.RecordRegisterSavedToStack(fp, 0);
28     } else {
29       eh_frame_writer_.RecordRegisterFollowsInitialRule(kLrDwarfCode);
30     }
31     saved_lr_ = initial_state->saved_lr_;
32   }
33 }
34 
EndInstructionBlock(const InstructionBlock * block)35 void UnwindingInfoWriter::EndInstructionBlock(const InstructionBlock* block) {
36   if (!enabled() || block_will_exit_) return;
37 
38   for (const RpoNumber& successor : block->successors()) {
39     int successor_index = successor.ToInt();
40     DCHECK_LT(successor_index, static_cast<int>(block_initial_states_.size()));
41     const BlockInitialState* existing_state =
42         block_initial_states_[successor_index];
43 
44     // If we already had an entry for this BB, check that the values are the
45     // same we are trying to insert.
46     if (existing_state) {
47       DCHECK_EQ(existing_state->saved_lr_, saved_lr_);
48     } else {
49       block_initial_states_[successor_index] =
50           zone_->New<BlockInitialState>(saved_lr_);
51     }
52   }
53 }
54 
MarkFrameConstructed(int at_pc)55 void UnwindingInfoWriter::MarkFrameConstructed(int at_pc) {
56   if (!enabled()) return;
57 
58   // Regardless of the type of frame constructed, the relevant part of the
59   // layout is always the one in the diagram:
60   //
61   // |   ....   |         higher addresses
62   // +----------+               ^
63   // |    LR    |               |            |
64   // +----------+               |            |
65   // | saved FP |               |            |
66   // +----------+ <-- FP                     v
67   // |   ....   |                       stack growth
68   //
69   // The LR is pushed on the stack, and we can record this fact at the end of
70   // the construction, since the LR itself is not modified in the process.
71   eh_frame_writer_.AdvanceLocation(at_pc);
72   eh_frame_writer_.RecordRegisterSavedToStack(kLrDwarfCode,
73                                               kSystemPointerSize);
74   eh_frame_writer_.RecordRegisterSavedToStack(fp, 0);
75   saved_lr_ = true;
76 }
77 
MarkFrameDeconstructed(int at_pc)78 void UnwindingInfoWriter::MarkFrameDeconstructed(int at_pc) {
79   if (!enabled()) return;
80 
81   // The lr is restored by the last operation in LeaveFrame().
82   eh_frame_writer_.AdvanceLocation(at_pc);
83   eh_frame_writer_.RecordRegisterFollowsInitialRule(kLrDwarfCode);
84   saved_lr_ = false;
85 }
86 
MarkLinkRegisterOnTopOfStack(int pc_offset)87 void UnwindingInfoWriter::MarkLinkRegisterOnTopOfStack(int pc_offset) {
88   if (!enabled()) return;
89 
90   eh_frame_writer_.AdvanceLocation(pc_offset);
91   eh_frame_writer_.SetBaseAddressRegisterAndOffset(sp, 0);
92   eh_frame_writer_.RecordRegisterSavedToStack(kLrDwarfCode, 0);
93 }
94 
MarkPopLinkRegisterFromTopOfStack(int pc_offset)95 void UnwindingInfoWriter::MarkPopLinkRegisterFromTopOfStack(int pc_offset) {
96   if (!enabled()) return;
97 
98   eh_frame_writer_.AdvanceLocation(pc_offset);
99   eh_frame_writer_.SetBaseAddressRegisterAndOffset(fp, 0);
100   eh_frame_writer_.RecordRegisterFollowsInitialRule(kLrDwarfCode);
101 }
102 
103 }  // namespace compiler
104 }  // namespace internal
105 }  // namespace v8
106