From ee465749313579ccd91575ca8acf70b75c221a2c Mon Sep 17 00:00:00 2001 From: Duncan Sands Date: Wed, 29 Aug 2007 19:01:20 +0000 Subject: [PATCH] Move getX86RegNum into X86RegisterInfo and use it in the trampoline lowering. Lookup the jump and mov opcodes for the trampoline rather than hard coding them. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@41577 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/X86/X86CodeEmitter.cpp | 55 +----------------------------- lib/Target/X86/X86CodeEmitter.h | 25 -------------- lib/Target/X86/X86ISelLowering.cpp | 18 +++++----- lib/Target/X86/X86InstrInfo.h | 5 ++- lib/Target/X86/X86RegisterInfo.cpp | 53 ++++++++++++++++++++++++++++ lib/Target/X86/X86RegisterInfo.h | 12 +++++++ 6 files changed, 80 insertions(+), 88 deletions(-) delete mode 100644 lib/Target/X86/X86CodeEmitter.h diff --git a/lib/Target/X86/X86CodeEmitter.cpp b/lib/Target/X86/X86CodeEmitter.cpp index 0a7beb251a7..90d361bc2f3 100644 --- a/lib/Target/X86/X86CodeEmitter.cpp +++ b/lib/Target/X86/X86CodeEmitter.cpp @@ -13,7 +13,6 @@ //===----------------------------------------------------------------------===// #define DEBUG_TYPE "x86-emitter" -#include "X86CodeEmitter.h" #include "X86InstrInfo.h" #include "X86Subtarget.h" #include "X86TargetMachine.h" @@ -193,60 +192,8 @@ void Emitter::emitJumpTableAddress(unsigned JTI, unsigned Reloc, MCE.emitWordLE(0); // The relocated value will be added to the displacement } -// getX86RegNum - This function maps LLVM register identifiers to their X86 -// specific numbering, which is used in various places encoding instructions. -// unsigned Emitter::getX86RegNum(unsigned RegNo) { - switch(RegNo) { - case X86::RAX: case X86::EAX: case X86::AX: case X86::AL: return N86::EAX; - case X86::RCX: case X86::ECX: case X86::CX: case X86::CL: return N86::ECX; - case X86::RDX: case X86::EDX: case X86::DX: case X86::DL: return N86::EDX; - case X86::RBX: case X86::EBX: case X86::BX: case X86::BL: return N86::EBX; - case X86::RSP: case X86::ESP: case X86::SP: case X86::SPL: case X86::AH: - return N86::ESP; - case X86::RBP: case X86::EBP: case X86::BP: case X86::BPL: case X86::CH: - return N86::EBP; - case X86::RSI: case X86::ESI: case X86::SI: case X86::SIL: case X86::DH: - return N86::ESI; - case X86::RDI: case X86::EDI: case X86::DI: case X86::DIL: case X86::BH: - return N86::EDI; - - case X86::R8: case X86::R8D: case X86::R8W: case X86::R8B: - return N86::EAX; - case X86::R9: case X86::R9D: case X86::R9W: case X86::R9B: - return N86::ECX; - case X86::R10: case X86::R10D: case X86::R10W: case X86::R10B: - return N86::EDX; - case X86::R11: case X86::R11D: case X86::R11W: case X86::R11B: - return N86::EBX; - case X86::R12: case X86::R12D: case X86::R12W: case X86::R12B: - return N86::ESP; - case X86::R13: case X86::R13D: case X86::R13W: case X86::R13B: - return N86::EBP; - case X86::R14: case X86::R14D: case X86::R14W: case X86::R14B: - return N86::ESI; - case X86::R15: case X86::R15D: case X86::R15W: case X86::R15B: - return N86::EDI; - - case X86::ST0: case X86::ST1: case X86::ST2: case X86::ST3: - case X86::ST4: case X86::ST5: case X86::ST6: case X86::ST7: - return RegNo-X86::ST0; - - case X86::XMM0: case X86::XMM1: case X86::XMM2: case X86::XMM3: - case X86::XMM4: case X86::XMM5: case X86::XMM6: case X86::XMM7: - return II->getRegisterInfo().getDwarfRegNum(RegNo) - - II->getRegisterInfo().getDwarfRegNum(X86::XMM0); - case X86::XMM8: case X86::XMM9: case X86::XMM10: case X86::XMM11: - case X86::XMM12: case X86::XMM13: case X86::XMM14: case X86::XMM15: - return II->getRegisterInfo().getDwarfRegNum(RegNo) - - II->getRegisterInfo().getDwarfRegNum(X86::XMM8); - - default: - assert(MRegisterInfo::isVirtualRegister(RegNo) && - "Unknown physical register!"); - assert(0 && "Register allocator hasn't allocated reg correctly yet!"); - return 0; - } + return ((X86RegisterInfo&)II->getRegisterInfo()).getX86RegNum(RegNo); } inline static unsigned char ModRMByte(unsigned Mod, unsigned RegOpcode, diff --git a/lib/Target/X86/X86CodeEmitter.h b/lib/Target/X86/X86CodeEmitter.h deleted file mode 100644 index f3e9dc0b473..00000000000 --- a/lib/Target/X86/X86CodeEmitter.h +++ /dev/null @@ -1,25 +0,0 @@ -//===-- X86CodeEmitter.h - X86 DAG Lowering Interface -----------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file was developed by Duncan Sands and is distributed under -// the University of Illinois Open Source License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// -// -// This file defines utilities for X86 code emission. -// -//===----------------------------------------------------------------------===// - -#ifndef X86CODEEMITTER_H -#define X86CODEEMITTER_H - -/// N86 namespace - Native X86 Register numbers... used by X86 backend. -/// -namespace N86 { - enum { - EAX = 0, ECX = 1, EDX = 2, EBX = 3, ESP = 4, EBP = 5, ESI = 6, EDI = 7 - }; -} - -#endif // X86CODEEMITTER_H diff --git a/lib/Target/X86/X86ISelLowering.cpp b/lib/Target/X86/X86ISelLowering.cpp index 2e9dce36f13..7ebac836dd7 100644 --- a/lib/Target/X86/X86ISelLowering.cpp +++ b/lib/Target/X86/X86ISelLowering.cpp @@ -13,7 +13,6 @@ //===----------------------------------------------------------------------===// #include "X86.h" -#include "X86CodeEmitter.h" #include "X86InstrBuilder.h" #include "X86ISelLowering.h" #include "X86MachineFunctionInfo.h" @@ -4330,7 +4329,7 @@ SDOperand X86TargetLowering::LowerTRAMPOLINE(SDOperand Op, Function *Func = (Function *) cast(cast(Op.getOperand(5))->getValue()); unsigned CC = Func->getCallingConv(); - unsigned char NestReg; + unsigned NestReg; switch (CC) { default: @@ -4340,7 +4339,7 @@ SDOperand X86TargetLowering::LowerTRAMPOLINE(SDOperand Op, case CallingConv::X86_StdCall: { // Pass 'nest' parameter in ECX. // Must be kept in sync with X86CallingConv.td - NestReg = N86::ECX; + NestReg = X86::ECX; // Check that ECX wasn't needed by an 'inreg' parameter. const FunctionType *FTy = Func->getFunctionType(); @@ -4366,26 +4365,29 @@ SDOperand X86TargetLowering::LowerTRAMPOLINE(SDOperand Op, case CallingConv::X86_FastCall: // Pass 'nest' parameter in EAX. // Must be kept in sync with X86CallingConv.td - NestReg = N86::EAX; + NestReg = X86::EAX; break; } + const X86InstrInfo *TII = + ((X86TargetMachine&)getTargetMachine()).getInstrInfo(); + SDOperand OutChains[4]; SDOperand Addr, Disp; Addr = DAG.getNode(ISD::ADD, MVT::i32, Trmp, DAG.getConstant(10, MVT::i32)); Disp = DAG.getNode(ISD::SUB, MVT::i32, FPtr, Addr); - const unsigned char MOV32ri = 0xB8; - const unsigned char JMP = 0xE9; - - OutChains[0] = DAG.getStore(Root, DAG.getConstant(MOV32ri|NestReg, MVT::i8), + unsigned char MOV32ri = TII->getBaseOpcodeFor(X86::MOV32ri); + unsigned char N86Reg = ((X86RegisterInfo&)RegInfo).getX86RegNum(NestReg); + OutChains[0] = DAG.getStore(Root, DAG.getConstant(MOV32ri|N86Reg, MVT::i8), Trmp, TrmpSV->getValue(), TrmpSV->getOffset()); Addr = DAG.getNode(ISD::ADD, MVT::i32, Trmp, DAG.getConstant(1, MVT::i32)); OutChains[1] = DAG.getStore(Root, Nest, Addr, TrmpSV->getValue(), TrmpSV->getOffset() + 1, false, 1); + unsigned char JMP = TII->getBaseOpcodeFor(X86::JMP); Addr = DAG.getNode(ISD::ADD, MVT::i32, Trmp, DAG.getConstant(5, MVT::i32)); OutChains[2] = DAG.getStore(Root, DAG.getConstant(JMP, MVT::i8), Addr, TrmpSV->getValue() + 5, TrmpSV->getOffset()); diff --git a/lib/Target/X86/X86InstrInfo.h b/lib/Target/X86/X86InstrInfo.h index ec30cc7c8c9..2694481caab 100644 --- a/lib/Target/X86/X86InstrInfo.h +++ b/lib/Target/X86/X86InstrInfo.h @@ -275,11 +275,14 @@ public: const TargetRegisterClass *getPointerRegClass() const; // getBaseOpcodeFor - This function returns the "base" X86 opcode for the - // specified opcode number. + // specified machine instruction. // unsigned char getBaseOpcodeFor(const TargetInstrDescriptor *TID) const { return TID->TSFlags >> X86II::OpcodeShift; } + unsigned char getBaseOpcodeFor(MachineOpCode Opcode) const { + return getBaseOpcodeFor(&get(Opcode)); + } }; } // End llvm namespace diff --git a/lib/Target/X86/X86RegisterInfo.cpp b/lib/Target/X86/X86RegisterInfo.cpp index bd4179f3486..11c754759d1 100644 --- a/lib/Target/X86/X86RegisterInfo.cpp +++ b/lib/Target/X86/X86RegisterInfo.cpp @@ -65,6 +65,59 @@ X86RegisterInfo::X86RegisterInfo(X86TargetMachine &tm, } } +// getX86RegNum - This function maps LLVM register identifiers to their X86 +// specific numbering, which is used in various places encoding instructions. +// +unsigned X86RegisterInfo::getX86RegNum(unsigned RegNo) { + switch(RegNo) { + case X86::RAX: case X86::EAX: case X86::AX: case X86::AL: return N86::EAX; + case X86::RCX: case X86::ECX: case X86::CX: case X86::CL: return N86::ECX; + case X86::RDX: case X86::EDX: case X86::DX: case X86::DL: return N86::EDX; + case X86::RBX: case X86::EBX: case X86::BX: case X86::BL: return N86::EBX; + case X86::RSP: case X86::ESP: case X86::SP: case X86::SPL: case X86::AH: + return N86::ESP; + case X86::RBP: case X86::EBP: case X86::BP: case X86::BPL: case X86::CH: + return N86::EBP; + case X86::RSI: case X86::ESI: case X86::SI: case X86::SIL: case X86::DH: + return N86::ESI; + case X86::RDI: case X86::EDI: case X86::DI: case X86::DIL: case X86::BH: + return N86::EDI; + + case X86::R8: case X86::R8D: case X86::R8W: case X86::R8B: + return N86::EAX; + case X86::R9: case X86::R9D: case X86::R9W: case X86::R9B: + return N86::ECX; + case X86::R10: case X86::R10D: case X86::R10W: case X86::R10B: + return N86::EDX; + case X86::R11: case X86::R11D: case X86::R11W: case X86::R11B: + return N86::EBX; + case X86::R12: case X86::R12D: case X86::R12W: case X86::R12B: + return N86::ESP; + case X86::R13: case X86::R13D: case X86::R13W: case X86::R13B: + return N86::EBP; + case X86::R14: case X86::R14D: case X86::R14W: case X86::R14B: + return N86::ESI; + case X86::R15: case X86::R15D: case X86::R15W: case X86::R15B: + return N86::EDI; + + case X86::ST0: case X86::ST1: case X86::ST2: case X86::ST3: + case X86::ST4: case X86::ST5: case X86::ST6: case X86::ST7: + return RegNo-X86::ST0; + + case X86::XMM0: case X86::XMM1: case X86::XMM2: case X86::XMM3: + case X86::XMM4: case X86::XMM5: case X86::XMM6: case X86::XMM7: + return getDwarfRegNum(RegNo) - getDwarfRegNum(X86::XMM0); + case X86::XMM8: case X86::XMM9: case X86::XMM10: case X86::XMM11: + case X86::XMM12: case X86::XMM13: case X86::XMM14: case X86::XMM15: + return getDwarfRegNum(RegNo) - getDwarfRegNum(X86::XMM8); + + default: + assert(isVirtualRegister(RegNo) && "Unknown physical register!"); + assert(0 && "Register allocator hasn't allocated reg correctly yet!"); + return 0; + } +} + bool X86RegisterInfo::spillCalleeSavedRegisters(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, const std::vector &CSI) const { diff --git a/lib/Target/X86/X86RegisterInfo.h b/lib/Target/X86/X86RegisterInfo.h index cdec55f3297..bcfba246adf 100644 --- a/lib/Target/X86/X86RegisterInfo.h +++ b/lib/Target/X86/X86RegisterInfo.h @@ -22,6 +22,14 @@ namespace llvm { class TargetInstrInfo; class X86TargetMachine; +/// N86 namespace - Native X86 register numbers +/// +namespace N86 { + enum { + EAX = 0, ECX = 1, EDX = 2, EBX = 3, ESP = 4, EBP = 5, ESI = 6, EDI = 7 + }; +} + class X86RegisterInfo : public X86GenRegisterInfo { public: X86TargetMachine &TM; @@ -43,6 +51,10 @@ private: public: X86RegisterInfo(X86TargetMachine &tm, const TargetInstrInfo &tii); + /// getX86RegNum - Returns the native X86 register number for the given LLVM + /// register identifier. + unsigned getX86RegNum(unsigned RegNo); + /// Code Generation virtual methods... bool spillCalleeSavedRegisters(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,