blob: bd968e474c98b39640ec3a771b9c69ed4d478b4c [file] [log] [blame]
Anton Korobeynikov33464912010-11-15 00:06:54 +00001//=======- MBlazeFrameInfo.cpp - MBlaze Frame Information ------*- C++ -*-====//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This file contains the MBlaze implementation of TargetFrameInfo class.
11//
12//===----------------------------------------------------------------------===//
13
14#include "MBlazeFrameInfo.h"
15#include "MBlazeInstrInfo.h"
16#include "MBlazeMachineFunction.h"
17#include "llvm/Function.h"
18#include "llvm/CodeGen/MachineFrameInfo.h"
19#include "llvm/CodeGen/MachineFunction.h"
20#include "llvm/CodeGen/MachineInstrBuilder.h"
21#include "llvm/CodeGen/MachineModuleInfo.h"
22#include "llvm/CodeGen/MachineRegisterInfo.h"
23#include "llvm/Target/TargetData.h"
24#include "llvm/Target/TargetOptions.h"
25#include "llvm/Support/CommandLine.h"
26
27using namespace llvm;
28
Anton Korobeynikov33464912010-11-15 00:06:54 +000029//===----------------------------------------------------------------------===//
30//
31// Stack Frame Processing methods
32// +----------------------------+
33//
34// The stack is allocated decrementing the stack pointer on
35// the first instruction of a function prologue. Once decremented,
36// all stack references are are done through a positive offset
37// from the stack/frame pointer, so the stack is considered
38// to grow up.
39//
40//===----------------------------------------------------------------------===//
41
Anton Korobeynikovd0c38172010-11-18 21:19:35 +000042// hasFP - Return true if the specified function should have a dedicated frame
43// pointer register. This is true if the function has variable sized allocas or
44// if frame pointer elimination is disabled.
45bool MBlazeFrameInfo::hasFP(const MachineFunction &MF) const {
46 const MachineFrameInfo *MFI = MF.getFrameInfo();
47 return DisableFramePointerElim(MF) || MFI->hasVarSizedObjects();
48}
49
Anton Korobeynikov33464912010-11-15 00:06:54 +000050void MBlazeFrameInfo::emitPrologue(MachineFunction &MF) const {
51 MachineBasicBlock &MBB = MF.front();
52 MachineFrameInfo *MFI = MF.getFrameInfo();
Anton Korobeynikov33464912010-11-15 00:06:54 +000053 const MBlazeInstrInfo &TII =
54 *static_cast<const MBlazeInstrInfo*>(MF.getTarget().getInstrInfo());
55 MBlazeFunctionInfo *MBlazeFI = MF.getInfo<MBlazeFunctionInfo>();
56 MachineBasicBlock::iterator MBBI = MBB.begin();
57 DebugLoc DL = MBBI != MBB.end() ? MBBI->getDebugLoc() : DebugLoc();
58
Wesley Peck8397be02010-12-09 03:42:04 +000059 // Replace the dummy '0' SPOffset by the negative offsets, as explained on
60 // LowerFORMAL_ARGUMENTS. Leaving '0' for while is necessary to avoid
61 // the approach done by calculateFrameObjectOffsets to the stack frame.
62 MBlazeFI->adjustLoadArgsFI(MFI);
63 MBlazeFI->adjustStoreVarArgsFI(MFI);
Anton Korobeynikov33464912010-11-15 00:06:54 +000064
65 // Get the number of bytes to allocate from the FrameInfo.
66 unsigned StackSize = MFI->getStackSize();
67
68 // No need to allocate space on the stack.
69 if (StackSize == 0 && !MFI->adjustsStack()) return;
Anton Korobeynikov33464912010-11-15 00:06:54 +000070
71 int FPOffset = MBlazeFI->getFPStackOffset();
72 int RAOffset = MBlazeFI->getRAStackOffset();
73
74 // Adjust stack : addi R1, R1, -imm
75 BuildMI(MBB, MBBI, DL, TII.get(MBlaze::ADDI), MBlaze::R1)
76 .addReg(MBlaze::R1).addImm(-StackSize);
77
Anton Korobeynikov33464912010-11-15 00:06:54 +000078 // swi R15, R1, stack_loc
79 if (MFI->adjustsStack()) {
80 BuildMI(MBB, MBBI, DL, TII.get(MBlaze::SWI))
81 .addReg(MBlaze::R15).addReg(MBlaze::R1).addImm(RAOffset);
82 }
83
Anton Korobeynikovd0c38172010-11-18 21:19:35 +000084 if (hasFP(MF)) {
Anton Korobeynikov33464912010-11-15 00:06:54 +000085 // swi R19, R1, stack_loc
86 BuildMI(MBB, MBBI, DL, TII.get(MBlaze::SWI))
87 .addReg(MBlaze::R19).addReg(MBlaze::R1).addImm(FPOffset);
88
89 // add R19, R1, R0
90 BuildMI(MBB, MBBI, DL, TII.get(MBlaze::ADD), MBlaze::R19)
91 .addReg(MBlaze::R1).addReg(MBlaze::R0);
92 }
93}
94
95void MBlazeFrameInfo::emitEpilogue(MachineFunction &MF,
96 MachineBasicBlock &MBB) const {
97 MachineBasicBlock::iterator MBBI = prior(MBB.end());
98 MachineFrameInfo *MFI = MF.getFrameInfo();
Anton Korobeynikovd0c38172010-11-18 21:19:35 +000099 MBlazeFunctionInfo *MBlazeFI = MF.getInfo<MBlazeFunctionInfo>();
Anton Korobeynikov33464912010-11-15 00:06:54 +0000100 const MBlazeInstrInfo &TII =
101 *static_cast<const MBlazeInstrInfo*>(MF.getTarget().getInstrInfo());
102
103 DebugLoc dl = MBBI->getDebugLoc();
104
105 // Get the FI's where RA and FP are saved.
106 int FPOffset = MBlazeFI->getFPStackOffset();
107 int RAOffset = MBlazeFI->getRAStackOffset();
108
Anton Korobeynikovd0c38172010-11-18 21:19:35 +0000109 if (hasFP(MF)) {
Anton Korobeynikov33464912010-11-15 00:06:54 +0000110 // add R1, R19, R0
111 BuildMI(MBB, MBBI, dl, TII.get(MBlaze::ADD), MBlaze::R1)
112 .addReg(MBlaze::R19).addReg(MBlaze::R0);
113
114 // lwi R19, R1, stack_loc
115 BuildMI(MBB, MBBI, dl, TII.get(MBlaze::LWI), MBlaze::R19)
116 .addReg(MBlaze::R1).addImm(FPOffset);
117 }
118
Anton Korobeynikov33464912010-11-15 00:06:54 +0000119 // lwi R15, R1, stack_loc
120 if (MFI->adjustsStack()) {
121 BuildMI(MBB, MBBI, dl, TII.get(MBlaze::LWI), MBlaze::R15)
122 .addReg(MBlaze::R1).addImm(RAOffset);
123 }
124
125 // Get the number of bytes from FrameInfo
126 int StackSize = (int) MFI->getStackSize();
Anton Korobeynikov33464912010-11-15 00:06:54 +0000127
Anton Korobeynikov33464912010-11-15 00:06:54 +0000128 // addi R1, R1, imm
129 if (StackSize) {
130 BuildMI(MBB, MBBI, dl, TII.get(MBlaze::ADDI), MBlaze::R1)
131 .addReg(MBlaze::R1).addImm(StackSize);
132 }
133}
Wesley Peck8397be02010-12-09 03:42:04 +0000134
135void MBlazeFrameInfo::processFunctionBeforeCalleeSavedScan(MachineFunction &MF, RegScavenger *RS)
136 const {
137 MachineFrameInfo *MFI = MF.getFrameInfo();
138 MBlazeFunctionInfo *MBlazeFI = MF.getInfo<MBlazeFunctionInfo>();
139
140 if (MFI->adjustsStack()) {
141 MBlazeFI->setRAStackOffset(0);
142 MFI->CreateFixedObject(4,0,true);
143 }
144
145 if (hasFP(MF)) {
146 MBlazeFI->setFPStackOffset(4);
147 MFI->CreateFixedObject(4,4,true);
148 }
149}