blob: cae62905d370029de6fd6100ebee67447a4a40b3 [file] [log] [blame]
Misha Brukmancf2b9ac2002-11-22 22:43:47 +00001//===- X86RegisterInfo.cpp - X86 Register Information -----------*- C++ -*-===//
Alkis Evlogimenos39354c92004-03-14 07:19:51 +00002//
John Criswellb576c942003-10-20 19:43:21 +00003// The LLVM Compiler Infrastructure
4//
Chris Lattner4ee451d2007-12-29 20:36:04 +00005// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
Alkis Evlogimenos39354c92004-03-14 07:19:51 +00007//
John Criswellb576c942003-10-20 19:43:21 +00008//===----------------------------------------------------------------------===//
Chris Lattner72614082002-10-25 22:55:53 +00009//
Dan Gohman6f0d0242008-02-10 18:45:23 +000010// This file contains the X86 implementation of the TargetRegisterInfo class.
11// This file is responsible for the frame pointer elimination optimization
12// on X86.
Chris Lattner72614082002-10-25 22:55:53 +000013//
14//===----------------------------------------------------------------------===//
15
Misha Brukmanb83b2862002-11-20 18:59:43 +000016#include "X86.h"
Chris Lattner72614082002-10-25 22:55:53 +000017#include "X86RegisterInfo.h"
Misha Brukmancf2b9ac2002-11-22 22:43:47 +000018#include "X86InstrBuilder.h"
Evan Chenge8bd0a32006-06-06 23:30:24 +000019#include "X86MachineFunctionInfo.h"
Evan Cheng25ab6902006-09-08 06:48:29 +000020#include "X86Subtarget.h"
Evan Chenge8bd0a32006-06-06 23:30:24 +000021#include "X86TargetMachine.h"
Misha Brukmanb83b2862002-11-20 18:59:43 +000022#include "llvm/Constants.h"
Evan Cheng3649b0e2006-06-02 22:38:37 +000023#include "llvm/Function.h"
Evan Cheng25ab6902006-09-08 06:48:29 +000024#include "llvm/Type.h"
Chris Lattnerc8c377d2003-07-29 05:14:16 +000025#include "llvm/CodeGen/ValueTypes.h"
Misha Brukmanb83b2862002-11-20 18:59:43 +000026#include "llvm/CodeGen/MachineInstrBuilder.h"
Chris Lattner198ab642002-12-15 20:06:35 +000027#include "llvm/CodeGen/MachineFunction.h"
Dan Gohman2dad0252008-07-01 18:15:35 +000028#include "llvm/CodeGen/MachineFunctionPass.h"
Chris Lattneraa09b752002-12-28 21:08:28 +000029#include "llvm/CodeGen/MachineFrameInfo.h"
Jim Laskeyf1d78e82006-03-23 18:12:57 +000030#include "llvm/CodeGen/MachineLocation.h"
Chris Lattner84bc5422007-12-31 04:13:23 +000031#include "llvm/CodeGen/MachineModuleInfo.h"
32#include "llvm/CodeGen/MachineRegisterInfo.h"
Anton Korobeynikovce3b4652007-05-02 19:53:33 +000033#include "llvm/Target/TargetAsmInfo.h"
Chris Lattnerf158da22003-01-16 02:20:12 +000034#include "llvm/Target/TargetFrameInfo.h"
Evan Cheng51cdcd12006-12-07 01:21:59 +000035#include "llvm/Target/TargetInstrInfo.h"
Misha Brukman83eaa0b2004-06-21 21:10:24 +000036#include "llvm/Target/TargetMachine.h"
Chris Lattner0cf0c372004-07-11 04:17:10 +000037#include "llvm/Target/TargetOptions.h"
Evan Chengb371f452007-02-19 21:49:54 +000038#include "llvm/ADT/BitVector.h"
Reid Spencer551ccae2004-09-01 22:55:40 +000039#include "llvm/ADT/STLExtras.h"
Dan Gohmana4714e02009-07-30 01:56:29 +000040#include "llvm/Support/CommandLine.h"
Anton Korobeynikov856914f2008-04-23 18:23:05 +000041#include "llvm/Support/Compiler.h"
Torok Edwinc25e7582009-07-11 20:10:48 +000042#include "llvm/Support/ErrorHandling.h"
Chris Lattner300d0ed2004-02-14 06:00:36 +000043using namespace llvm;
Brian Gaeked0fde302003-11-11 22:41:34 +000044
Evan Cheng25ab6902006-09-08 06:48:29 +000045X86RegisterInfo::X86RegisterInfo(X86TargetMachine &tm,
46 const TargetInstrInfo &tii)
Dan Gohman6d4b0522008-10-01 18:28:06 +000047 : X86GenRegisterInfo(tm.getSubtarget<X86Subtarget>().is64Bit() ?
48 X86::ADJCALLSTACKDOWN64 :
49 X86::ADJCALLSTACKDOWN32,
50 tm.getSubtarget<X86Subtarget>().is64Bit() ?
51 X86::ADJCALLSTACKUP64 :
52 X86::ADJCALLSTACKUP32),
Evan Cheng25ab6902006-09-08 06:48:29 +000053 TM(tm), TII(tii) {
54 // Cache some information.
55 const X86Subtarget *Subtarget = &TM.getSubtarget<X86Subtarget>();
56 Is64Bit = Subtarget->is64Bit();
Anton Korobeynikov1dcce212008-03-22 21:04:01 +000057 IsWin64 = Subtarget->isTargetWin64();
Evan Chengdb807ed2007-11-05 07:30:01 +000058 StackAlign = TM.getFrameInfo()->getStackAlignment();
Evan Cheng25ab6902006-09-08 06:48:29 +000059 if (Is64Bit) {
60 SlotSize = 8;
61 StackPtr = X86::RSP;
62 FramePtr = X86::RBP;
63 } else {
64 SlotSize = 4;
65 StackPtr = X86::ESP;
66 FramePtr = X86::EBP;
67 }
68}
Chris Lattner7ad3e062003-08-03 15:48:14 +000069
Dale Johannesen483ec212007-11-07 00:25:05 +000070// getDwarfRegNum - This function maps LLVM register identifiers to the
71// Dwarf specific numbering, used in debug info and exception tables.
Dale Johannesen4542edc2007-11-07 21:48:35 +000072
Dale Johannesenb97aec62007-11-13 19:13:01 +000073int X86RegisterInfo::getDwarfRegNum(unsigned RegNo, bool isEH) const {
Dale Johannesen483ec212007-11-07 00:25:05 +000074 const X86Subtarget *Subtarget = &TM.getSubtarget<X86Subtarget>();
Anton Korobeynikovf191c802007-11-11 19:50:10 +000075 unsigned Flavour = DWARFFlavour::X86_64;
Dale Johannesen7a42f242007-11-09 18:07:11 +000076 if (!Subtarget->is64Bit()) {
Anton Korobeynikovf191c802007-11-11 19:50:10 +000077 if (Subtarget->isTargetDarwin()) {
Anton Korobeynikov8eea3392008-01-25 00:34:13 +000078 if (isEH)
79 Flavour = DWARFFlavour::X86_32_DarwinEH;
80 else
81 Flavour = DWARFFlavour::X86_32_Generic;
Anton Korobeynikovf191c802007-11-11 19:50:10 +000082 } else if (Subtarget->isTargetCygMing()) {
83 // Unsupported by now, just quick fallback
Anton Korobeynikov8eea3392008-01-25 00:34:13 +000084 Flavour = DWARFFlavour::X86_32_Generic;
Anton Korobeynikovf191c802007-11-11 19:50:10 +000085 } else {
Anton Korobeynikov8eea3392008-01-25 00:34:13 +000086 Flavour = DWARFFlavour::X86_32_Generic;
Dale Johannesen7a42f242007-11-09 18:07:11 +000087 }
Dale Johannesen483ec212007-11-07 00:25:05 +000088 }
Anton Korobeynikovf191c802007-11-11 19:50:10 +000089
90 return X86GenRegisterInfo::getDwarfRegNumFull(RegNo, Flavour);
Dale Johannesen483ec212007-11-07 00:25:05 +000091}
92
Duncan Sandsee465742007-08-29 19:01:20 +000093// getX86RegNum - This function maps LLVM register identifiers to their X86
94// specific numbering, which is used in various places encoding instructions.
95//
Nicolas Geoffray52e724a2008-04-16 20:10:13 +000096unsigned X86RegisterInfo::getX86RegNum(unsigned RegNo) {
Duncan Sandsee465742007-08-29 19:01:20 +000097 switch(RegNo) {
98 case X86::RAX: case X86::EAX: case X86::AX: case X86::AL: return N86::EAX;
99 case X86::RCX: case X86::ECX: case X86::CX: case X86::CL: return N86::ECX;
100 case X86::RDX: case X86::EDX: case X86::DX: case X86::DL: return N86::EDX;
101 case X86::RBX: case X86::EBX: case X86::BX: case X86::BL: return N86::EBX;
102 case X86::RSP: case X86::ESP: case X86::SP: case X86::SPL: case X86::AH:
103 return N86::ESP;
104 case X86::RBP: case X86::EBP: case X86::BP: case X86::BPL: case X86::CH:
105 return N86::EBP;
106 case X86::RSI: case X86::ESI: case X86::SI: case X86::SIL: case X86::DH:
107 return N86::ESI;
108 case X86::RDI: case X86::EDI: case X86::DI: case X86::DIL: case X86::BH:
109 return N86::EDI;
110
111 case X86::R8: case X86::R8D: case X86::R8W: case X86::R8B:
112 return N86::EAX;
113 case X86::R9: case X86::R9D: case X86::R9W: case X86::R9B:
114 return N86::ECX;
115 case X86::R10: case X86::R10D: case X86::R10W: case X86::R10B:
116 return N86::EDX;
117 case X86::R11: case X86::R11D: case X86::R11W: case X86::R11B:
118 return N86::EBX;
119 case X86::R12: case X86::R12D: case X86::R12W: case X86::R12B:
120 return N86::ESP;
121 case X86::R13: case X86::R13D: case X86::R13W: case X86::R13B:
122 return N86::EBP;
123 case X86::R14: case X86::R14D: case X86::R14W: case X86::R14B:
124 return N86::ESI;
125 case X86::R15: case X86::R15D: case X86::R15W: case X86::R15B:
126 return N86::EDI;
127
128 case X86::ST0: case X86::ST1: case X86::ST2: case X86::ST3:
129 case X86::ST4: case X86::ST5: case X86::ST6: case X86::ST7:
130 return RegNo-X86::ST0;
131
Nate Begeman6e041c22007-12-11 18:06:14 +0000132 case X86::XMM0: case X86::XMM8: case X86::MM0:
Evan Chenge7c87542007-11-13 17:54:34 +0000133 return 0;
Nate Begeman6e041c22007-12-11 18:06:14 +0000134 case X86::XMM1: case X86::XMM9: case X86::MM1:
Evan Chenge7c87542007-11-13 17:54:34 +0000135 return 1;
Nate Begeman6e041c22007-12-11 18:06:14 +0000136 case X86::XMM2: case X86::XMM10: case X86::MM2:
Evan Chenge7c87542007-11-13 17:54:34 +0000137 return 2;
Nate Begeman6e041c22007-12-11 18:06:14 +0000138 case X86::XMM3: case X86::XMM11: case X86::MM3:
Evan Chenge7c87542007-11-13 17:54:34 +0000139 return 3;
Nate Begeman6e041c22007-12-11 18:06:14 +0000140 case X86::XMM4: case X86::XMM12: case X86::MM4:
Evan Chenge7c87542007-11-13 17:54:34 +0000141 return 4;
Nate Begeman6e041c22007-12-11 18:06:14 +0000142 case X86::XMM5: case X86::XMM13: case X86::MM5:
Evan Chenge7c87542007-11-13 17:54:34 +0000143 return 5;
Nate Begeman6e041c22007-12-11 18:06:14 +0000144 case X86::XMM6: case X86::XMM14: case X86::MM6:
Evan Chenge7c87542007-11-13 17:54:34 +0000145 return 6;
Nate Begeman6e041c22007-12-11 18:06:14 +0000146 case X86::XMM7: case X86::XMM15: case X86::MM7:
Evan Chenge7c87542007-11-13 17:54:34 +0000147 return 7;
Duncan Sandsee465742007-08-29 19:01:20 +0000148
149 default:
150 assert(isVirtualRegister(RegNo) && "Unknown physical register!");
Torok Edwinc23197a2009-07-14 16:55:14 +0000151 llvm_unreachable("Register allocator hasn't allocated reg correctly yet!");
Duncan Sandsee465742007-08-29 19:01:20 +0000152 return 0;
153 }
154}
155
Evan Cheng52484682009-07-18 02:10:10 +0000156const TargetRegisterClass *
157X86RegisterInfo::getMatchingSuperRegClass(const TargetRegisterClass *A,
158 const TargetRegisterClass *B,
159 unsigned SubIdx) const {
160 switch (SubIdx) {
161 default: return 0;
162 case 1:
163 // 8-bit
164 if (B == &X86::GR8RegClass) {
Evan Cheng753480a2009-07-20 19:47:55 +0000165 if (A->getSize() == 2 || A->getSize() == 4 || A->getSize() == 8)
166 return A;
Evan Cheng52484682009-07-18 02:10:10 +0000167 } else if (B == &X86::GR8_ABCD_LRegClass || B == &X86::GR8_ABCD_HRegClass) {
Evan Cheng753480a2009-07-20 19:47:55 +0000168 if (A == &X86::GR64RegClass || A == &X86::GR64_ABCDRegClass ||
Dan Gohmana4714e02009-07-30 01:56:29 +0000169 A == &X86::GR64_NOREXRegClass ||
170 A == &X86::GR64_NOSPRegClass ||
171 A == &X86::GR64_NOREX_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000172 return &X86::GR64_ABCDRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000173 else if (A == &X86::GR32RegClass || A == &X86::GR32_ABCDRegClass ||
Dan Gohmana4714e02009-07-30 01:56:29 +0000174 A == &X86::GR32_NOREXRegClass ||
175 A == &X86::GR32_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000176 return &X86::GR32_ABCDRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000177 else if (A == &X86::GR16RegClass || A == &X86::GR16_ABCDRegClass ||
178 A == &X86::GR16_NOREXRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000179 return &X86::GR16_ABCDRegClass;
180 } else if (B == &X86::GR8_NOREXRegClass) {
Dan Gohmana4714e02009-07-30 01:56:29 +0000181 if (A == &X86::GR64RegClass || A == &X86::GR64_NOREXRegClass ||
182 A == &X86::GR64_NOSPRegClass || A == &X86::GR64_NOREX_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000183 return &X86::GR64_NOREXRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000184 else if (A == &X86::GR64_ABCDRegClass)
185 return &X86::GR64_ABCDRegClass;
Dan Gohmana4714e02009-07-30 01:56:29 +0000186 else if (A == &X86::GR32RegClass || A == &X86::GR32_NOREXRegClass ||
187 A == &X86::GR32_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000188 return &X86::GR32_NOREXRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000189 else if (A == &X86::GR32_ABCDRegClass)
190 return &X86::GR32_ABCDRegClass;
Evan Cheng52484682009-07-18 02:10:10 +0000191 else if (A == &X86::GR16RegClass || A == &X86::GR16_NOREXRegClass)
192 return &X86::GR16_NOREXRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000193 else if (A == &X86::GR16_ABCDRegClass)
194 return &X86::GR16_ABCDRegClass;
Evan Cheng52484682009-07-18 02:10:10 +0000195 }
196 break;
197 case 2:
198 // 8-bit hi
199 if (B == &X86::GR8_ABCD_HRegClass) {
Evan Cheng753480a2009-07-20 19:47:55 +0000200 if (A == &X86::GR64RegClass || A == &X86::GR64_ABCDRegClass ||
Dan Gohmana4714e02009-07-30 01:56:29 +0000201 A == &X86::GR64_NOREXRegClass ||
202 A == &X86::GR64_NOSPRegClass ||
203 A == &X86::GR64_NOREX_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000204 return &X86::GR64_ABCDRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000205 else if (A == &X86::GR32RegClass || A == &X86::GR32_ABCDRegClass ||
Dan Gohmana4714e02009-07-30 01:56:29 +0000206 A == &X86::GR32_NOREXRegClass || A == &X86::GR32_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000207 return &X86::GR32_ABCDRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000208 else if (A == &X86::GR16RegClass || A == &X86::GR16_ABCDRegClass ||
209 A == &X86::GR16_NOREXRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000210 return &X86::GR16_ABCDRegClass;
211 }
212 break;
213 case 3:
214 // 16-bit
215 if (B == &X86::GR16RegClass) {
Evan Cheng753480a2009-07-20 19:47:55 +0000216 if (A->getSize() == 4 || A->getSize() == 8)
217 return A;
Evan Cheng52484682009-07-18 02:10:10 +0000218 } else if (B == &X86::GR16_ABCDRegClass) {
Evan Cheng753480a2009-07-20 19:47:55 +0000219 if (A == &X86::GR64RegClass || A == &X86::GR64_ABCDRegClass ||
Dan Gohmana4714e02009-07-30 01:56:29 +0000220 A == &X86::GR64_NOREXRegClass ||
221 A == &X86::GR64_NOSPRegClass ||
222 A == &X86::GR64_NOREX_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000223 return &X86::GR64_ABCDRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000224 else if (A == &X86::GR32RegClass || A == &X86::GR32_ABCDRegClass ||
Dan Gohmana4714e02009-07-30 01:56:29 +0000225 A == &X86::GR32_NOREXRegClass || A == &X86::GR32_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000226 return &X86::GR32_ABCDRegClass;
227 } else if (B == &X86::GR16_NOREXRegClass) {
Dan Gohmana4714e02009-07-30 01:56:29 +0000228 if (A == &X86::GR64RegClass || A == &X86::GR64_NOREXRegClass ||
229 A == &X86::GR64_NOSPRegClass || A == &X86::GR64_NOREX_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000230 return &X86::GR64_NOREXRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000231 else if (A == &X86::GR64_ABCDRegClass)
232 return &X86::GR64_ABCDRegClass;
Dan Gohmana4714e02009-07-30 01:56:29 +0000233 else if (A == &X86::GR32RegClass || A == &X86::GR32_NOREXRegClass ||
234 A == &X86::GR32_NOSPRegClass)
Evan Cheng753480a2009-07-20 19:47:55 +0000235 return &X86::GR32_NOREXRegClass;
236 else if (A == &X86::GR32_ABCDRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000237 return &X86::GR64_ABCDRegClass;
238 }
239 break;
240 case 4:
241 // 32-bit
Dan Gohmana4714e02009-07-30 01:56:29 +0000242 if (B == &X86::GR32RegClass || B == &X86::GR32_NOSPRegClass) {
Evan Cheng753480a2009-07-20 19:47:55 +0000243 if (A->getSize() == 8)
244 return A;
Evan Cheng52484682009-07-18 02:10:10 +0000245 } else if (B == &X86::GR32_ABCDRegClass) {
Evan Cheng753480a2009-07-20 19:47:55 +0000246 if (A == &X86::GR64RegClass || A == &X86::GR64_ABCDRegClass ||
Dan Gohmana4714e02009-07-30 01:56:29 +0000247 A == &X86::GR64_NOREXRegClass ||
248 A == &X86::GR64_NOSPRegClass ||
249 A == &X86::GR64_NOREX_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000250 return &X86::GR64_ABCDRegClass;
251 } else if (B == &X86::GR32_NOREXRegClass) {
Dan Gohmana4714e02009-07-30 01:56:29 +0000252 if (A == &X86::GR64RegClass || A == &X86::GR64_NOREXRegClass ||
253 A == &X86::GR64_NOSPRegClass || A == &X86::GR64_NOREX_NOSPRegClass)
Evan Cheng52484682009-07-18 02:10:10 +0000254 return &X86::GR64_NOREXRegClass;
Evan Cheng753480a2009-07-20 19:47:55 +0000255 else if (A == &X86::GR64_ABCDRegClass)
256 return &X86::GR64_ABCDRegClass;
Evan Cheng52484682009-07-18 02:10:10 +0000257 }
258 break;
259 }
260 return 0;
261}
262
Chris Lattner2cfd52c2009-07-29 20:31:52 +0000263const TargetRegisterClass *X86RegisterInfo::
264getPointerRegClass(unsigned Kind) const {
Dan Gohmana4714e02009-07-30 01:56:29 +0000265 switch (Kind) {
266 default: llvm_unreachable("Unexpected Kind in getPointerRegClass!");
267 case 0: // Normal GPRs.
268 if (TM.getSubtarget<X86Subtarget>().is64Bit())
269 return &X86::GR64RegClass;
270 return &X86::GR32RegClass;
271 case 1: // Normal GRPs except the stack pointer (for encoding reasons).
Dan Gohman74f6f9a2009-08-05 17:40:24 +0000272 if (TM.getSubtarget<X86Subtarget>().is64Bit())
273 return &X86::GR64_NOSPRegClass;
274 return &X86::GR32_NOSPRegClass;
Dan Gohmana4714e02009-07-30 01:56:29 +0000275 }
Evan Cheng770bcc72009-02-06 17:43:24 +0000276}
277
Evan Chengff110262007-09-26 21:31:07 +0000278const TargetRegisterClass *
279X86RegisterInfo::getCrossCopyRegClass(const TargetRegisterClass *RC) const {
Anton Korobeynikov4aefd6b2008-02-20 12:07:57 +0000280 if (RC == &X86::CCRRegClass) {
Evan Cheng3f2d9ec2007-09-27 21:50:05 +0000281 if (Is64Bit)
282 return &X86::GR64RegClass;
283 else
284 return &X86::GR32RegClass;
Anton Korobeynikov4aefd6b2008-02-20 12:07:57 +0000285 }
Evan Chengff110262007-09-26 21:31:07 +0000286 return NULL;
287}
Evan Chengbf2c8b32007-03-20 08:09:38 +0000288
Evan Cheng64d80e32007-07-19 01:14:50 +0000289const unsigned *
290X86RegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const {
Anton Korobeynikovb84c1672008-09-08 21:12:47 +0000291 bool callsEHReturn = false;
292
293 if (MF) {
294 const MachineFrameInfo *MFI = MF->getFrameInfo();
295 const MachineModuleInfo *MMI = MFI->getMachineModuleInfo();
296 callsEHReturn = (MMI ? MMI->callsEHReturn() : false);
297 }
298
Evan Chengc2b861d2007-01-02 21:33:40 +0000299 static const unsigned CalleeSavedRegs32Bit[] = {
Evan Cheng0f3ac8d2006-05-18 00:12:58 +0000300 X86::ESI, X86::EDI, X86::EBX, X86::EBP, 0
301 };
Anton Korobeynikov2365f512007-07-14 14:06:15 +0000302
303 static const unsigned CalleeSavedRegs32EHRet[] = {
304 X86::EAX, X86::EDX, X86::ESI, X86::EDI, X86::EBX, X86::EBP, 0
305 };
306
Evan Chengc2b861d2007-01-02 21:33:40 +0000307 static const unsigned CalleeSavedRegs64Bit[] = {
Evan Cheng25ab6902006-09-08 06:48:29 +0000308 X86::RBX, X86::R12, X86::R13, X86::R14, X86::R15, X86::RBP, 0
309 };
310
Anton Korobeynikovb84c1672008-09-08 21:12:47 +0000311 static const unsigned CalleeSavedRegs64EHRet[] = {
312 X86::RAX, X86::RDX, X86::RBX, X86::R12,
313 X86::R13, X86::R14, X86::R15, X86::RBP, 0
314 };
315
Anton Korobeynikov1dcce212008-03-22 21:04:01 +0000316 static const unsigned CalleeSavedRegsWin64[] = {
Anton Korobeynikov5979d712008-09-24 22:03:04 +0000317 X86::RBX, X86::RBP, X86::RDI, X86::RSI,
318 X86::R12, X86::R13, X86::R14, X86::R15,
319 X86::XMM6, X86::XMM7, X86::XMM8, X86::XMM9,
320 X86::XMM10, X86::XMM11, X86::XMM12, X86::XMM13,
321 X86::XMM14, X86::XMM15, 0
Anton Korobeynikov1dcce212008-03-22 21:04:01 +0000322 };
323
324 if (Is64Bit) {
325 if (IsWin64)
326 return CalleeSavedRegsWin64;
327 else
Anton Korobeynikovb84c1672008-09-08 21:12:47 +0000328 return (callsEHReturn ? CalleeSavedRegs64EHRet : CalleeSavedRegs64Bit);
Anton Korobeynikov1dcce212008-03-22 21:04:01 +0000329 } else {
Anton Korobeynikovb84c1672008-09-08 21:12:47 +0000330 return (callsEHReturn ? CalleeSavedRegs32EHRet : CalleeSavedRegs32Bit);
Anton Korobeynikov2365f512007-07-14 14:06:15 +0000331 }
Evan Cheng0f3ac8d2006-05-18 00:12:58 +0000332}
333
334const TargetRegisterClass* const*
Anton Korobeynikov2365f512007-07-14 14:06:15 +0000335X86RegisterInfo::getCalleeSavedRegClasses(const MachineFunction *MF) const {
Anton Korobeynikovb84c1672008-09-08 21:12:47 +0000336 bool callsEHReturn = false;
337
338 if (MF) {
339 const MachineFrameInfo *MFI = MF->getFrameInfo();
340 const MachineModuleInfo *MMI = MFI->getMachineModuleInfo();
341 callsEHReturn = (MMI ? MMI->callsEHReturn() : false);
342 }
343
Evan Chengc2b861d2007-01-02 21:33:40 +0000344 static const TargetRegisterClass * const CalleeSavedRegClasses32Bit[] = {
Evan Cheng0f3ac8d2006-05-18 00:12:58 +0000345 &X86::GR32RegClass, &X86::GR32RegClass,
346 &X86::GR32RegClass, &X86::GR32RegClass, 0
347 };
Anton Korobeynikov2365f512007-07-14 14:06:15 +0000348 static const TargetRegisterClass * const CalleeSavedRegClasses32EHRet[] = {
349 &X86::GR32RegClass, &X86::GR32RegClass,
350 &X86::GR32RegClass, &X86::GR32RegClass,
351 &X86::GR32RegClass, &X86::GR32RegClass, 0
352 };
Evan Chengc2b861d2007-01-02 21:33:40 +0000353 static const TargetRegisterClass * const CalleeSavedRegClasses64Bit[] = {
Evan Cheng25ab6902006-09-08 06:48:29 +0000354 &X86::GR64RegClass, &X86::GR64RegClass,
355 &X86::GR64RegClass, &X86::GR64RegClass,
356 &X86::GR64RegClass, &X86::GR64RegClass, 0
357 };
Anton Korobeynikovb84c1672008-09-08 21:12:47 +0000358 static const TargetRegisterClass * const CalleeSavedRegClasses64EHRet[] = {
359 &X86::GR64RegClass, &X86::GR64RegClass,
360 &X86::GR64RegClass, &X86::GR64RegClass,
361 &X86::GR64RegClass, &X86::GR64RegClass,
362 &X86::GR64RegClass, &X86::GR64RegClass, 0
363 };
Anton Korobeynikov1dcce212008-03-22 21:04:01 +0000364 static const TargetRegisterClass * const CalleeSavedRegClassesWin64[] = {
Anton Korobeynikov5979d712008-09-24 22:03:04 +0000365 &X86::GR64RegClass, &X86::GR64RegClass,
366 &X86::GR64RegClass, &X86::GR64RegClass,
367 &X86::GR64RegClass, &X86::GR64RegClass,
368 &X86::GR64RegClass, &X86::GR64RegClass,
369 &X86::VR128RegClass, &X86::VR128RegClass,
370 &X86::VR128RegClass, &X86::VR128RegClass,
371 &X86::VR128RegClass, &X86::VR128RegClass,
372 &X86::VR128RegClass, &X86::VR128RegClass,
373 &X86::VR128RegClass, &X86::VR128RegClass, 0
Anton Korobeynikov1dcce212008-03-22 21:04:01 +0000374 };
Evan Cheng25ab6902006-09-08 06:48:29 +0000375
Anton Korobeynikov1dcce212008-03-22 21:04:01 +0000376 if (Is64Bit) {
377 if (IsWin64)
378 return CalleeSavedRegClassesWin64;
379 else
Anton Korobeynikovb84c1672008-09-08 21:12:47 +0000380 return (callsEHReturn ?
381 CalleeSavedRegClasses64EHRet : CalleeSavedRegClasses64Bit);
Anton Korobeynikov1dcce212008-03-22 21:04:01 +0000382 } else {
Anton Korobeynikovb84c1672008-09-08 21:12:47 +0000383 return (callsEHReturn ?
384 CalleeSavedRegClasses32EHRet : CalleeSavedRegClasses32Bit);
Anton Korobeynikov2365f512007-07-14 14:06:15 +0000385 }
Evan Cheng0f3ac8d2006-05-18 00:12:58 +0000386}
387
Evan Chengb371f452007-02-19 21:49:54 +0000388BitVector X86RegisterInfo::getReservedRegs(const MachineFunction &MF) const {
389 BitVector Reserved(getNumRegs());
Dan Gohmana32b7ac2008-12-18 01:05:09 +0000390 // Set the stack-pointer register and its aliases as reserved.
Evan Chengb371f452007-02-19 21:49:54 +0000391 Reserved.set(X86::RSP);
392 Reserved.set(X86::ESP);
393 Reserved.set(X86::SP);
394 Reserved.set(X86::SPL);
Dan Gohmana32b7ac2008-12-18 01:05:09 +0000395 // Set the frame-pointer register and its aliases as reserved if needed.
Evan Chengb371f452007-02-19 21:49:54 +0000396 if (hasFP(MF)) {
397 Reserved.set(X86::RBP);
398 Reserved.set(X86::EBP);
399 Reserved.set(X86::BP);
400 Reserved.set(X86::BPL);
401 }
Dan Gohmana32b7ac2008-12-18 01:05:09 +0000402 // Mark the x87 stack registers as reserved, since they don't
403 // behave normally with respect to liveness. We don't fully
404 // model the effects of x87 stack pushes and pops after
405 // stackification.
406 Reserved.set(X86::ST0);
407 Reserved.set(X86::ST1);
408 Reserved.set(X86::ST2);
409 Reserved.set(X86::ST3);
410 Reserved.set(X86::ST4);
411 Reserved.set(X86::ST5);
412 Reserved.set(X86::ST6);
413 Reserved.set(X86::ST7);
Evan Chengb371f452007-02-19 21:49:54 +0000414 return Reserved;
415}
416
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000417//===----------------------------------------------------------------------===//
418// Stack Frame Processing methods
419//===----------------------------------------------------------------------===//
420
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000421static unsigned calculateMaxStackAlignment(const MachineFrameInfo *FFI) {
422 unsigned MaxAlign = 0;
423 for (int i = FFI->getObjectIndexBegin(),
424 e = FFI->getObjectIndexEnd(); i != e; ++i) {
425 if (FFI->isDeadObjectIndex(i))
426 continue;
427 unsigned Align = FFI->getObjectAlignment(i);
428 MaxAlign = std::max(MaxAlign, Align);
429 }
430
431 return MaxAlign;
432}
433
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000434// hasFP - Return true if the specified function should have a dedicated frame
435// pointer register. This is true if the function has variable sized allocas or
436// if frame pointer elimination is disabled.
437//
Evan Chengdc775402007-01-23 00:57:47 +0000438bool X86RegisterInfo::hasFP(const MachineFunction &MF) const {
Dan Gohman8e5f2c62008-07-07 23:14:23 +0000439 const MachineFrameInfo *MFI = MF.getFrameInfo();
440 const MachineModuleInfo *MMI = MFI->getMachineModuleInfo();
Anton Korobeynikov2365f512007-07-14 14:06:15 +0000441
Anton Korobeynikove2011902008-04-23 18:15:11 +0000442 return (NoFramePointerElim ||
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000443 needsStackRealignment(MF) ||
Evan Cheng7e7bbf82007-07-19 00:42:05 +0000444 MFI->hasVarSizedObjects() ||
Evan Cheng184793f2008-09-27 01:56:22 +0000445 MFI->isFrameAddressTaken() ||
Anton Korobeynikov2365f512007-07-14 14:06:15 +0000446 MF.getInfo<X86MachineFunctionInfo>()->getForceFramePointer() ||
447 (MMI && MMI->callsUnwindInit()));
Misha Brukman03c6faf2002-12-03 23:11:21 +0000448}
Misha Brukman2adb3952002-12-04 23:57:03 +0000449
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000450bool X86RegisterInfo::needsStackRealignment(const MachineFunction &MF) const {
Nick Lewycky9c0f1462009-03-19 05:51:39 +0000451 const MachineFrameInfo *MFI = MF.getFrameInfo();
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000452
Anton Korobeynikov35410a42008-04-23 18:16:43 +0000453 // FIXME: Currently we don't support stack realignment for functions with
454 // variable-sized allocas
Anton Korobeynikov941ff582008-04-23 18:24:25 +0000455 return (RealignStack &&
Anton Korobeynikov856914f2008-04-23 18:23:05 +0000456 (MFI->getMaxAlignment() > StackAlign &&
Anton Korobeynikovcfcd20e2008-04-23 18:17:11 +0000457 !MFI->hasVarSizedObjects()));
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000458}
459
Evan Cheng7e7bbf82007-07-19 00:42:05 +0000460bool X86RegisterInfo::hasReservedCallFrame(MachineFunction &MF) const {
461 return !MF.getFrameInfo()->hasVarSizedObjects();
462}
463
Evan Cheng910139f2009-07-09 06:53:48 +0000464bool X86RegisterInfo::hasReservedSpillSlot(MachineFunction &MF, unsigned Reg,
465 int &FrameIdx) const {
466 if (Reg == FramePtr && hasFP(MF)) {
467 FrameIdx = MF.getFrameInfo()->getObjectIndexBegin();
468 return true;
469 }
470 return false;
471}
472
473
Anton Korobeynikov82751e32008-04-23 18:18:36 +0000474int
475X86RegisterInfo::getFrameIndexOffset(MachineFunction &MF, int FI) const {
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000476 const TargetFrameInfo &TFI = *MF.getTarget().getFrameInfo();
477 MachineFrameInfo *MFI = MF.getFrameInfo();
478
479 int Offset = MFI->getObjectOffset(FI) - TFI.getOffsetOfLocalArea();
480 uint64_t StackSize = MFI->getStackSize();
Anton Korobeynikov82751e32008-04-23 18:18:36 +0000481
Anton Korobeynikov8e91ec52008-04-23 18:21:02 +0000482 if (needsStackRealignment(MF)) {
483 if (FI < 0)
484 // Skip the saved EBP
485 Offset += SlotSize;
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000486 else {
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000487 unsigned Align = MFI->getObjectAlignment(FI);
Dale Johannesenb5dae002008-06-26 01:51:13 +0000488 assert( (-(Offset + StackSize)) % Align == 0);
Devang Patelfd1c6c32008-12-23 21:56:28 +0000489 Align = 0;
Dale Johannesenb5dae002008-06-26 01:51:13 +0000490 return Offset + StackSize;
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000491 }
Anton Korobeynikovd1c133a2008-04-23 18:19:23 +0000492
Anton Korobeynikov8e91ec52008-04-23 18:21:02 +0000493 // FIXME: Support tail calls
494 } else {
495 if (!hasFP(MF))
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000496 return Offset + StackSize;
Anton Korobeynikov8e91ec52008-04-23 18:21:02 +0000497
498 // Skip the saved EBP
499 Offset += SlotSize;
500
501 // Skip the RETADDR move area
502 X86MachineFunctionInfo *X86FI = MF.getInfo<X86MachineFunctionInfo>();
503 int TailCallReturnAddrDelta = X86FI->getTCReturnAddrDelta();
504 if (TailCallReturnAddrDelta < 0) Offset -= TailCallReturnAddrDelta;
505 }
506
Anton Korobeynikov82751e32008-04-23 18:18:36 +0000507 return Offset;
508}
509
Chris Lattnerbb07ef92004-02-14 19:49:54 +0000510void X86RegisterInfo::
511eliminateCallFramePseudoInstr(MachineFunction &MF, MachineBasicBlock &MBB,
512 MachineBasicBlock::iterator I) const {
Evan Cheng7e7bbf82007-07-19 00:42:05 +0000513 if (!hasReservedCallFrame(MF)) {
514 // If the stack pointer can be changed after prologue, turn the
515 // adjcallstackup instruction into a 'sub ESP, <amt>' and the
516 // adjcallstackdown instruction into 'add ESP, <amt>'
517 // TODO: consider using push / pop instead of sub + store / add
Chris Lattnerbb07ef92004-02-14 19:49:54 +0000518 MachineInstr *Old = I;
Chris Lattner61807802007-04-25 04:25:10 +0000519 uint64_t Amount = Old->getOperand(0).getImm();
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000520 if (Amount != 0) {
Chris Lattnerf158da22003-01-16 02:20:12 +0000521 // We need to keep the stack aligned properly. To do this, we round the
522 // amount of space needed for the outgoing arguments up to the next
523 // alignment boundary.
Evan Chengdb807ed2007-11-05 07:30:01 +0000524 Amount = (Amount+StackAlign-1)/StackAlign*StackAlign;
Chris Lattnerf158da22003-01-16 02:20:12 +0000525
Chris Lattner3648c672005-05-13 21:44:04 +0000526 MachineInstr *New = 0;
Dan Gohman6d4b0522008-10-01 18:28:06 +0000527 if (Old->getOpcode() == getCallFrameSetupOpcode()) {
Dale Johannesen21b55412009-02-12 23:08:38 +0000528 New = BuildMI(MF, Old->getDebugLoc(),
529 TII.get(Is64Bit ? X86::SUB64ri32 : X86::SUB32ri),
Evan Chengbdf7b5d2008-08-25 21:58:43 +0000530 StackPtr).addReg(StackPtr).addImm(Amount);
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000531 } else {
Dan Gohman6d4b0522008-10-01 18:28:06 +0000532 assert(Old->getOpcode() == getCallFrameDestroyOpcode());
Chris Lattner3648c672005-05-13 21:44:04 +0000533 // factor out the amount the callee already popped.
Chris Lattner61807802007-04-25 04:25:10 +0000534 uint64_t CalleeAmt = Old->getOperand(1).getImm();
Chris Lattner3648c672005-05-13 21:44:04 +0000535 Amount -= CalleeAmt;
Chris Lattnerd77525d2006-02-03 18:20:04 +0000536 if (Amount) {
Evan Cheng25ab6902006-09-08 06:48:29 +0000537 unsigned Opc = (Amount < 128) ?
538 (Is64Bit ? X86::ADD64ri8 : X86::ADD32ri8) :
539 (Is64Bit ? X86::ADD64ri32 : X86::ADD32ri);
Dale Johannesen21b55412009-02-12 23:08:38 +0000540 New = BuildMI(MF, Old->getDebugLoc(), TII.get(Opc), StackPtr)
Evan Chengbdf7b5d2008-08-25 21:58:43 +0000541 .addReg(StackPtr).addImm(Amount);
Chris Lattnerd77525d2006-02-03 18:20:04 +0000542 }
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000543 }
Chris Lattnerbb07ef92004-02-14 19:49:54 +0000544
Dan Gohmand293e0d2009-02-11 19:50:24 +0000545 if (New) {
546 // The EFLAGS implicit def is dead.
547 New->getOperand(3).setIsDead();
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000548
Dan Gohmand293e0d2009-02-11 19:50:24 +0000549 // Replace the pseudo instruction with a new instruction...
550 MBB.insert(I, New);
551 }
Chris Lattner3648c672005-05-13 21:44:04 +0000552 }
Dan Gohman6d4b0522008-10-01 18:28:06 +0000553 } else if (I->getOpcode() == getCallFrameDestroyOpcode()) {
Chris Lattner3648c672005-05-13 21:44:04 +0000554 // If we are performing frame pointer elimination and if the callee pops
555 // something off the stack pointer, add it back. We do this until we have
556 // more advanced stack pointer tracking ability.
Chris Lattner61807802007-04-25 04:25:10 +0000557 if (uint64_t CalleeAmt = I->getOperand(1).getImm()) {
Evan Cheng25ab6902006-09-08 06:48:29 +0000558 unsigned Opc = (CalleeAmt < 128) ?
559 (Is64Bit ? X86::SUB64ri8 : X86::SUB32ri8) :
560 (Is64Bit ? X86::SUB64ri32 : X86::SUB32ri);
Dale Johannesen21b55412009-02-12 23:08:38 +0000561 MachineInstr *Old = I;
Jeff Cohen00b168892005-07-27 06:12:32 +0000562 MachineInstr *New =
Dale Johannesen21b55412009-02-12 23:08:38 +0000563 BuildMI(MF, Old->getDebugLoc(), TII.get(Opc),
564 StackPtr).addReg(StackPtr).addImm(CalleeAmt);
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000565 // The EFLAGS implicit def is dead.
566 New->getOperand(3).setIsDead();
567
Chris Lattnerbb07ef92004-02-14 19:49:54 +0000568 MBB.insert(I, New);
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000569 }
570 }
571
Chris Lattnerbb07ef92004-02-14 19:49:54 +0000572 MBB.erase(I);
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000573}
574
Evan Cheng5e6df462007-02-28 00:21:17 +0000575void X86RegisterInfo::eliminateFrameIndex(MachineBasicBlock::iterator II,
Evan Cheng97de9132007-05-01 09:13:03 +0000576 int SPAdj, RegScavenger *RS) const{
577 assert(SPAdj == 0 && "Unexpected");
578
Chris Lattnerd264bec2003-01-13 00:50:33 +0000579 unsigned i = 0;
Alkis Evlogimenosc0b9dc52004-02-12 02:27:10 +0000580 MachineInstr &MI = *II;
Nate Begemanf8be5e92004-08-14 22:05:10 +0000581 MachineFunction &MF = *MI.getParent()->getParent();
Dan Gohmand735b802008-10-03 15:45:36 +0000582 while (!MI.getOperand(i).isFI()) {
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000583 ++i;
584 assert(i < MI.getNumOperands() && "Instr doesn't have FrameIndex operand!");
585 }
586
Chris Lattner8aa797a2007-12-30 23:10:15 +0000587 int FrameIndex = MI.getOperand(i).getIndex();
Anton Korobeynikov8e91ec52008-04-23 18:21:02 +0000588
589 unsigned BasePtr;
590 if (needsStackRealignment(MF))
591 BasePtr = (FrameIndex < 0 ? FramePtr : StackPtr);
592 else
593 BasePtr = (hasFP(MF) ? FramePtr : StackPtr);
594
Chris Lattnerd264bec2003-01-13 00:50:33 +0000595 // This must be part of a four operand memory reference. Replace the
Evan Cheng25ab6902006-09-08 06:48:29 +0000596 // FrameIndex with base register with EBP. Add an offset to the offset.
Anton Korobeynikov8e91ec52008-04-23 18:21:02 +0000597 MI.getOperand(i).ChangeToRegister(BasePtr, false);
Chris Lattnerd264bec2003-01-13 00:50:33 +0000598
Dan Gohman82779702008-12-24 00:27:51 +0000599 // Now add the frame object offset to the offset from EBP.
600 if (MI.getOperand(i+3).isImm()) {
601 // Offset is a 32-bit integer.
602 int Offset = getFrameIndexOffset(MF, FrameIndex) +
603 (int)(MI.getOperand(i+3).getImm());
604
605 MI.getOperand(i+3).ChangeToImmediate(Offset);
606 } else {
607 // Offset is symbolic. This is extremely rare.
608 uint64_t Offset = getFrameIndexOffset(MF, FrameIndex) +
609 (uint64_t)MI.getOperand(i+3).getOffset();
610 MI.getOperand(i+3).setOffset(Offset);
611 }
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000612}
613
Chris Lattnerbb07ef92004-02-14 19:49:54 +0000614void
Anton Korobeynikovb51dce32008-04-23 18:20:17 +0000615X86RegisterInfo::processFunctionBeforeCalleeSavedScan(MachineFunction &MF,
616 RegScavenger *RS) const {
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000617 MachineFrameInfo *MFI = MF.getFrameInfo();
Anton Korobeynikovb51dce32008-04-23 18:20:17 +0000618
619 // Calculate and set max stack object alignment early, so we can decide
620 // whether we will need stack realignment (and thus FP).
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000621 unsigned MaxAlign = std::max(MFI->getMaxAlignment(),
622 calculateMaxStackAlignment(MFI));
Anton Korobeynikovb51dce32008-04-23 18:20:17 +0000623
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000624 MFI->setMaxAlignment(MaxAlign);
Anton Korobeynikovb51dce32008-04-23 18:20:17 +0000625
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000626 X86MachineFunctionInfo *X86FI = MF.getInfo<X86MachineFunctionInfo>();
627 int32_t TailCallReturnAddrDelta = X86FI->getTCReturnAddrDelta();
628 if (TailCallReturnAddrDelta < 0) {
629 // create RETURNADDR area
630 // arg
631 // arg
632 // RETADDR
633 // { ...
634 // RETADDR area
635 // ...
636 // }
637 // [EBP]
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000638 MFI->CreateFixedObject(-TailCallReturnAddrDelta,
639 (-1*SlotSize)+TailCallReturnAddrDelta);
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000640 }
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000641
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000642 if (hasFP(MF)) {
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000643 assert((TailCallReturnAddrDelta <= 0) &&
644 "The Delta should always be zero or negative");
Anton Korobeynikovdd93f5e2009-08-03 08:14:30 +0000645 const TargetFrameInfo &TFI = *MF.getTarget().getFrameInfo();
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000646 // Create a frame entry for the EBP register that must be saved.
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000647 int FrameIdx = MFI->CreateFixedObject(SlotSize,
Anton Korobeynikovdd93f5e2009-08-03 08:14:30 +0000648 -(int)SlotSize +
649 TFI.getOffsetOfLocalArea() +
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000650 TailCallReturnAddrDelta);
651 assert(FrameIdx == MFI->getObjectIndexBegin() &&
Chris Lattner96c3d2e2004-02-15 00:15:37 +0000652 "Slot for EBP register must be last in order to be found!");
Devang Patelfd1c6c32008-12-23 21:56:28 +0000653 FrameIdx = 0;
Chris Lattner3c1c03d2002-12-28 20:32:28 +0000654 }
655}
656
Evan Chenga24dddd2007-04-26 01:09:28 +0000657/// emitSPUpdate - Emit a series of instructions to increment / decrement the
658/// stack pointer by a constant value.
659static
660void emitSPUpdate(MachineBasicBlock &MBB, MachineBasicBlock::iterator &MBBI,
661 unsigned StackPtr, int64_t NumBytes, bool Is64Bit,
662 const TargetInstrInfo &TII) {
663 bool isSub = NumBytes < 0;
664 uint64_t Offset = isSub ? -NumBytes : NumBytes;
665 unsigned Opc = isSub
666 ? ((Offset < 128) ?
667 (Is64Bit ? X86::SUB64ri8 : X86::SUB32ri8) :
668 (Is64Bit ? X86::SUB64ri32 : X86::SUB32ri))
669 : ((Offset < 128) ?
670 (Is64Bit ? X86::ADD64ri8 : X86::ADD32ri8) :
671 (Is64Bit ? X86::ADD64ri32 : X86::ADD32ri));
672 uint64_t Chunk = (1LL << 31) - 1;
Bill Wendling5a45d762009-02-21 01:11:36 +0000673 DebugLoc DL = (MBBI != MBB.end() ? MBBI->getDebugLoc() :
674 DebugLoc::getUnknownLoc());
Evan Chenga24dddd2007-04-26 01:09:28 +0000675
676 while (Offset) {
677 uint64_t ThisVal = (Offset > Chunk) ? Chunk : Offset;
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000678 MachineInstr *MI =
Dale Johannesen8d13f8f2009-02-13 02:33:27 +0000679 BuildMI(MBB, MBBI, DL, TII.get(Opc), StackPtr)
680 .addReg(StackPtr).addImm(ThisVal);
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000681 // The EFLAGS implicit def is dead.
682 MI->getOperand(3).setIsDead();
Evan Chenga24dddd2007-04-26 01:09:28 +0000683 Offset -= ThisVal;
684 }
685}
686
Anton Korobeynikov4f1c33f2007-10-06 16:17:49 +0000687// mergeSPUpdatesUp - Merge two stack-manipulating instructions upper iterator.
688static
689void mergeSPUpdatesUp(MachineBasicBlock &MBB, MachineBasicBlock::iterator &MBBI,
690 unsigned StackPtr, uint64_t *NumBytes = NULL) {
Chris Lattnereac93852007-10-07 21:53:12 +0000691 if (MBBI == MBB.begin()) return;
Anton Korobeynikove2011902008-04-23 18:15:11 +0000692
Chris Lattnereac93852007-10-07 21:53:12 +0000693 MachineBasicBlock::iterator PI = prior(MBBI);
694 unsigned Opc = PI->getOpcode();
695 if ((Opc == X86::ADD64ri32 || Opc == X86::ADD64ri8 ||
696 Opc == X86::ADD32ri || Opc == X86::ADD32ri8) &&
697 PI->getOperand(0).getReg() == StackPtr) {
698 if (NumBytes)
699 *NumBytes += PI->getOperand(2).getImm();
700 MBB.erase(PI);
701 } else if ((Opc == X86::SUB64ri32 || Opc == X86::SUB64ri8 ||
702 Opc == X86::SUB32ri || Opc == X86::SUB32ri8) &&
703 PI->getOperand(0).getReg() == StackPtr) {
704 if (NumBytes)
705 *NumBytes -= PI->getOperand(2).getImm();
706 MBB.erase(PI);
Anton Korobeynikov4f1c33f2007-10-06 16:17:49 +0000707 }
708}
709
Anton Korobeynikov25083722007-10-06 16:39:43 +0000710// mergeSPUpdatesUp - Merge two stack-manipulating instructions lower iterator.
711static
Chris Lattnereac93852007-10-07 21:53:12 +0000712void mergeSPUpdatesDown(MachineBasicBlock &MBB,
713 MachineBasicBlock::iterator &MBBI,
Anton Korobeynikov25083722007-10-06 16:39:43 +0000714 unsigned StackPtr, uint64_t *NumBytes = NULL) {
Chris Lattnerf443ba72007-10-07 22:00:31 +0000715 return;
Anton Korobeynikove2011902008-04-23 18:15:11 +0000716
Chris Lattnereac93852007-10-07 21:53:12 +0000717 if (MBBI == MBB.end()) return;
Anton Korobeynikove2011902008-04-23 18:15:11 +0000718
Chris Lattnereac93852007-10-07 21:53:12 +0000719 MachineBasicBlock::iterator NI = next(MBBI);
720 if (NI == MBB.end()) return;
Anton Korobeynikove2011902008-04-23 18:15:11 +0000721
Chris Lattnereac93852007-10-07 21:53:12 +0000722 unsigned Opc = NI->getOpcode();
723 if ((Opc == X86::ADD64ri32 || Opc == X86::ADD64ri8 ||
724 Opc == X86::ADD32ri || Opc == X86::ADD32ri8) &&
725 NI->getOperand(0).getReg() == StackPtr) {
726 if (NumBytes)
727 *NumBytes -= NI->getOperand(2).getImm();
728 MBB.erase(NI);
729 MBBI = NI;
730 } else if ((Opc == X86::SUB64ri32 || Opc == X86::SUB64ri8 ||
731 Opc == X86::SUB32ri || Opc == X86::SUB32ri8) &&
732 NI->getOperand(0).getReg() == StackPtr) {
733 if (NumBytes)
734 *NumBytes += NI->getOperand(2).getImm();
735 MBB.erase(NI);
736 MBBI = NI;
Anton Korobeynikov25083722007-10-06 16:39:43 +0000737 }
738}
739
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000740/// mergeSPUpdates - Checks the instruction before/after the passed
Anton Korobeynikove2011902008-04-23 18:15:11 +0000741/// instruction. If it is an ADD/SUB instruction it is deleted
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000742/// argument and the stack adjustment is returned as a positive value for ADD
Anton Korobeynikove2011902008-04-23 18:15:11 +0000743/// and a negative for SUB.
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000744static int mergeSPUpdates(MachineBasicBlock &MBB,
745 MachineBasicBlock::iterator &MBBI,
Anton Korobeynikove2011902008-04-23 18:15:11 +0000746 unsigned StackPtr,
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000747 bool doMergeWithPrevious) {
748
749 if ((doMergeWithPrevious && MBBI == MBB.begin()) ||
750 (!doMergeWithPrevious && MBBI == MBB.end()))
751 return 0;
752
753 int Offset = 0;
754
755 MachineBasicBlock::iterator PI = doMergeWithPrevious ? prior(MBBI) : MBBI;
756 MachineBasicBlock::iterator NI = doMergeWithPrevious ? 0 : next(MBBI);
757 unsigned Opc = PI->getOpcode();
758 if ((Opc == X86::ADD64ri32 || Opc == X86::ADD64ri8 ||
759 Opc == X86::ADD32ri || Opc == X86::ADD32ri8) &&
760 PI->getOperand(0).getReg() == StackPtr){
761 Offset += PI->getOperand(2).getImm();
762 MBB.erase(PI);
763 if (!doMergeWithPrevious) MBBI = NI;
764 } else if ((Opc == X86::SUB64ri32 || Opc == X86::SUB64ri8 ||
765 Opc == X86::SUB32ri || Opc == X86::SUB32ri8) &&
766 PI->getOperand(0).getReg() == StackPtr) {
767 Offset -= PI->getOperand(2).getImm();
768 MBB.erase(PI);
769 if (!doMergeWithPrevious) MBBI = NI;
Anton Korobeynikove2011902008-04-23 18:15:11 +0000770 }
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000771
772 return Offset;
773}
774
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000775void X86RegisterInfo::emitCalleeSavedFrameMoves(MachineFunction &MF,
776 unsigned LabelId,
777 unsigned FramePtr) const {
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000778 MachineFrameInfo *MFI = MF.getFrameInfo();
779 MachineModuleInfo *MMI = MFI->getMachineModuleInfo();
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000780 if (!MMI) return;
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000781
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000782 // Add callee saved registers to move list.
783 const std::vector<CalleeSavedInfo> &CSI = MFI->getCalleeSavedInfo();
784 if (CSI.empty()) return;
785
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000786 std::vector<MachineMove> &Moves = MMI->getFrameMoves();
787 const TargetData *TD = MF.getTarget().getTargetData();
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000788 bool HasFP = hasFP(MF);
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000789
790 // Calculate amount of bytes used for return address storing
791 int stackGrowth =
792 (MF.getTarget().getFrameInfo()->getStackGrowthDirection() ==
793 TargetFrameInfo::StackGrowsUp ?
794 TD->getPointerSize() : -TD->getPointerSize());
795
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000796 // FIXME: This is dirty hack. The code itself is pretty mess right now.
797 // It should be rewritten from scratch and generalized sometimes.
798
799 // Determine maximum offset (minumum due to stack growth)
800 int64_t MaxOffset = 0;
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000801 for (std::vector<CalleeSavedInfo>::const_iterator
802 I = CSI.begin(), E = CSI.end(); I != E; ++I)
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000803 MaxOffset = std::min(MaxOffset,
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000804 MFI->getObjectOffset(I->getFrameIdx()));
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000805
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000806 // Calculate offsets.
807 int64_t saveAreaOffset = (HasFP ? 3 : 2) * stackGrowth;
808 for (std::vector<CalleeSavedInfo>::const_iterator
809 I = CSI.begin(), E = CSI.end(); I != E; ++I) {
810 int64_t Offset = MFI->getObjectOffset(I->getFrameIdx());
811 unsigned Reg = I->getReg();
812 Offset = MaxOffset - Offset + saveAreaOffset;
813
Duncan Sandsdaf22122009-07-23 19:00:02 +0000814 // Don't output a new machine move if we're re-saving the frame
815 // pointer. This happens when the PrologEpilogInserter has inserted an extra
816 // "PUSH" of the frame pointer -- the "emitPrologue" method automatically
817 // generates one when frame pointers are used. If we generate a "machine
818 // move" for this extra "PUSH", the linker will lose track of the fact that
819 // the frame pointer should have the value of the first "PUSH" when it's
820 // trying to unwind.
821 //
822 // FIXME: This looks inelegant. It's possibly correct, but it's covering up
823 // another bug. I.e., one where we generate a prolog like this:
824 //
825 // pushl %ebp
826 // movl %esp, %ebp
827 // pushl %ebp
828 // pushl %esi
829 // ...
830 //
831 // The immediate re-push of EBP is unnecessary. At the least, it's an
832 // optimization bug. EBP can be used as a scratch register in certain
833 // cases, but probably not when we have a frame pointer.
834 if (HasFP && FramePtr == Reg)
835 continue;
836
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000837 MachineLocation CSDst(MachineLocation::VirtualFP, Offset);
838 MachineLocation CSSrc(Reg);
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000839 Moves.push_back(MachineMove(LabelId, CSDst, CSSrc));
Bill Wendlingfe7f2942009-06-16 04:12:45 +0000840 }
Anton Korobeynikov9bbbea52008-04-23 18:15:48 +0000841}
842
Chris Lattnerbb07ef92004-02-14 19:49:54 +0000843void X86RegisterInfo::emitPrologue(MachineFunction &MF) const {
Chris Lattner198ab642002-12-15 20:06:35 +0000844 MachineBasicBlock &MBB = MF.front(); // Prolog goes in entry BB
Chris Lattnereafa4232003-01-15 22:57:35 +0000845 MachineFrameInfo *MFI = MF.getFrameInfo();
Evan Cheng3649b0e2006-06-02 22:38:37 +0000846 const Function* Fn = MF.getFunction();
847 const X86Subtarget* Subtarget = &MF.getTarget().getSubtarget<X86Subtarget>();
Jim Laskey44c3b9f2007-01-26 21:22:28 +0000848 MachineModuleInfo *MMI = MFI->getMachineModuleInfo();
Evan Cheng89d16592007-07-17 07:59:08 +0000849 X86MachineFunctionInfo *X86FI = MF.getInfo<X86MachineFunctionInfo>();
850 MachineBasicBlock::iterator MBBI = MBB.begin();
Anton Korobeynikove2011902008-04-23 18:15:11 +0000851 bool needsFrameMoves = (MMI && MMI->hasDebugInfo()) ||
Dale Johannesen4e1b7942008-04-08 00:10:24 +0000852 !Fn->doesNotThrow() ||
Dale Johannesen3541af72008-04-14 17:54:17 +0000853 UnwindTablesMandatory;
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000854 bool HasFP = hasFP(MF);
Devang Patel369de262009-06-17 00:48:26 +0000855 DebugLoc DL;
Bill Wendling3d2445f2009-02-21 00:43:56 +0000856
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000857 // Get the number of bytes to allocate from the FrameInfo.
Evan Cheng89d16592007-07-17 07:59:08 +0000858 uint64_t StackSize = MFI->getStackSize();
Bill Wendling3d2445f2009-02-21 00:43:56 +0000859
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000860 // Get desired stack alignment
861 uint64_t MaxAlign = MFI->getMaxAlignment();
862
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000863 // Add RETADDR move area to callee saved frame size.
864 int TailCallReturnAddrDelta = X86FI->getTCReturnAddrDelta();
Anton Korobeynikove2011902008-04-23 18:15:11 +0000865 if (TailCallReturnAddrDelta < 0)
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000866 X86FI->setCalleeSavedFrameSize(
867 X86FI->getCalleeSavedFrameSize() +(-TailCallReturnAddrDelta));
Evan Chengd9245ca2006-04-14 07:26:43 +0000868
Dan Gohman336b6362009-01-27 00:40:06 +0000869 // If this is x86-64 and the Red Zone is not disabled, if we are a leaf
870 // function, and use up to 128 bytes of stack space, don't have a frame
871 // pointer, calls, or dynamic alloca then we do not need to adjust the
872 // stack pointer (we fit in the Red Zone).
Devang Pateld18e31a2009-06-04 22:05:33 +0000873 bool DisableRedZone = Fn->hasFnAttr(Attribute::NoRedZone);
Dan Gohman336b6362009-01-27 00:40:06 +0000874 if (Is64Bit && !DisableRedZone &&
875 !needsStackRealignment(MF) &&
876 !MFI->hasVarSizedObjects() && // No dynamic alloca.
Eli Friedman9a417122009-06-04 02:02:01 +0000877 !MFI->hasCalls() && // No calls.
878 !Subtarget->isTargetWin64()) { // Win64 has no Red Zone
Dan Gohman336b6362009-01-27 00:40:06 +0000879 uint64_t MinSize = X86FI->getCalleeSavedFrameSize();
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000880 if (HasFP) MinSize += SlotSize;
Dan Gohman336b6362009-01-27 00:40:06 +0000881 StackSize = std::max(MinSize,
882 StackSize > 128 ? StackSize - 128 : 0);
883 MFI->setStackSize(StackSize);
Anton Korobeynikovcf6b7392009-08-03 08:12:53 +0000884 } else if (Subtarget->isTargetWin64()) {
885 // We need to always allocate 32 bytes as register spill area.
886 // FIXME: we might reuse these 32 bytes for leaf functions.
887 StackSize += 32;
888 MFI->setStackSize(StackSize);
Dan Gohman336b6362009-01-27 00:40:06 +0000889 }
890
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000891 // Insert stack pointer adjustment for later moving of return addr. Only
892 // applies to tail call optimized functions where the callee argument stack
893 // size is bigger than the callers.
894 if (TailCallReturnAddrDelta < 0) {
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000895 MachineInstr *MI =
Dale Johannesen21b55412009-02-12 23:08:38 +0000896 BuildMI(MBB, MBBI, DL, TII.get(Is64Bit? X86::SUB64ri32 : X86::SUB32ri),
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000897 StackPtr).addReg(StackPtr).addImm(-TailCallReturnAddrDelta);
898 // The EFLAGS implicit def is dead.
899 MI->getOperand(3).setIsDead();
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +0000900 }
901
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000902 // uint64_t StackSize = MFI->getStackSize();
903 std::vector<MachineMove> &Moves = MMI->getFrameMoves();
904 const TargetData *TD = MF.getTarget().getTargetData();
905 int stackGrowth =
906 (MF.getTarget().getFrameInfo()->getStackGrowthDirection() ==
907 TargetFrameInfo::StackGrowsUp ?
908 TD->getPointerSize() : -TD->getPointerSize());
909
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000910 uint64_t NumBytes = 0;
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000911 if (HasFP) {
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000912 // Calculate required stack adjustment
913 uint64_t FrameSize = StackSize - SlotSize;
914 if (needsStackRealignment(MF))
915 FrameSize = (FrameSize + MaxAlign - 1)/MaxAlign*MaxAlign;
916
917 NumBytes = FrameSize - X86FI->getCalleeSavedFrameSize();
918
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000919 // Get the offset of the stack slot for the EBP register, which is
Evan Cheng89d16592007-07-17 07:59:08 +0000920 // guaranteed to be the last slot by processFunctionBeforeFrameFinalized.
921 // Update the frame offset adjustment.
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000922 MFI->setOffsetAdjustment(-NumBytes);
Evan Cheng89d16592007-07-17 07:59:08 +0000923
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000924 // Save EBP/RBP into the appropriate stack slot...
Dale Johannesen21b55412009-02-12 23:08:38 +0000925 BuildMI(MBB, MBBI, DL, TII.get(Is64Bit ? X86::PUSH64r : X86::PUSH32r))
Bill Wendling587daed2009-05-13 21:33:08 +0000926 .addReg(FramePtr, RegState::Kill);
Evan Cheng89d16592007-07-17 07:59:08 +0000927
Bill Wendling92c1e122009-02-13 02:16:35 +0000928 if (needsFrameMoves) {
929 // Mark effective beginning of when frame pointer becomes valid.
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000930 unsigned FrameLabelId = MMI->NextLabelID();
Bill Wendling92c1e122009-02-13 02:16:35 +0000931 BuildMI(MBB, MBBI, DL, TII.get(X86::DBG_LABEL)).addImm(FrameLabelId);
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000932
933 // Define the current CFA rule to use the provided offset.
934 if (StackSize) {
935 MachineLocation SPDst(MachineLocation::VirtualFP);
936 MachineLocation SPSrc(MachineLocation::VirtualFP,
937 HasFP ? 2 * stackGrowth :
938 -StackSize + stackGrowth);
939 Moves.push_back(MachineMove(FrameLabelId, SPDst, SPSrc));
940 } else {
941 // FIXME: Verify & implement for FP
942 MachineLocation SPDst(StackPtr);
943 MachineLocation SPSrc(StackPtr, stackGrowth);
944 Moves.push_back(MachineMove(FrameLabelId, SPDst, SPSrc));
945 }
946
947 // Change the rule for the FramePtr to be an "offset" rule.
948 MachineLocation FPDst(MachineLocation::VirtualFP, 2 * stackGrowth);
949 MachineLocation FPSrc(FramePtr);
950 Moves.push_back(MachineMove(FrameLabelId, FPDst, FPSrc));
Bill Wendling92c1e122009-02-13 02:16:35 +0000951 }
952
Evan Cheng89d16592007-07-17 07:59:08 +0000953 // Update EBP with the new base value...
Dale Johannesen21b55412009-02-12 23:08:38 +0000954 BuildMI(MBB, MBBI, DL,
955 TII.get(Is64Bit ? X86::MOV64rr : X86::MOV32rr), FramePtr)
956 .addReg(StackPtr);
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000957
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000958 if (needsFrameMoves) {
959 unsigned FrameLabelId = MMI->NextLabelID();
960 BuildMI(MBB, MBBI, DL, TII.get(X86::DBG_LABEL)).addImm(FrameLabelId);
961
962 // Define the current CFA to use the EBP/RBP register.
963 MachineLocation FPDst(FramePtr);
964 MachineLocation FPSrc(MachineLocation::VirtualFP);
965 Moves.push_back(MachineMove(FrameLabelId, FPDst, FPSrc));
966 }
967
Dan Gohman34d6ad72008-12-18 22:01:52 +0000968 // Mark the FramePtr as live-in in every block except the entry.
969 for (MachineFunction::iterator I = next(MF.begin()), E = MF.end();
970 I != E; ++I)
971 I->addLiveIn(FramePtr);
972
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000973 // Realign stack
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000974 if (needsStackRealignment(MF)) {
975 MachineInstr *MI =
Dale Johannesen21b55412009-02-12 23:08:38 +0000976 BuildMI(MBB, MBBI, DL,
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000977 TII.get(Is64Bit ? X86::AND64ri32 : X86::AND32ri),
978 StackPtr).addReg(StackPtr).addImm(-MaxAlign);
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000979
Dan Gohmanbfd23c92008-12-18 22:03:42 +0000980 // The EFLAGS implicit def is dead.
981 MI->getOperand(3).setIsDead();
982 }
Bill Wendling3d2445f2009-02-21 00:43:56 +0000983 } else {
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +0000984 NumBytes = StackSize - X86FI->getCalleeSavedFrameSize();
Bill Wendling3d2445f2009-02-21 00:43:56 +0000985 }
Anton Korobeynikove2011902008-04-23 18:15:11 +0000986
Evan Cheng89d16592007-07-17 07:59:08 +0000987 // Skip the callee-saved push instructions.
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000988 bool RegsSaved = false;
Evan Cheng89d16592007-07-17 07:59:08 +0000989 while (MBBI != MBB.end() &&
990 (MBBI->getOpcode() == X86::PUSH32r ||
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000991 MBBI->getOpcode() == X86::PUSH64r)) {
992 RegsSaved = true;
Evan Cheng89d16592007-07-17 07:59:08 +0000993 ++MBBI;
Bill Wendlingc3d505c2009-07-08 21:02:53 +0000994 }
995
996 if (RegsSaved && needsFrameMoves) {
997 // Mark end of callee-saved push instructions.
998 unsigned LabelId = MMI->NextLabelID();
999 BuildMI(MBB, MBBI, DL, TII.get(X86::DBG_LABEL)).addImm(LabelId);
1000
1001 // Emit DWARF info specifying the offsets of the callee-saved registers.
Bill Wendlingd15f45f2009-07-09 22:30:02 +00001002 emitCalleeSavedFrameMoves(MF, LabelId, HasFP ? FramePtr : StackPtr);
Bill Wendlingc3d505c2009-07-08 21:02:53 +00001003 }
Evan Cheng89d16592007-07-17 07:59:08 +00001004
Bill Wendling3d2445f2009-02-21 00:43:56 +00001005 if (MBBI != MBB.end())
1006 DL = MBBI->getDebugLoc();
1007
Bill Wendling3ae67f52009-06-09 20:08:51 +00001008 // Adjust stack pointer: ESP -= numbytes.
1009 if (NumBytes >= 4096 && Subtarget->isTargetCygMing()) {
1010 // Check, whether EAX is livein for this function.
1011 bool isEAXAlive = false;
1012 for (MachineRegisterInfo::livein_iterator
Chris Lattner84bc5422007-12-31 04:13:23 +00001013 II = MF.getRegInfo().livein_begin(),
1014 EE = MF.getRegInfo().livein_end(); (II != EE) && !isEAXAlive; ++II) {
Bill Wendling3ae67f52009-06-09 20:08:51 +00001015 unsigned Reg = II->first;
1016 isEAXAlive = (Reg == X86::EAX || Reg == X86::AX ||
1017 Reg == X86::AH || Reg == X86::AL);
Evan Cheng004fb922006-06-13 05:14:44 +00001018 }
Bill Wendling3ae67f52009-06-09 20:08:51 +00001019
1020 // Function prologue calls _alloca to probe the stack when allocating more
1021 // than 4k bytes in one go. Touching the stack at 4K increments is necessary
1022 // to ensure that the guard pages used by the OS virtual memory manager are
1023 // allocated in correct sequence.
1024 if (!isEAXAlive) {
1025 BuildMI(MBB, MBBI, DL, TII.get(X86::MOV32ri), X86::EAX)
1026 .addImm(NumBytes);
1027 BuildMI(MBB, MBBI, DL, TII.get(X86::CALLpcrel32))
1028 .addExternalSymbol("_alloca");
1029 } else {
1030 // Save EAX
1031 BuildMI(MBB, MBBI, DL, TII.get(X86::PUSH32r))
1032 .addReg(X86::EAX, RegState::Kill);
1033
1034 // Allocate NumBytes-4 bytes on stack. We'll also use 4 already
1035 // allocated bytes for EAX.
1036 BuildMI(MBB, MBBI, DL, TII.get(X86::MOV32ri), X86::EAX)
1037 .addImm(NumBytes - 4);
1038 BuildMI(MBB, MBBI, DL, TII.get(X86::CALLpcrel32))
1039 .addExternalSymbol("_alloca");
1040
1041 // Restore EAX
1042 MachineInstr *MI = addRegOffset(BuildMI(MF, DL, TII.get(X86::MOV32rm),
1043 X86::EAX),
1044 StackPtr, false, NumBytes - 4);
1045 MBB.insert(MBBI, MI);
1046 }
1047 } else if (NumBytes) {
1048 // If there is an SUB32ri of ESP immediately before this instruction, merge
1049 // the two. This can be the case when tail call elimination is enabled and
1050 // the callee has more arguments then the caller.
1051 NumBytes -= mergeSPUpdates(MBB, MBBI, StackPtr, true);
1052
1053 // If there is an ADD32ri or SUB32ri of ESP immediately after this
1054 // instruction, merge the two instructions.
1055 mergeSPUpdatesDown(MBB, MBBI, StackPtr, &NumBytes);
1056
1057 if (NumBytes)
1058 emitSPUpdate(MBB, MBBI, StackPtr, -(int64_t)NumBytes, Is64Bit, TII);
Evan Chengd9245ca2006-04-14 07:26:43 +00001059 }
Bill Wendlingd15f45f2009-07-09 22:30:02 +00001060
Bill Wendling3bb9b9a2009-08-02 22:25:37 +00001061 if (!HasFP && needsFrameMoves) {
Bill Wendlingd15f45f2009-07-09 22:30:02 +00001062 // Mark end of stack pointer adjustment.
1063 unsigned LabelId = MMI->NextLabelID();
1064 BuildMI(MBB, MBBI, DL, TII.get(X86::DBG_LABEL)).addImm(LabelId);
1065
1066 // Define the current CFA rule to use the provided offset.
1067 if (StackSize) {
1068 MachineLocation SPDst(MachineLocation::VirtualFP);
1069 MachineLocation SPSrc(MachineLocation::VirtualFP,
1070 -StackSize + stackGrowth);
1071 Moves.push_back(MachineMove(LabelId, SPDst, SPSrc));
1072 } else {
1073 // FIXME: Verify & implement for FP
1074 MachineLocation SPDst(StackPtr);
1075 MachineLocation SPSrc(StackPtr, stackGrowth);
1076 Moves.push_back(MachineMove(LabelId, SPDst, SPSrc));
1077 }
1078 }
Misha Brukman2adb3952002-12-04 23:57:03 +00001079}
1080
Chris Lattnerbb07ef92004-02-14 19:49:54 +00001081void X86RegisterInfo::emitEpilogue(MachineFunction &MF,
1082 MachineBasicBlock &MBB) const {
Chris Lattneraa09b752002-12-28 21:08:28 +00001083 const MachineFrameInfo *MFI = MF.getFrameInfo();
Evan Cheng89d16592007-07-17 07:59:08 +00001084 X86MachineFunctionInfo *X86FI = MF.getInfo<X86MachineFunctionInfo>();
Alkis Evlogimenosf81af212004-02-14 01:18:34 +00001085 MachineBasicBlock::iterator MBBI = prior(MBB.end());
Anton Korobeynikov2365f512007-07-14 14:06:15 +00001086 unsigned RetOpcode = MBBI->getOpcode();
Bill Wendling2625f9b2009-02-21 00:32:08 +00001087 DebugLoc DL = MBBI->getDebugLoc();
Chris Lattner2b3d56e2005-05-14 23:35:21 +00001088
Anton Korobeynikov2365f512007-07-14 14:06:15 +00001089 switch (RetOpcode) {
Chris Lattner2b3d56e2005-05-14 23:35:21 +00001090 case X86::RET:
1091 case X86::RETI:
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +00001092 case X86::TCRETURNdi:
1093 case X86::TCRETURNri:
1094 case X86::TCRETURNri64:
1095 case X86::TCRETURNdi64:
Anton Korobeynikov2365f512007-07-14 14:06:15 +00001096 case X86::EH_RETURN:
Anton Korobeynikovb84c1672008-09-08 21:12:47 +00001097 case X86::EH_RETURN64:
Chris Lattner2b3d56e2005-05-14 23:35:21 +00001098 case X86::TAILJMPd:
1099 case X86::TAILJMPr:
1100 case X86::TAILJMPm: break; // These are ok
1101 default:
Torok Edwinc23197a2009-07-14 16:55:14 +00001102 llvm_unreachable("Can only insert epilog into returning blocks");
Chris Lattner2b3d56e2005-05-14 23:35:21 +00001103 }
Misha Brukman2adb3952002-12-04 23:57:03 +00001104
Evan Cheng89d16592007-07-17 07:59:08 +00001105 // Get the number of bytes to allocate from the FrameInfo
1106 uint64_t StackSize = MFI->getStackSize();
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001107 uint64_t MaxAlign = MFI->getMaxAlignment();
Evan Cheng89d16592007-07-17 07:59:08 +00001108 unsigned CSSize = X86FI->getCalleeSavedFrameSize();
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001109 uint64_t NumBytes = 0;
Evan Cheng89d16592007-07-17 07:59:08 +00001110
Chris Lattner3c1c03d2002-12-28 20:32:28 +00001111 if (hasFP(MF)) {
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001112 // Calculate required stack adjustment
1113 uint64_t FrameSize = StackSize - SlotSize;
1114 if (needsStackRealignment(MF))
1115 FrameSize = (FrameSize + MaxAlign - 1)/MaxAlign*MaxAlign;
1116
1117 NumBytes = FrameSize - CSSize;
1118
Evan Cheng89d16592007-07-17 07:59:08 +00001119 // pop EBP.
Bill Wendling3d2445f2009-02-21 00:43:56 +00001120 BuildMI(MBB, MBBI, DL,
Dale Johannesen21b55412009-02-12 23:08:38 +00001121 TII.get(Is64Bit ? X86::POP64r : X86::POP32r), FramePtr);
Bill Wendling2625f9b2009-02-21 00:32:08 +00001122 } else {
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001123 NumBytes = StackSize - CSSize;
Bill Wendling2625f9b2009-02-21 00:32:08 +00001124 }
Anton Korobeynikov2365f512007-07-14 14:06:15 +00001125
Evan Chengf27795d2007-07-17 18:03:34 +00001126 // Skip the callee-saved pop instructions.
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001127 MachineBasicBlock::iterator LastCSPop = MBBI;
Evan Chengf27795d2007-07-17 18:03:34 +00001128 while (MBBI != MBB.begin()) {
Evan Chengfcc87932007-07-26 17:45:41 +00001129 MachineBasicBlock::iterator PI = prior(MBBI);
1130 unsigned Opc = PI->getOpcode();
Bill Wendlingf7c09402008-10-31 18:30:19 +00001131 if (Opc != X86::POP32r && Opc != X86::POP64r &&
1132 !PI->getDesc().isTerminator())
Evan Chengf27795d2007-07-17 18:03:34 +00001133 break;
1134 --MBBI;
1135 }
1136
Bill Wendling3d2445f2009-02-21 00:43:56 +00001137 DL = MBBI->getDebugLoc();
1138
Anton Korobeynikov4f1c33f2007-10-06 16:17:49 +00001139 // If there is an ADD32ri or SUB32ri of ESP immediately before this
1140 // instruction, merge the two instructions.
1141 if (NumBytes || MFI->hasVarSizedObjects())
1142 mergeSPUpdatesUp(MBB, MBBI, StackPtr, &NumBytes);
Evan Cheng5b3332c2007-07-17 18:40:47 +00001143
Anton Korobeynikov4f1c33f2007-10-06 16:17:49 +00001144 // If dynamic alloca is used, then reset esp to point to the last callee-saved
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001145 // slot before popping them off! Same applies for the case, when stack was
1146 // realigned
1147 if (needsStackRealignment(MF)) {
1148 // We cannot use LEA here, because stack pointer was realigned. We need to
1149 // deallocate local frame back
Evan Cheng3c46eef2007-07-18 21:26:06 +00001150 if (CSSize) {
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001151 emitSPUpdate(MBB, MBBI, StackPtr, NumBytes, Is64Bit, TII);
1152 MBBI = prior(LastCSPop);
1153 }
1154
Dale Johannesen21b55412009-02-12 23:08:38 +00001155 BuildMI(MBB, MBBI, DL,
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001156 TII.get(Is64Bit ? X86::MOV64rr : X86::MOV32rr),
1157 StackPtr).addReg(FramePtr);
1158 } else if (MFI->hasVarSizedObjects()) {
1159 if (CSSize) {
1160 unsigned Opc = Is64Bit ? X86::LEA64r : X86::LEA32r;
Rafael Espindola094fad32009-04-08 21:14:34 +00001161 MachineInstr *MI = addLeaRegOffset(BuildMI(MF, DL, TII.get(Opc), StackPtr),
1162 FramePtr, false, -CSSize);
Evan Cheng3c46eef2007-07-18 21:26:06 +00001163 MBB.insert(MBBI, MI);
1164 } else
Dale Johannesen21b55412009-02-12 23:08:38 +00001165 BuildMI(MBB, MBBI, DL, TII.get(Is64Bit ? X86::MOV64rr : X86::MOV32rr),
Nate Begemanbeb572b2008-07-25 17:34:41 +00001166 StackPtr).addReg(FramePtr);
Evan Cheng3c46eef2007-07-18 21:26:06 +00001167
Anton Korobeynikov2c430cb2008-04-23 18:21:27 +00001168 } else {
1169 // adjust stack pointer back: ESP += numbytes
1170 if (NumBytes)
1171 emitSPUpdate(MBB, MBBI, StackPtr, NumBytes, Is64Bit, TII);
Evan Cheng3c46eef2007-07-18 21:26:06 +00001172 }
1173
Evan Cheng5b3332c2007-07-17 18:40:47 +00001174 // We're returning from function via eh_return.
Anton Korobeynikovb84c1672008-09-08 21:12:47 +00001175 if (RetOpcode == X86::EH_RETURN || RetOpcode == X86::EH_RETURN64) {
Evan Cheng5b3332c2007-07-17 18:40:47 +00001176 MBBI = prior(MBB.end());
1177 MachineOperand &DestAddr = MBBI->getOperand(0);
Dan Gohmand735b802008-10-03 15:45:36 +00001178 assert(DestAddr.isReg() && "Offset should be in register!");
Dale Johannesen21b55412009-02-12 23:08:38 +00001179 BuildMI(MBB, MBBI, DL,
Anton Korobeynikovb84c1672008-09-08 21:12:47 +00001180 TII.get(Is64Bit ? X86::MOV64rr : X86::MOV32rr),
1181 StackPtr).addReg(DestAddr.getReg());
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +00001182 // Tail call return: adjust the stack pointer and jump to callee
1183 } else if (RetOpcode == X86::TCRETURNri || RetOpcode == X86::TCRETURNdi ||
1184 RetOpcode== X86::TCRETURNri64 || RetOpcode == X86::TCRETURNdi64) {
1185 MBBI = prior(MBB.end());
1186 MachineOperand &JumpTarget = MBBI->getOperand(0);
1187 MachineOperand &StackAdjust = MBBI->getOperand(1);
Dan Gohmand735b802008-10-03 15:45:36 +00001188 assert(StackAdjust.isImm() && "Expecting immediate value.");
Anton Korobeynikove2011902008-04-23 18:15:11 +00001189
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +00001190 // Adjust stack pointer.
1191 int StackAdj = StackAdjust.getImm();
1192 int MaxTCDelta = X86FI->getTCReturnAddrDelta();
1193 int Offset = 0;
1194 assert(MaxTCDelta <= 0 && "MaxTCDelta should never be positive");
1195 // Incoporate the retaddr area.
1196 Offset = StackAdj-MaxTCDelta;
1197 assert(Offset >= 0 && "Offset should never be negative");
Bill Wendling3d2445f2009-02-21 00:43:56 +00001198
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +00001199 if (Offset) {
1200 // Check for possible merge with preceeding ADD instruction.
1201 Offset += mergeSPUpdates(MBB, MBBI, StackPtr, true);
1202 emitSPUpdate(MBB, MBBI, StackPtr, Offset, Is64Bit, TII);
Anton Korobeynikove2011902008-04-23 18:15:11 +00001203 }
Bill Wendling3d2445f2009-02-21 00:43:56 +00001204
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +00001205 // Jump to label or value in register.
1206 if (RetOpcode == X86::TCRETURNdi|| RetOpcode == X86::TCRETURNdi64)
Dale Johannesen21b55412009-02-12 23:08:38 +00001207 BuildMI(MBB, MBBI, DL, TII.get(X86::TAILJMPd)).
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +00001208 addGlobalAddress(JumpTarget.getGlobal(), JumpTarget.getOffset());
Bill Wendling3d2445f2009-02-21 00:43:56 +00001209 else if (RetOpcode== X86::TCRETURNri64)
Dale Johannesen21b55412009-02-12 23:08:38 +00001210 BuildMI(MBB, MBBI, DL, TII.get(X86::TAILJMPr64), JumpTarget.getReg());
Bill Wendling3d2445f2009-02-21 00:43:56 +00001211 else
Dale Johannesen21b55412009-02-12 23:08:38 +00001212 BuildMI(MBB, MBBI, DL, TII.get(X86::TAILJMPr), JumpTarget.getReg());
Bill Wendling3d2445f2009-02-21 00:43:56 +00001213
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +00001214 // Delete the pseudo instruction TCRETURN.
1215 MBB.erase(MBBI);
Anton Korobeynikove2011902008-04-23 18:15:11 +00001216 } else if ((RetOpcode == X86::RET || RetOpcode == X86::RETI) &&
Arnold Schwaighoferc85e1712007-10-11 19:40:01 +00001217 (X86FI->getTCReturnAddrDelta() < 0)) {
1218 // Add the return addr area delta back since we are not tail calling.
1219 int delta = -1*X86FI->getTCReturnAddrDelta();
1220 MBBI = prior(MBB.end());
1221 // Check for possible merge with preceeding ADD instruction.
1222 delta += mergeSPUpdates(MBB, MBBI, StackPtr, true);
1223 emitSPUpdate(MBB, MBBI, StackPtr, delta, Is64Bit, TII);
Evan Cheng5b3332c2007-07-17 18:40:47 +00001224 }
Chris Lattner3c1c03d2002-12-28 20:32:28 +00001225}
1226
Jim Laskey41886992006-04-07 16:34:46 +00001227unsigned X86RegisterInfo::getRARegister() const {
Anton Korobeynikov038082d2007-05-02 08:46:03 +00001228 if (Is64Bit)
1229 return X86::RIP; // Should have dwarf #16
1230 else
1231 return X86::EIP; // Should have dwarf #8
Jim Laskey41886992006-04-07 16:34:46 +00001232}
1233
Jim Laskeya9979182006-03-28 13:48:33 +00001234unsigned X86RegisterInfo::getFrameRegister(MachineFunction &MF) const {
Evan Cheng25ab6902006-09-08 06:48:29 +00001235 return hasFP(MF) ? FramePtr : StackPtr;
Jim Laskeyf1d78e82006-03-23 18:12:57 +00001236}
1237
Jim Laskey0e410942007-01-24 19:15:24 +00001238void X86RegisterInfo::getInitialFrameState(std::vector<MachineMove> &Moves)
1239 const {
Anton Korobeynikov0ff3ca42007-05-12 22:36:25 +00001240 // Calculate amount of bytes used for return address storing
1241 int stackGrowth = (Is64Bit ? -8 : -4);
1242
1243 // Initial state of the frame pointer is esp+4.
Jim Laskey0e410942007-01-24 19:15:24 +00001244 MachineLocation Dst(MachineLocation::VirtualFP);
Anton Korobeynikov0ff3ca42007-05-12 22:36:25 +00001245 MachineLocation Src(StackPtr, stackGrowth);
Jim Laskey0e410942007-01-24 19:15:24 +00001246 Moves.push_back(MachineMove(0, Dst, Src));
Anton Korobeynikov0ff3ca42007-05-12 22:36:25 +00001247
1248 // Add return address to move list
1249 MachineLocation CSDst(StackPtr, stackGrowth);
1250 MachineLocation CSSrc(getRARegister());
1251 Moves.push_back(MachineMove(0, CSDst, CSSrc));
Jim Laskey0e410942007-01-24 19:15:24 +00001252}
1253
Jim Laskey62819f32007-02-21 22:54:50 +00001254unsigned X86RegisterInfo::getEHExceptionRegister() const {
Torok Edwinc23197a2009-07-14 16:55:14 +00001255 llvm_unreachable("What is the exception register");
Jim Laskey62819f32007-02-21 22:54:50 +00001256 return 0;
1257}
1258
1259unsigned X86RegisterInfo::getEHHandlerRegister() const {
Torok Edwinc23197a2009-07-14 16:55:14 +00001260 llvm_unreachable("What is the exception handler register");
Jim Laskey62819f32007-02-21 22:54:50 +00001261 return 0;
1262}
1263
Evan Cheng8f7f7122006-05-05 05:40:20 +00001264namespace llvm {
Duncan Sands83ec4b62008-06-06 12:08:01 +00001265unsigned getX86SubSuperRegister(unsigned Reg, MVT VT, bool High) {
1266 switch (VT.getSimpleVT()) {
Evan Cheng8f7f7122006-05-05 05:40:20 +00001267 default: return Reg;
1268 case MVT::i8:
1269 if (High) {
1270 switch (Reg) {
Evan Cheng25ab6902006-09-08 06:48:29 +00001271 default: return 0;
1272 case X86::AH: case X86::AL: case X86::AX: case X86::EAX: case X86::RAX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001273 return X86::AH;
Evan Cheng25ab6902006-09-08 06:48:29 +00001274 case X86::DH: case X86::DL: case X86::DX: case X86::EDX: case X86::RDX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001275 return X86::DH;
Evan Cheng25ab6902006-09-08 06:48:29 +00001276 case X86::CH: case X86::CL: case X86::CX: case X86::ECX: case X86::RCX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001277 return X86::CH;
Evan Cheng25ab6902006-09-08 06:48:29 +00001278 case X86::BH: case X86::BL: case X86::BX: case X86::EBX: case X86::RBX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001279 return X86::BH;
1280 }
1281 } else {
1282 switch (Reg) {
Evan Cheng25ab6902006-09-08 06:48:29 +00001283 default: return 0;
1284 case X86::AH: case X86::AL: case X86::AX: case X86::EAX: case X86::RAX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001285 return X86::AL;
Evan Cheng25ab6902006-09-08 06:48:29 +00001286 case X86::DH: case X86::DL: case X86::DX: case X86::EDX: case X86::RDX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001287 return X86::DL;
Evan Cheng25ab6902006-09-08 06:48:29 +00001288 case X86::CH: case X86::CL: case X86::CX: case X86::ECX: case X86::RCX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001289 return X86::CL;
Evan Cheng25ab6902006-09-08 06:48:29 +00001290 case X86::BH: case X86::BL: case X86::BX: case X86::EBX: case X86::RBX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001291 return X86::BL;
Evan Cheng25ab6902006-09-08 06:48:29 +00001292 case X86::SIL: case X86::SI: case X86::ESI: case X86::RSI:
1293 return X86::SIL;
1294 case X86::DIL: case X86::DI: case X86::EDI: case X86::RDI:
1295 return X86::DIL;
1296 case X86::BPL: case X86::BP: case X86::EBP: case X86::RBP:
1297 return X86::BPL;
1298 case X86::SPL: case X86::SP: case X86::ESP: case X86::RSP:
1299 return X86::SPL;
1300 case X86::R8B: case X86::R8W: case X86::R8D: case X86::R8:
1301 return X86::R8B;
1302 case X86::R9B: case X86::R9W: case X86::R9D: case X86::R9:
1303 return X86::R9B;
1304 case X86::R10B: case X86::R10W: case X86::R10D: case X86::R10:
1305 return X86::R10B;
1306 case X86::R11B: case X86::R11W: case X86::R11D: case X86::R11:
1307 return X86::R11B;
1308 case X86::R12B: case X86::R12W: case X86::R12D: case X86::R12:
1309 return X86::R12B;
1310 case X86::R13B: case X86::R13W: case X86::R13D: case X86::R13:
1311 return X86::R13B;
1312 case X86::R14B: case X86::R14W: case X86::R14D: case X86::R14:
1313 return X86::R14B;
1314 case X86::R15B: case X86::R15W: case X86::R15D: case X86::R15:
1315 return X86::R15B;
Evan Cheng8f7f7122006-05-05 05:40:20 +00001316 }
1317 }
1318 case MVT::i16:
1319 switch (Reg) {
1320 default: return Reg;
Evan Cheng25ab6902006-09-08 06:48:29 +00001321 case X86::AH: case X86::AL: case X86::AX: case X86::EAX: case X86::RAX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001322 return X86::AX;
Evan Cheng25ab6902006-09-08 06:48:29 +00001323 case X86::DH: case X86::DL: case X86::DX: case X86::EDX: case X86::RDX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001324 return X86::DX;
Evan Cheng25ab6902006-09-08 06:48:29 +00001325 case X86::CH: case X86::CL: case X86::CX: case X86::ECX: case X86::RCX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001326 return X86::CX;
Evan Cheng25ab6902006-09-08 06:48:29 +00001327 case X86::BH: case X86::BL: case X86::BX: case X86::EBX: case X86::RBX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001328 return X86::BX;
Evan Cheng25ab6902006-09-08 06:48:29 +00001329 case X86::SIL: case X86::SI: case X86::ESI: case X86::RSI:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001330 return X86::SI;
Evan Cheng25ab6902006-09-08 06:48:29 +00001331 case X86::DIL: case X86::DI: case X86::EDI: case X86::RDI:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001332 return X86::DI;
Evan Cheng25ab6902006-09-08 06:48:29 +00001333 case X86::BPL: case X86::BP: case X86::EBP: case X86::RBP:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001334 return X86::BP;
Evan Cheng25ab6902006-09-08 06:48:29 +00001335 case X86::SPL: case X86::SP: case X86::ESP: case X86::RSP:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001336 return X86::SP;
Evan Cheng25ab6902006-09-08 06:48:29 +00001337 case X86::R8B: case X86::R8W: case X86::R8D: case X86::R8:
1338 return X86::R8W;
1339 case X86::R9B: case X86::R9W: case X86::R9D: case X86::R9:
1340 return X86::R9W;
1341 case X86::R10B: case X86::R10W: case X86::R10D: case X86::R10:
1342 return X86::R10W;
1343 case X86::R11B: case X86::R11W: case X86::R11D: case X86::R11:
1344 return X86::R11W;
1345 case X86::R12B: case X86::R12W: case X86::R12D: case X86::R12:
1346 return X86::R12W;
1347 case X86::R13B: case X86::R13W: case X86::R13D: case X86::R13:
1348 return X86::R13W;
1349 case X86::R14B: case X86::R14W: case X86::R14D: case X86::R14:
1350 return X86::R14W;
1351 case X86::R15B: case X86::R15W: case X86::R15D: case X86::R15:
1352 return X86::R15W;
Evan Cheng8f7f7122006-05-05 05:40:20 +00001353 }
1354 case MVT::i32:
1355 switch (Reg) {
Evan Cheng25ab6902006-09-08 06:48:29 +00001356 default: return Reg;
1357 case X86::AH: case X86::AL: case X86::AX: case X86::EAX: case X86::RAX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001358 return X86::EAX;
Evan Cheng25ab6902006-09-08 06:48:29 +00001359 case X86::DH: case X86::DL: case X86::DX: case X86::EDX: case X86::RDX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001360 return X86::EDX;
Evan Cheng25ab6902006-09-08 06:48:29 +00001361 case X86::CH: case X86::CL: case X86::CX: case X86::ECX: case X86::RCX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001362 return X86::ECX;
Evan Cheng25ab6902006-09-08 06:48:29 +00001363 case X86::BH: case X86::BL: case X86::BX: case X86::EBX: case X86::RBX:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001364 return X86::EBX;
Evan Cheng25ab6902006-09-08 06:48:29 +00001365 case X86::SIL: case X86::SI: case X86::ESI: case X86::RSI:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001366 return X86::ESI;
Evan Cheng25ab6902006-09-08 06:48:29 +00001367 case X86::DIL: case X86::DI: case X86::EDI: case X86::RDI:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001368 return X86::EDI;
Evan Cheng25ab6902006-09-08 06:48:29 +00001369 case X86::BPL: case X86::BP: case X86::EBP: case X86::RBP:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001370 return X86::EBP;
Evan Cheng25ab6902006-09-08 06:48:29 +00001371 case X86::SPL: case X86::SP: case X86::ESP: case X86::RSP:
Evan Cheng8f7f7122006-05-05 05:40:20 +00001372 return X86::ESP;
Evan Cheng25ab6902006-09-08 06:48:29 +00001373 case X86::R8B: case X86::R8W: case X86::R8D: case X86::R8:
1374 return X86::R8D;
1375 case X86::R9B: case X86::R9W: case X86::R9D: case X86::R9:
1376 return X86::R9D;
1377 case X86::R10B: case X86::R10W: case X86::R10D: case X86::R10:
1378 return X86::R10D;
1379 case X86::R11B: case X86::R11W: case X86::R11D: case X86::R11:
1380 return X86::R11D;
1381 case X86::R12B: case X86::R12W: case X86::R12D: case X86::R12:
1382 return X86::R12D;
1383 case X86::R13B: case X86::R13W: case X86::R13D: case X86::R13:
1384 return X86::R13D;
1385 case X86::R14B: case X86::R14W: case X86::R14D: case X86::R14:
1386 return X86::R14D;
1387 case X86::R15B: case X86::R15W: case X86::R15D: case X86::R15:
1388 return X86::R15D;
1389 }
1390 case MVT::i64:
1391 switch (Reg) {
1392 default: return Reg;
1393 case X86::AH: case X86::AL: case X86::AX: case X86::EAX: case X86::RAX:
1394 return X86::RAX;
1395 case X86::DH: case X86::DL: case X86::DX: case X86::EDX: case X86::RDX:
1396 return X86::RDX;
1397 case X86::CH: case X86::CL: case X86::CX: case X86::ECX: case X86::RCX:
1398 return X86::RCX;
1399 case X86::BH: case X86::BL: case X86::BX: case X86::EBX: case X86::RBX:
1400 return X86::RBX;
1401 case X86::SIL: case X86::SI: case X86::ESI: case X86::RSI:
1402 return X86::RSI;
1403 case X86::DIL: case X86::DI: case X86::EDI: case X86::RDI:
1404 return X86::RDI;
1405 case X86::BPL: case X86::BP: case X86::EBP: case X86::RBP:
1406 return X86::RBP;
1407 case X86::SPL: case X86::SP: case X86::ESP: case X86::RSP:
1408 return X86::RSP;
1409 case X86::R8B: case X86::R8W: case X86::R8D: case X86::R8:
1410 return X86::R8;
1411 case X86::R9B: case X86::R9W: case X86::R9D: case X86::R9:
1412 return X86::R9;
1413 case X86::R10B: case X86::R10W: case X86::R10D: case X86::R10:
1414 return X86::R10;
1415 case X86::R11B: case X86::R11W: case X86::R11D: case X86::R11:
1416 return X86::R11;
1417 case X86::R12B: case X86::R12W: case X86::R12D: case X86::R12:
1418 return X86::R12;
1419 case X86::R13B: case X86::R13W: case X86::R13D: case X86::R13:
1420 return X86::R13;
1421 case X86::R14B: case X86::R14W: case X86::R14D: case X86::R14:
1422 return X86::R14;
1423 case X86::R15B: case X86::R15W: case X86::R15D: case X86::R15:
1424 return X86::R15;
Evan Cheng8f7f7122006-05-05 05:40:20 +00001425 }
1426 }
1427
1428 return Reg;
1429}
1430}
1431
Chris Lattner7ad3e062003-08-03 15:48:14 +00001432#include "X86GenRegisterInfo.inc"
Anton Korobeynikov856914f2008-04-23 18:23:05 +00001433
1434namespace {
1435 struct VISIBILITY_HIDDEN MSAC : public MachineFunctionPass {
1436 static char ID;
Dan Gohmanae73dc12008-09-04 17:05:41 +00001437 MSAC() : MachineFunctionPass(&ID) {}
Anton Korobeynikov856914f2008-04-23 18:23:05 +00001438
1439 virtual bool runOnMachineFunction(MachineFunction &MF) {
1440 MachineFrameInfo *FFI = MF.getFrameInfo();
Anton Korobeynikovd52bdaf2008-04-23 18:23:30 +00001441 MachineRegisterInfo &RI = MF.getRegInfo();
Anton Korobeynikov856914f2008-04-23 18:23:05 +00001442
Anton Korobeynikovd52bdaf2008-04-23 18:23:30 +00001443 // Calculate max stack alignment of all already allocated stack objects.
Anton Korobeynikov856914f2008-04-23 18:23:05 +00001444 unsigned MaxAlign = calculateMaxStackAlignment(FFI);
1445
Anton Korobeynikovd52bdaf2008-04-23 18:23:30 +00001446 // Be over-conservative: scan over all vreg defs and find, whether vector
1447 // registers are used. If yes - there is probability, that vector register
1448 // will be spilled and thus stack needs to be aligned properly.
1449 for (unsigned RegNum = TargetRegisterInfo::FirstVirtualRegister;
1450 RegNum < RI.getLastVirtReg(); ++RegNum)
1451 MaxAlign = std::max(MaxAlign, RI.getRegClass(RegNum)->getAlignment());
1452
Dan Gohman92aa4042009-08-01 00:31:02 +00001453 if (FFI->getMaxAlignment() == MaxAlign)
1454 return false;
Anton Korobeynikov856914f2008-04-23 18:23:05 +00001455
Dan Gohman92aa4042009-08-01 00:31:02 +00001456 FFI->setMaxAlignment(MaxAlign);
1457 return true;
Anton Korobeynikov856914f2008-04-23 18:23:05 +00001458 }
1459
1460 virtual const char *getPassName() const {
1461 return "X86 Maximal Stack Alignment Calculator";
1462 }
Dan Gohman92aa4042009-08-01 00:31:02 +00001463
1464 virtual void getAnalysisUsage(AnalysisUsage &AU) const {
1465 AU.setPreservesCFG();
1466 MachineFunctionPass::getAnalysisUsage(AU);
1467 }
Anton Korobeynikov856914f2008-04-23 18:23:05 +00001468 };
1469
1470 char MSAC::ID = 0;
1471}
1472
1473FunctionPass*
1474llvm::createX86MaxStackAlignmentCalculatorPass() { return new MSAC(); }