11cb0ef41Sopenharmony_ci// Copyright 2015 the V8 project authors. All rights reserved.
21cb0ef41Sopenharmony_ci// Use of this source code is governed by a BSD-style license that can be
31cb0ef41Sopenharmony_ci// found in the LICENSE file.
41cb0ef41Sopenharmony_ci
51cb0ef41Sopenharmony_ci#include "src/compiler/frame.h"
61cb0ef41Sopenharmony_ci
71cb0ef41Sopenharmony_ci#include "src/compiler/linkage.h"
81cb0ef41Sopenharmony_ci
91cb0ef41Sopenharmony_cinamespace v8 {
101cb0ef41Sopenharmony_cinamespace internal {
111cb0ef41Sopenharmony_cinamespace compiler {
121cb0ef41Sopenharmony_ci
131cb0ef41Sopenharmony_ciFrame::Frame(int fixed_frame_size_in_slots)
141cb0ef41Sopenharmony_ci    : fixed_slot_count_(fixed_frame_size_in_slots),
151cb0ef41Sopenharmony_ci      allocated_registers_(nullptr),
161cb0ef41Sopenharmony_ci      allocated_double_registers_(nullptr) {
171cb0ef41Sopenharmony_ci  slot_allocator_.AllocateUnaligned(fixed_frame_size_in_slots);
181cb0ef41Sopenharmony_ci}
191cb0ef41Sopenharmony_ci
201cb0ef41Sopenharmony_civoid Frame::AlignFrame(int alignment) {
211cb0ef41Sopenharmony_ci#if DEBUG
221cb0ef41Sopenharmony_ci  spill_slots_finished_ = true;
231cb0ef41Sopenharmony_ci  frame_aligned_ = true;
241cb0ef41Sopenharmony_ci#endif
251cb0ef41Sopenharmony_ci  // In the calculations below we assume that alignment is a power of 2.
261cb0ef41Sopenharmony_ci  DCHECK(base::bits::IsPowerOfTwo(alignment));
271cb0ef41Sopenharmony_ci  int alignment_in_slots = AlignedSlotAllocator::NumSlotsForWidth(alignment);
281cb0ef41Sopenharmony_ci
291cb0ef41Sopenharmony_ci  // We have to align return slots separately, because they are claimed
301cb0ef41Sopenharmony_ci  // separately on the stack.
311cb0ef41Sopenharmony_ci  const int mask = alignment_in_slots - 1;
321cb0ef41Sopenharmony_ci  int return_delta = alignment_in_slots - (return_slot_count_ & mask);
331cb0ef41Sopenharmony_ci  if (return_delta != alignment_in_slots) {
341cb0ef41Sopenharmony_ci    return_slot_count_ += return_delta;
351cb0ef41Sopenharmony_ci  }
361cb0ef41Sopenharmony_ci  int delta = alignment_in_slots - (slot_allocator_.Size() & mask);
371cb0ef41Sopenharmony_ci  if (delta != alignment_in_slots) {
381cb0ef41Sopenharmony_ci    slot_allocator_.Align(alignment_in_slots);
391cb0ef41Sopenharmony_ci    if (spill_slot_count_ != 0) {
401cb0ef41Sopenharmony_ci      spill_slot_count_ += delta;
411cb0ef41Sopenharmony_ci    }
421cb0ef41Sopenharmony_ci  }
431cb0ef41Sopenharmony_ci}
441cb0ef41Sopenharmony_ci
451cb0ef41Sopenharmony_civoid FrameAccessState::MarkHasFrame(bool state) {
461cb0ef41Sopenharmony_ci  has_frame_ = state;
471cb0ef41Sopenharmony_ci  SetFrameAccessToDefault();
481cb0ef41Sopenharmony_ci}
491cb0ef41Sopenharmony_ci
501cb0ef41Sopenharmony_civoid FrameAccessState::SetFrameAccessToDefault() {
511cb0ef41Sopenharmony_ci  if (has_frame() && !FLAG_turbo_sp_frame_access) {
521cb0ef41Sopenharmony_ci    SetFrameAccessToFP();
531cb0ef41Sopenharmony_ci  } else {
541cb0ef41Sopenharmony_ci    SetFrameAccessToSP();
551cb0ef41Sopenharmony_ci  }
561cb0ef41Sopenharmony_ci}
571cb0ef41Sopenharmony_ci
581cb0ef41Sopenharmony_ci
591cb0ef41Sopenharmony_ciFrameOffset FrameAccessState::GetFrameOffset(int spill_slot) const {
601cb0ef41Sopenharmony_ci  const int frame_offset = FrameSlotToFPOffset(spill_slot);
611cb0ef41Sopenharmony_ci  if (access_frame_with_fp()) {
621cb0ef41Sopenharmony_ci    return FrameOffset::FromFramePointer(frame_offset);
631cb0ef41Sopenharmony_ci  } else {
641cb0ef41Sopenharmony_ci    // No frame. Retrieve all parameters relative to stack pointer.
651cb0ef41Sopenharmony_ci    int sp_offset = frame_offset + GetSPToFPOffset();
661cb0ef41Sopenharmony_ci    return FrameOffset::FromStackPointer(sp_offset);
671cb0ef41Sopenharmony_ci  }
681cb0ef41Sopenharmony_ci}
691cb0ef41Sopenharmony_ci
701cb0ef41Sopenharmony_ci
711cb0ef41Sopenharmony_ci}  // namespace compiler
721cb0ef41Sopenharmony_ci}  // namespace internal
731cb0ef41Sopenharmony_ci}  // namespace v8
74