summaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authordim <dim@FreeBSD.org>2011-12-09 18:27:22 +0000
committerdim <dim@FreeBSD.org>2011-12-09 18:27:22 +0000
commit07637c87f826cdf411f0673595e9bc92ebd793f2 (patch)
treed5baf24dba561bcf8bc6ec60db36bfc5586f6378 /lib
parent7b3392326c40c3c20697816acae597ba7b3144eb (diff)
downloadFreeBSD-src-07637c87f826cdf411f0673595e9bc92ebd793f2.zip
FreeBSD-src-07637c87f826cdf411f0673595e9bc92ebd793f2.tar.gz
Vendor import of llvm 3.0 final release:
http://llvm.org/svn/llvm-project/llvm/tags/RELEASE_30/final@145349
Diffstat (limited to 'lib')
-rw-r--r--lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp16
-rw-r--r--lib/CodeGen/LLVMTargetMachine.cpp3
-rw-r--r--lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp11
-rw-r--r--lib/CodeGen/TargetLoweringObjectFileImpl.cpp8
-rw-r--r--lib/Target/ARM/ARMBaseRegisterInfo.cpp15
-rw-r--r--lib/Target/ARM/ARMCallingConv.td19
-rw-r--r--lib/Target/ARM/ARMFastISel.cpp5
-rw-r--r--lib/Target/ARM/ARMFrameLowering.cpp10
-rw-r--r--lib/Target/ARM/ARMISelLowering.cpp2
-rw-r--r--lib/Target/ARM/ARMInstrThumb2.td12
-rw-r--r--lib/Target/CppBackend/CPPBackend.cpp99
-rw-r--r--lib/Target/Mips/CMakeLists.txt1
-rw-r--r--lib/Target/Mips/Makefile2
-rw-r--r--lib/Target/Mips/Mips64InstrInfo.td40
-rw-r--r--lib/Target/Mips/MipsCodeEmitter.cpp31
-rw-r--r--lib/Target/Mips/MipsInstrFPU.td56
-rw-r--r--lib/Target/Mips/MipsInstrFormats.td83
-rw-r--r--lib/Target/Mips/MipsInstrInfo.td97
-rw-r--r--lib/Target/Mips/MipsJITInfo.cpp14
-rw-r--r--lib/Target/PowerPC/PPCFrameLowering.cpp4
-rw-r--r--lib/Target/X86/X86CodeEmitter.cpp33
-rw-r--r--lib/Transforms/InstCombine/InstructionCombining.cpp7
22 files changed, 407 insertions, 161 deletions
diff --git a/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp b/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
index 88b7524..6fe476d 100644
--- a/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
+++ b/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
@@ -527,18 +527,20 @@ bool CompileUnit::addConstantValue(DIE *Die, const ConstantInt *CI,
// Get the raw data form of the large APInt.
const APInt Val = CI->getValue();
- const char *Ptr = (const char*)Val.getRawData();
+ const uint64_t *Ptr64 = Val.getRawData();
int NumBytes = Val.getBitWidth() / 8; // 8 bits per byte.
bool LittleEndian = Asm->getTargetData().isLittleEndian();
- int Incr = (LittleEndian ? 1 : -1);
- int Start = (LittleEndian ? 0 : NumBytes - 1);
- int Stop = (LittleEndian ? NumBytes : -1);
// Output the constant to DWARF one byte at a time.
- for (; Start != Stop; Start += Incr)
- addUInt(Block, 0, dwarf::DW_FORM_data1,
- (unsigned char)0xFF & Ptr[Start]);
+ for (int i = 0; i < NumBytes; i++) {
+ uint8_t c;
+ if (LittleEndian)
+ c = Ptr64[i / 8] >> (8 * (i & 7));
+ else
+ c = Ptr64[(NumBytes - 1 - i) / 8] >> (8 * ((NumBytes - 1 - i) & 7));
+ addUInt(Block, 0, dwarf::DW_FORM_data1, c);
+ }
addBlock(Die, dwarf::DW_AT_const_value, 0, Block);
return true;
diff --git a/lib/CodeGen/LLVMTargetMachine.cpp b/lib/CodeGen/LLVMTargetMachine.cpp
index 80ecc22..187147a 100644
--- a/lib/CodeGen/LLVMTargetMachine.cpp
+++ b/lib/CodeGen/LLVMTargetMachine.cpp
@@ -119,7 +119,8 @@ LLVMTargetMachine::LLVMTargetMachine(const Target &T, StringRef Triple,
// we'll crash later.
// Provide the user with a useful error message about what's wrong.
assert(AsmInfo && "MCAsmInfo not initialized."
- "Make sure you include the correct TargetSelect.h!");
+ "Make sure you include the correct TargetSelect.h"
+ "and that InitializeAllTargetMCs() is being invoked!");
}
bool LLVMTargetMachine::addPassesToEmitFile(PassManagerBase &PM,
diff --git a/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp b/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
index 7ed46a6..095b400 100644
--- a/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
+++ b/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
@@ -2034,14 +2034,17 @@ bool SelectionDAGBuilder::handleJTSwitchCase(CaseRec &CR,
return false;
APInt Range = ComputeRange(First, Last);
- double Density = TSize.roundToDouble() / Range.roundToDouble();
- if (Density < 0.4)
+ // The density is TSize / Range. Require at least 40%.
+ // It should not be possible for IntTSize to saturate for sane code, but make
+ // sure we handle Range saturation correctly.
+ uint64_t IntRange = Range.getLimitedValue(UINT64_MAX/10);
+ uint64_t IntTSize = TSize.getLimitedValue(UINT64_MAX/10);
+ if (IntTSize * 10 < IntRange * 4)
return false;
DEBUG(dbgs() << "Lowering jump table\n"
<< "First entry: " << First << ". Last entry: " << Last << '\n'
- << "Range: " << Range
- << ". Size: " << TSize << ". Density: " << Density << "\n\n");
+ << "Range: " << Range << ". Size: " << TSize << ".\n\n");
// Get the MachineFunction which holds the current MBB. This is used when
// inserting any additional MBBs necessary to represent the switch.
diff --git a/lib/CodeGen/TargetLoweringObjectFileImpl.cpp b/lib/CodeGen/TargetLoweringObjectFileImpl.cpp
index fb87154..3848f4d 100644
--- a/lib/CodeGen/TargetLoweringObjectFileImpl.cpp
+++ b/lib/CodeGen/TargetLoweringObjectFileImpl.cpp
@@ -506,7 +506,9 @@ getExprForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang,
// Add information about the stub reference to MachOMMI so that the stub
// gets emitted by the asmprinter.
MCSymbol *SSym = getContext().GetOrCreateSymbol(Name.str());
- MachineModuleInfoImpl::StubValueTy &StubSym = MachOMMI.getGVStubEntry(SSym);
+ MachineModuleInfoImpl::StubValueTy &StubSym =
+ GV->hasHiddenVisibility() ? MachOMMI.getHiddenGVStubEntry(SSym) :
+ MachOMMI.getGVStubEntry(SSym);
if (StubSym.getPointer() == 0) {
MCSymbol *Sym = Mang->getSymbol(GV);
StubSym = MachineModuleInfoImpl::StubValueTy(Sym, !GV->hasLocalLinkage());
@@ -534,7 +536,9 @@ getCFIPersonalitySymbol(const GlobalValue *GV, Mangler *Mang,
// Add information about the stub reference to MachOMMI so that the stub
// gets emitted by the asmprinter.
MCSymbol *SSym = getContext().GetOrCreateSymbol(Name.str());
- MachineModuleInfoImpl::StubValueTy &StubSym = MachOMMI.getGVStubEntry(SSym);
+ MachineModuleInfoImpl::StubValueTy &StubSym =
+ GV->hasHiddenVisibility() ? MachOMMI.getHiddenGVStubEntry(SSym) :
+ MachOMMI.getGVStubEntry(SSym);
if (StubSym.getPointer() == 0) {
MCSymbol *Sym = Mang->getSymbol(GV);
StubSym = MachineModuleInfoImpl::StubValueTy(Sym, !GV->hasLocalLinkage());
diff --git a/lib/Target/ARM/ARMBaseRegisterInfo.cpp b/lib/Target/ARM/ARMBaseRegisterInfo.cpp
index 7c42342..154f1f8 100644
--- a/lib/Target/ARM/ARMBaseRegisterInfo.cpp
+++ b/lib/Target/ARM/ARMBaseRegisterInfo.cpp
@@ -63,6 +63,13 @@ ARMBaseRegisterInfo::ARMBaseRegisterInfo(const ARMBaseInstrInfo &tii,
const unsigned*
ARMBaseRegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const {
+ bool ghcCall = false;
+
+ if (MF) {
+ const Function *F = MF->getFunction();
+ ghcCall = (F ? F->getCallingConv() == CallingConv::GHC : false);
+ }
+
static const unsigned CalleeSavedRegs[] = {
ARM::LR, ARM::R11, ARM::R10, ARM::R9, ARM::R8,
ARM::R7, ARM::R6, ARM::R5, ARM::R4,
@@ -82,7 +89,13 @@ ARMBaseRegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const {
ARM::D11, ARM::D10, ARM::D9, ARM::D8,
0
};
- return STI.isTargetDarwin() ? DarwinCalleeSavedRegs : CalleeSavedRegs;
+
+ static const unsigned GhcCalleeSavedRegs[] = {
+ 0
+ };
+
+ return ghcCall ? GhcCalleeSavedRegs :
+ STI.isTargetDarwin() ? DarwinCalleeSavedRegs : CalleeSavedRegs;
}
BitVector ARMBaseRegisterInfo::
diff --git a/lib/Target/ARM/ARMCallingConv.td b/lib/Target/ARM/ARMCallingConv.td
index d2981c0..47b2e98 100644
--- a/lib/Target/ARM/ARMCallingConv.td
+++ b/lib/Target/ARM/ARMCallingConv.td
@@ -82,6 +82,25 @@ def RetFastCC_ARM_APCS : CallingConv<[
CCDelegateTo<RetCC_ARM_APCS>
]>;
+//===----------------------------------------------------------------------===//
+// ARM APCS Calling Convention for GHC
+//===----------------------------------------------------------------------===//
+
+def CC_ARM_APCS_GHC : CallingConv<[
+ // Handle all vector types as either f64 or v2f64.
+ CCIfType<[v1i64, v2i32, v4i16, v8i8, v2f32], CCBitConvertToType<f64>>,
+ CCIfType<[v2i64, v4i32, v8i16, v16i8, v4f32], CCBitConvertToType<v2f64>>,
+
+ CCIfType<[v2f64], CCAssignToReg<[Q4, Q5]>>,
+ CCIfType<[f64], CCAssignToReg<[D8, D9, D10, D11]>>,
+ CCIfType<[f32], CCAssignToReg<[S16, S17, S18, S19, S20, S21, S22, S23]>>,
+
+ // Promote i8/i16 arguments to i32.
+ CCIfType<[i8, i16], CCPromoteToType<i32>>,
+
+ // Pass in STG registers: Base, Sp, Hp, R1, R2, R3, R4, SpLim
+ CCIfType<[i32], CCAssignToReg<[R4, R5, R6, R7, R8, R9, R10, R11]>>
+]>;
//===----------------------------------------------------------------------===//
// ARM AAPCS (EABI) Calling Convention, common parts
diff --git a/lib/Target/ARM/ARMFastISel.cpp b/lib/Target/ARM/ARMFastISel.cpp
index 9bc7ef2..dc8e54d 100644
--- a/lib/Target/ARM/ARMFastISel.cpp
+++ b/lib/Target/ARM/ARMFastISel.cpp
@@ -1548,6 +1548,11 @@ CCAssignFn *ARMFastISel::CCAssignFnForCall(CallingConv::ID CC, bool Return) {
return (Return ? RetCC_ARM_AAPCS: CC_ARM_AAPCS);
case CallingConv::ARM_APCS:
return (Return ? RetCC_ARM_APCS: CC_ARM_APCS);
+ case CallingConv::GHC:
+ if (Return)
+ llvm_unreachable("Can't return in GHC call convention");
+ else
+ return CC_ARM_APCS_GHC;
}
}
diff --git a/lib/Target/ARM/ARMFrameLowering.cpp b/lib/Target/ARM/ARMFrameLowering.cpp
index 2d1de6f..412751b 100644
--- a/lib/Target/ARM/ARMFrameLowering.cpp
+++ b/lib/Target/ARM/ARMFrameLowering.cpp
@@ -15,6 +15,8 @@
#include "ARMBaseInstrInfo.h"
#include "ARMBaseRegisterInfo.h"
#include "ARMMachineFunctionInfo.h"
+#include "llvm/CallingConv.h"
+#include "llvm/Function.h"
#include "MCTargetDesc/ARMAddressingModes.h"
#include "llvm/CodeGen/MachineFrameInfo.h"
#include "llvm/CodeGen/MachineFunction.h"
@@ -139,6 +141,10 @@ void ARMFrameLowering::emitPrologue(MachineFunction &MF) const {
unsigned GPRCS1Size = 0, GPRCS2Size = 0, DPRCSSize = 0;
int FramePtrSpillFI = 0;
+ // All calls are tail calls in GHC calling conv, and functions have no prologue/epilogue.
+ if (MF.getFunction()->getCallingConv() == CallingConv::GHC)
+ return;
+
// Allocate the vararg register save area. This is not counted in NumBytes.
if (VARegSaveSize)
emitSPUpdate(isARM, MBB, MBBI, dl, TII, -VARegSaveSize,
@@ -326,6 +332,10 @@ void ARMFrameLowering::emitEpilogue(MachineFunction &MF,
int NumBytes = (int)MFI->getStackSize();
unsigned FramePtr = RegInfo->getFrameRegister(MF);
+ // All calls are tail calls in GHC calling conv, and functions have no prologue/epilogue.
+ if (MF.getFunction()->getCallingConv() == CallingConv::GHC)
+ return;
+
if (!AFI->hasStackFrame()) {
if (NumBytes != 0)
emitSPUpdate(isARM, MBB, MBBI, dl, TII, NumBytes);
diff --git a/lib/Target/ARM/ARMISelLowering.cpp b/lib/Target/ARM/ARMISelLowering.cpp
index e44e356..f60d177 100644
--- a/lib/Target/ARM/ARMISelLowering.cpp
+++ b/lib/Target/ARM/ARMISelLowering.cpp
@@ -1091,6 +1091,8 @@ CCAssignFn *ARMTargetLowering::CCAssignFnForNode(CallingConv::ID CC,
return (Return ? RetCC_ARM_AAPCS : CC_ARM_AAPCS);
case CallingConv::ARM_APCS:
return (Return ? RetCC_ARM_APCS : CC_ARM_APCS);
+ case CallingConv::GHC:
+ return (Return ? RetCC_ARM_APCS : CC_ARM_APCS_GHC);
}
}
diff --git a/lib/Target/ARM/ARMInstrThumb2.td b/lib/Target/ARM/ARMInstrThumb2.td
index 471ec29..05dcc89 100644
--- a/lib/Target/ARM/ARMInstrThumb2.td
+++ b/lib/Target/ARM/ARMInstrThumb2.td
@@ -1538,8 +1538,7 @@ multiclass thumb2_ld_mult<string asm, InstrItinClass itin,
let Inst{21} = 0; // No writeback
let Inst{20} = L_bit;
let Inst{19-16} = Rn;
- let Inst{15} = 0;
- let Inst{14-0} = regs{14-0};
+ let Inst{15-0} = regs;
}
def IA_UPD :
T2XIt<(outs GPR:$wb), (ins GPR:$Rn, pred:$p, reglist:$regs, variable_ops),
@@ -1554,8 +1553,7 @@ multiclass thumb2_ld_mult<string asm, InstrItinClass itin,
let Inst{21} = 1; // Writeback
let Inst{20} = L_bit;
let Inst{19-16} = Rn;
- let Inst{15} = 0;
- let Inst{14-0} = regs{14-0};
+ let Inst{15-0} = regs;
}
def DB :
T2XI<(outs), (ins GPR:$Rn, pred:$p, reglist:$regs, variable_ops),
@@ -1570,8 +1568,7 @@ multiclass thumb2_ld_mult<string asm, InstrItinClass itin,
let Inst{21} = 0; // No writeback
let Inst{20} = L_bit;
let Inst{19-16} = Rn;
- let Inst{15} = 0;
- let Inst{14-0} = regs{14-0};
+ let Inst{15-0} = regs;
}
def DB_UPD :
T2XIt<(outs GPR:$wb), (ins GPR:$Rn, pred:$p, reglist:$regs, variable_ops),
@@ -1586,8 +1583,7 @@ multiclass thumb2_ld_mult<string asm, InstrItinClass itin,
let Inst{21} = 1; // Writeback
let Inst{20} = L_bit;
let Inst{19-16} = Rn;
- let Inst{15} = 0;
- let Inst{14-0} = regs{14-0};
+ let Inst{15-0} = regs;
}
}
diff --git a/lib/Target/CppBackend/CPPBackend.cpp b/lib/Target/CppBackend/CPPBackend.cpp
index ae0e3c4..394ea2b 100644
--- a/lib/Target/CppBackend/CPPBackend.cpp
+++ b/lib/Target/CppBackend/CPPBackend.cpp
@@ -1016,6 +1016,27 @@ std::string CppWriter::getOpName(const Value* V) {
return result;
}
+static StringRef ConvertAtomicOrdering(AtomicOrdering Ordering) {
+ switch (Ordering) {
+ case NotAtomic: return "NotAtomic";
+ case Unordered: return "Unordered";
+ case Monotonic: return "Monotonic";
+ case Acquire: return "Acquire";
+ case Release: return "Release";
+ case AcquireRelease: return "AcquireRelease";
+ case SequentiallyConsistent: return "SequentiallyConsistent";
+ }
+ llvm_unreachable("Unknown ordering");
+}
+
+static StringRef ConvertAtomicSynchScope(SynchronizationScope SynchScope) {
+ switch (SynchScope) {
+ case SingleThread: return "SingleThread";
+ case CrossThread: return "CrossThread";
+ }
+ llvm_unreachable("Unknown synch scope");
+}
+
// printInstruction - This member is called for each Instruction in a function.
void CppWriter::printInstruction(const Instruction *I,
const std::string& bbname) {
@@ -1237,15 +1258,33 @@ void CppWriter::printInstruction(const Instruction *I,
printEscapedString(load->getName());
Out << "\", " << (load->isVolatile() ? "true" : "false" )
<< ", " << bbname << ");";
+ if (load->getAlignment())
+ nl(Out) << iName << "->setAlignment("
+ << load->getAlignment() << ");";
+ if (load->isAtomic()) {
+ StringRef Ordering = ConvertAtomicOrdering(load->getOrdering());
+ StringRef CrossThread = ConvertAtomicSynchScope(load->getSynchScope());
+ nl(Out) << iName << "->setAtomic("
+ << Ordering << ", " << CrossThread << ");";
+ }
break;
}
case Instruction::Store: {
const StoreInst* store = cast<StoreInst>(I);
- Out << " new StoreInst("
+ Out << "StoreInst* " << iName << " = new StoreInst("
<< opNames[0] << ", "
<< opNames[1] << ", "
<< (store->isVolatile() ? "true" : "false")
<< ", " << bbname << ");";
+ if (store->getAlignment())
+ nl(Out) << iName << "->setAlignment("
+ << store->getAlignment() << ");";
+ if (store->isAtomic()) {
+ StringRef Ordering = ConvertAtomicOrdering(store->getOrdering());
+ StringRef CrossThread = ConvertAtomicSynchScope(store->getSynchScope());
+ nl(Out) << iName << "->setAtomic("
+ << Ordering << ", " << CrossThread << ");";
+ }
break;
}
case Instruction::GetElementPtr: {
@@ -1447,6 +1486,60 @@ void CppWriter::printInstruction(const Instruction *I,
Out << "\", " << bbname << ");";
break;
}
+ case Instruction::Fence: {
+ const FenceInst *fi = cast<FenceInst>(I);
+ StringRef Ordering = ConvertAtomicOrdering(fi->getOrdering());
+ StringRef CrossThread = ConvertAtomicSynchScope(fi->getSynchScope());
+ Out << "FenceInst* " << iName
+ << " = new FenceInst(mod->getContext(), "
+ << Ordering << ", " << CrossThread << ", " << bbname
+ << ");";
+ break;
+ }
+ case Instruction::AtomicCmpXchg: {
+ const AtomicCmpXchgInst *cxi = cast<AtomicCmpXchgInst>(I);
+ StringRef Ordering = ConvertAtomicOrdering(cxi->getOrdering());
+ StringRef CrossThread = ConvertAtomicSynchScope(cxi->getSynchScope());
+ Out << "AtomicCmpXchgInst* " << iName
+ << " = new AtomicCmpXchgInst("
+ << opNames[0] << ", " << opNames[1] << ", " << opNames[2] << ", "
+ << Ordering << ", " << CrossThread << ", " << bbname
+ << ");";
+ nl(Out) << iName << "->setName(\"";
+ printEscapedString(cxi->getName());
+ Out << "\");";
+ break;
+ }
+ case Instruction::AtomicRMW: {
+ const AtomicRMWInst *rmwi = cast<AtomicRMWInst>(I);
+ StringRef Ordering = ConvertAtomicOrdering(rmwi->getOrdering());
+ StringRef CrossThread = ConvertAtomicSynchScope(rmwi->getSynchScope());
+ StringRef Operation;
+ switch (rmwi->getOperation()) {
+ case AtomicRMWInst::Xchg: Operation = "AtomicRMWInst::Xchg"; break;
+ case AtomicRMWInst::Add: Operation = "AtomicRMWInst::Add"; break;
+ case AtomicRMWInst::Sub: Operation = "AtomicRMWInst::Sub"; break;
+ case AtomicRMWInst::And: Operation = "AtomicRMWInst::And"; break;
+ case AtomicRMWInst::Nand: Operation = "AtomicRMWInst::Nand"; break;
+ case AtomicRMWInst::Or: Operation = "AtomicRMWInst::Or"; break;
+ case AtomicRMWInst::Xor: Operation = "AtomicRMWInst::Xor"; break;
+ case AtomicRMWInst::Max: Operation = "AtomicRMWInst::Max"; break;
+ case AtomicRMWInst::Min: Operation = "AtomicRMWInst::Min"; break;
+ case AtomicRMWInst::UMax: Operation = "AtomicRMWInst::UMax"; break;
+ case AtomicRMWInst::UMin: Operation = "AtomicRMWInst::UMin"; break;
+ case AtomicRMWInst::BAD_BINOP: llvm_unreachable("Bad atomic operation");
+ }
+ Out << "AtomicRMWInst* " << iName
+ << " = new AtomicRMWInst("
+ << Operation << ", "
+ << opNames[0] << ", " << opNames[1] << ", "
+ << Ordering << ", " << CrossThread << ", " << bbname
+ << ");";
+ nl(Out) << iName << "->setName(\"";
+ printEscapedString(rmwi->getName());
+ Out << "\");";
+ break;
+ }
}
DefinedValues.insert(I);
nl(Out);
@@ -1623,7 +1716,9 @@ void CppWriter::printFunctionBody(const Function *F) {
Out << "Value* " << getCppName(AI) << " = args++;";
nl(Out);
if (AI->hasName()) {
- Out << getCppName(AI) << "->setName(\"" << AI->getName() << "\");";
+ Out << getCppName(AI) << "->setName(\"";
+ printEscapedString(AI->getName());
+ Out << "\");";
nl(Out);
}
}
diff --git a/lib/Target/Mips/CMakeLists.txt b/lib/Target/Mips/CMakeLists.txt
index 1b4329b..71391f3 100644
--- a/lib/Target/Mips/CMakeLists.txt
+++ b/lib/Target/Mips/CMakeLists.txt
@@ -2,6 +2,7 @@ set(LLVM_TARGET_DEFINITIONS Mips.td)
llvm_tablegen(MipsGenRegisterInfo.inc -gen-register-info)
llvm_tablegen(MipsGenInstrInfo.inc -gen-instr-info)
+llvm_tablegen(MipsGenCodeEmitter.inc -gen-emitter)
llvm_tablegen(MipsGenAsmWriter.inc -gen-asm-writer)
llvm_tablegen(MipsGenDAGISel.inc -gen-dag-isel)
llvm_tablegen(MipsGenCallingConv.inc -gen-callingconv)
diff --git a/lib/Target/Mips/Makefile b/lib/Target/Mips/Makefile
index cc4a8ae..d72693c 100644
--- a/lib/Target/Mips/Makefile
+++ b/lib/Target/Mips/Makefile
@@ -13,7 +13,7 @@ TARGET = Mips
# Make sure that tblgen is run, first thing.
BUILT_SOURCES = MipsGenRegisterInfo.inc MipsGenInstrInfo.inc \
- MipsGenAsmWriter.inc \
+ MipsGenAsmWriter.inc MipsGenCodeEmitter.inc \
MipsGenDAGISel.inc MipsGenCallingConv.inc \
MipsGenSubtargetInfo.inc
diff --git a/lib/Target/Mips/Mips64InstrInfo.td b/lib/Target/Mips/Mips64InstrInfo.td
index 49b0223..9758f4b 100644
--- a/lib/Target/Mips/Mips64InstrInfo.td
+++ b/lib/Target/Mips/Mips64InstrInfo.td
@@ -39,51 +39,51 @@ def imm32_63 : ImmLeaf<i64,
// Shifts
class LogicR_shift_rotate_imm64<bits<6> func, bits<5> _rs, string instr_asm,
SDNode OpNode, PatFrag PF>:
- FR<0x00, func, (outs CPU64Regs:$dst), (ins CPU64Regs:$b, shamt_64:$c),
- !strconcat(instr_asm, "\t$dst, $b, $c"),
- [(set CPU64Regs:$dst, (OpNode CPU64Regs:$b, (i64 PF:$c)))],
+ FR<0x00, func, (outs CPU64Regs:$rd), (ins CPU64Regs:$rt, shamt_64:$shamt),
+ !strconcat(instr_asm, "\t$rd, $rt, $shamt"),
+ [(set CPU64Regs:$rd, (OpNode CPU64Regs:$rt, (i64 PF:$shamt)))],
IIAlu> {
let rs = _rs;
}
class LogicR_shift_rotate_reg64<bits<6> func, bits<5> _shamt, string instr_asm,
SDNode OpNode>:
- FR<0x00, func, (outs CPU64Regs:$dst), (ins CPU64Regs:$c, CPU64Regs:$b),
- !strconcat(instr_asm, "\t$dst, $b, $c"),
- [(set CPU64Regs:$dst, (OpNode CPU64Regs:$b, CPU64Regs:$c))], IIAlu> {
+ FR<0x00, func, (outs CPU64Regs:$rd), (ins CPU64Regs:$rs, CPU64Regs:$rt),
+ !strconcat(instr_asm, "\t$rd, $rt, $rs"),
+ [(set CPU64Regs:$rd, (OpNode CPU64Regs:$rt, CPU64Regs:$rs))], IIAlu> {
let shamt = _shamt;
}
// Mul, Div
-let Defs = [HI64, LO64] in {
+let rd = 0, shamt = 0, Defs = [HI64, LO64] in {
let isCommutable = 1 in
class Mul64<bits<6> func, string instr_asm, InstrItinClass itin>:
- FR<0x00, func, (outs), (ins CPU64Regs:$a, CPU64Regs:$b),
- !strconcat(instr_asm, "\t$a, $b"), [], itin>;
+ FR<0x00, func, (outs), (ins CPU64Regs:$rs, CPU64Regs:$rt),
+ !strconcat(instr_asm, "\t$rs, $rt"), [], itin>;
class Div64<SDNode op, bits<6> func, string instr_asm, InstrItinClass itin>:
- FR<0x00, func, (outs), (ins CPU64Regs:$a, CPU64Regs:$b),
- !strconcat(instr_asm, "\t$$zero, $a, $b"),
- [(op CPU64Regs:$a, CPU64Regs:$b)], itin>;
+ FR<0x00, func, (outs), (ins CPU64Regs:$rs, CPU64Regs:$rt),
+ !strconcat(instr_asm, "\t$$zero, $rs, $rt"),
+ [(op CPU64Regs:$rs, CPU64Regs:$rt)], itin>;
}
// Move from Hi/Lo
let shamt = 0 in {
let rs = 0, rt = 0 in
class MoveFromLOHI64<bits<6> func, string instr_asm>:
- FR<0x00, func, (outs CPU64Regs:$dst), (ins),
- !strconcat(instr_asm, "\t$dst"), [], IIHiLo>;
+ FR<0x00, func, (outs CPU64Regs:$rd), (ins),
+ !strconcat(instr_asm, "\t$rd"), [], IIHiLo>;
let rt = 0, rd = 0 in
class MoveToLOHI64<bits<6> func, string instr_asm>:
- FR<0x00, func, (outs), (ins CPU64Regs:$src),
- !strconcat(instr_asm, "\t$src"), [], IIHiLo>;
+ FR<0x00, func, (outs), (ins CPU64Regs:$rs),
+ !strconcat(instr_asm, "\t$rs"), [], IIHiLo>;
}
// Count Leading Ones/Zeros in Word
class CountLeading64<bits<6> func, string instr_asm, list<dag> pattern>:
- FR<0x1c, func, (outs CPU64Regs:$dst), (ins CPU64Regs:$src),
- !strconcat(instr_asm, "\t$dst, $src"), pattern, IIAlu>,
+ FR<0x1c, func, (outs CPU64Regs:$rd), (ins CPU64Regs:$rs),
+ !strconcat(instr_asm, "\t$rd, $rs"), pattern, IIAlu>,
Requires<[HasBitCount]> {
let shamt = 0;
let rt = rd;
@@ -180,9 +180,9 @@ let Uses = [LO64] in
/// Count Leading
def DCLZ : CountLeading64<0x24, "dclz",
- [(set CPU64Regs:$dst, (ctlz CPU64Regs:$src))]>;
+ [(set CPU64Regs:$rd, (ctlz CPU64Regs:$rs))]>;
def DCLO : CountLeading64<0x25, "dclo",
- [(set CPU64Regs:$dst, (ctlz (not CPU64Regs:$src)))]>;
+ [(set CPU64Regs:$rd, (ctlz (not CPU64Regs:$rs)))]>;
//===----------------------------------------------------------------------===//
// Arbitrary patterns that map to one or more instructions
diff --git a/lib/Target/Mips/MipsCodeEmitter.cpp b/lib/Target/Mips/MipsCodeEmitter.cpp
index 9220d9c..23fabe3 100644
--- a/lib/Target/Mips/MipsCodeEmitter.cpp
+++ b/lib/Target/Mips/MipsCodeEmitter.cpp
@@ -105,6 +105,9 @@ class MipsCodeEmitter : public MachineFunctionPass {
unsigned getRelocation(const MachineInstr &MI,
const MachineOperand &MO) const;
+ unsigned getMemEncoding(const MachineInstr &MI, unsigned OpNo) const;
+ unsigned getSizeExtEncoding(const MachineInstr &MI, unsigned OpNo) const;
+ unsigned getSizeInsEncoding(const MachineInstr &MI, unsigned OpNo) const;
};
}
@@ -153,6 +156,28 @@ unsigned MipsCodeEmitter::getRelocation(const MachineInstr &MI,
return Mips::reloc_mips_lo;
}
+unsigned MipsCodeEmitter::getMemEncoding(const MachineInstr &MI,
+ unsigned OpNo) const {
+ // Base register is encoded in bits 20-16, offset is encoded in bits 15-0.
+ assert(MI.getOperand(OpNo).isReg());
+ unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo)) << 16;
+ return
+ (getMachineOpValue(MI, MI.getOperand(OpNo+1)) & 0xFFFF) | RegBits;
+}
+
+unsigned MipsCodeEmitter::getSizeExtEncoding(const MachineInstr &MI,
+ unsigned OpNo) const {
+ // size is encoded as size-1.
+ return getMachineOpValue(MI, MI.getOperand(OpNo)) - 1;
+}
+
+unsigned MipsCodeEmitter::getSizeInsEncoding(const MachineInstr &MI,
+ unsigned OpNo) const {
+ // size is encoded as pos+size-1.
+ return getMachineOpValue(MI, MI.getOperand(OpNo-1)) +
+ getMachineOpValue(MI, MI.getOperand(OpNo)) - 1;
+}
+
/// getMachineOpValue - Return binary encoding of operand. If the machine
/// operand requires relocation, record the relocation and return zero.
unsigned MipsCodeEmitter::getMachineOpValue(const MachineInstr &MI,
@@ -238,8 +263,4 @@ FunctionPass *llvm::createMipsJITCodeEmitterPass(MipsTargetMachine &TM,
return new MipsCodeEmitter(TM, JCE);
}
-unsigned MipsCodeEmitter::getBinaryCodeForInstr(const MachineInstr &MI) const {
- // this function will be automatically generated by the CodeEmitterGenerator
- // using TableGen
- return 0;
-}
+#include "MipsGenCodeEmitter.inc"
diff --git a/lib/Target/Mips/MipsInstrFPU.td b/lib/Target/Mips/MipsInstrFPU.td
index 2fb9d18..1fb779d 100644
--- a/lib/Target/Mips/MipsInstrFPU.td
+++ b/lib/Target/Mips/MipsInstrFPU.td
@@ -76,14 +76,16 @@ def IsNotSingleFloat : Predicate<"!Subtarget.isSingleFloat()">;
// FP load.
class FPLoad<bits<6> op, string opstr, PatFrag FOp, RegisterClass RC,
Operand MemOpnd>:
- FFI<op, (outs RC:$ft), (ins MemOpnd:$base),
- !strconcat(opstr, "\t$ft, $base"), [(set RC:$ft, (FOp addr:$base))]>;
+ FMem<op, (outs RC:$ft), (ins MemOpnd:$addr),
+ !strconcat(opstr, "\t$ft, $addr"), [(set RC:$ft, (FOp addr:$addr))],
+ IILoad>;
// FP store.
class FPStore<bits<6> op, string opstr, PatFrag FOp, RegisterClass RC,
Operand MemOpnd>:
- FFI<op, (outs), (ins RC:$ft, MemOpnd:$base),
- !strconcat(opstr, "\t$ft, $base"), [(store RC:$ft, addr:$base)]>;
+ FMem<op, (outs), (ins RC:$ft, MemOpnd:$addr),
+ !strconcat(opstr, "\t$ft, $addr"), [(store RC:$ft, addr:$addr)],
+ IIStore>;
// Instructions that convert an FP value to 32-bit fixed point.
multiclass FFR1_W_M<bits<6> funct, string opstr> {
@@ -158,22 +160,28 @@ defm FSQRT : FFR1P_M<0x4, "sqrt", fsqrt>;
// stores, and moves between floating-point and integer registers.
// When defining instructions, we reference all 32-bit registers,
// regardless of register aliasing.
-let fd = 0 in {
- /// Move Control Registers From/To CPU Registers
- def CFC1 : FFR<0x11, 0x0, 0x2, (outs CPURegs:$rt), (ins CCR:$fs),
+
+class FFRGPR<bits<5> _fmt, dag outs, dag ins, string asmstr, list<dag> pattern>:
+ FFR<0x11, 0x0, _fmt, outs, ins, asmstr, pattern> {
+ bits<5> rt;
+ let ft = rt;
+ let fd = 0;
+}
+
+/// Move Control Registers From/To CPU Registers
+def CFC1 : FFRGPR<0x2, (outs CPURegs:$rt), (ins CCR:$fs),
"cfc1\t$rt, $fs", []>;
- def CTC1 : FFR<0x11, 0x0, 0x6, (outs CCR:$rt), (ins CPURegs:$fs),
- "ctc1\t$fs, $rt", []>;
+def CTC1 : FFRGPR<0x6, (outs CCR:$fs), (ins CPURegs:$rt),
+ "ctc1\t$rt, $fs", []>;
- def MFC1 : FFR<0x11, 0x00, 0x00, (outs CPURegs:$rt), (ins FGR32:$fs),
+def MFC1 : FFRGPR<0x00, (outs CPURegs:$rt), (ins FGR32:$fs),
"mfc1\t$rt, $fs",
[(set CPURegs:$rt, (bitconvert FGR32:$fs))]>;
- def MTC1 : FFR<0x11, 0x00, 0x04, (outs FGR32:$fs), (ins CPURegs:$rt),
+def MTC1 : FFRGPR<0x04, (outs FGR32:$fs), (ins CPURegs:$rt),
"mtc1\t$rt, $fs",
[(set FGR32:$fs, (bitconvert CPURegs:$rt))]>;
-}
def FMOV_S : FFR1<0x6, 16, "mov", "s", FGR32, FGR32>;
def FMOV_D32 : FFR1<0x6, 17, "mov", "d", AFGR64, AFGR64>,
@@ -203,7 +211,7 @@ let Predicates = [NotN64] in {
}
/// Floating-point Aritmetic
-defm FADD : FFR2P_M<0x10, "add", fadd, 1>;
+defm FADD : FFR2P_M<0x00, "add", fadd, 1>;
defm FDIV : FFR2P_M<0x03, "div", fdiv>;
defm FMUL : FFR2P_M<0x02, "mul", fmul, 1>;
defm FSUB : FFR2P_M<0x01, "sub", fsub>;
@@ -218,12 +226,16 @@ def MIPS_BRANCH_T : PatLeaf<(i32 1)>;
/// Floating Point Branch of False/True (Likely)
let isBranch=1, isTerminator=1, hasDelaySlot=1, base=0x8, Uses=[FCR31] in
- class FBRANCH<PatLeaf op, string asmstr> : FFI<0x11, (outs),
- (ins brtarget:$dst), !strconcat(asmstr, "\t$dst"),
- [(MipsFPBrcond op, bb:$dst)]>;
+ class FBRANCH<bits<1> nd, bits<1> tf, PatLeaf op, string asmstr> :
+ FFI<0x11, (outs), (ins brtarget:$dst), !strconcat(asmstr, "\t$dst"),
+ [(MipsFPBrcond op, bb:$dst)]> {
+ let Inst{20-18} = 0;
+ let Inst{17} = nd;
+ let Inst{16} = tf;
+}
-def BC1F : FBRANCH<MIPS_BRANCH_F, "bc1f">;
-def BC1T : FBRANCH<MIPS_BRANCH_T, "bc1t">;
+def BC1F : FBRANCH<0, 0, MIPS_BRANCH_F, "bc1f">;
+def BC1T : FBRANCH<0, 1, MIPS_BRANCH_T, "bc1t">;
//===----------------------------------------------------------------------===//
// Floating Point Flag Conditions
@@ -249,11 +261,11 @@ def MIPS_FCOND_NGT : PatLeaf<(i32 15)>;
/// Floating Point Compare
let Defs=[FCR31] in {
- def FCMP_S32 : FCC<0x0, (outs), (ins FGR32:$fs, FGR32:$ft, condcode:$cc),
+ def FCMP_S32 : FCC<0x10, (outs), (ins FGR32:$fs, FGR32:$ft, condcode:$cc),
"c.$cc.s\t$fs, $ft",
[(MipsFPCmp FGR32:$fs, FGR32:$ft, imm:$cc)]>;
- def FCMP_D32 : FCC<0x1, (outs), (ins AFGR64:$fs, AFGR64:$ft, condcode:$cc),
+ def FCMP_D32 : FCC<0x11, (outs), (ins AFGR64:$fs, AFGR64:$ft, condcode:$cc),
"c.$cc.d\t$fs, $ft",
[(MipsFPCmp AFGR64:$fs, AFGR64:$ft, imm:$cc)]>,
Requires<[NotFP64bit]>;
@@ -287,7 +299,8 @@ let Predicates = [NotFP64bit] in {
defm : MovnPats<AFGR64, MOVN_D>;
}
-let usesCustomInserter = 1, Uses = [FCR31], Constraints = "$F = $dst" in {
+let cc = 0, usesCustomInserter = 1, Uses = [FCR31],
+ Constraints = "$F = $dst" in {
// flag:float, data:int
class CondMovFPInt<SDNode cmov, bits<1> tf, string instr_asm> :
FCMOV<tf, (outs CPURegs:$dst), (ins CPURegs:$T, CPURegs:$F),
@@ -295,6 +308,7 @@ class CondMovFPInt<SDNode cmov, bits<1> tf, string instr_asm> :
[(set CPURegs:$dst, (cmov CPURegs:$T, CPURegs:$F))]>;
// flag:float, data:float
+let cc = 0 in
class CondMovFPFP<RegisterClass RC, SDNode cmov, bits<5> fmt, bits<1> tf,
string instr_asm> :
FFCMOV<fmt, tf, (outs RC:$dst), (ins RC:$T, RC:$F),
diff --git a/lib/Target/Mips/MipsInstrFormats.td b/lib/Target/Mips/MipsInstrFormats.td
index d246a26..e1725fa 100644
--- a/lib/Target/Mips/MipsInstrFormats.td
+++ b/lib/Target/Mips/MipsInstrFormats.td
@@ -21,30 +21,55 @@
//
//===----------------------------------------------------------------------===//
+// Format specifies the encoding used by the instruction. This is part of the
+// ad-hoc solution used to emit machine instruction encodings by our machine
+// code emitter.
+class Format<bits<4> val> {
+ bits<4> Value = val;
+}
+
+def Pseudo : Format<0>;
+def FrmR : Format<1>;
+def FrmI : Format<2>;
+def FrmJ : Format<3>;
+def FrmFR : Format<4>;
+def FrmFI : Format<5>;
+def FrmOther : Format<6>; // Instruction w/ a custom format
+
// Generic Mips Format
class MipsInst<dag outs, dag ins, string asmstr, list<dag> pattern,
- InstrItinClass itin>: Instruction
+ InstrItinClass itin, Format f>: Instruction
{
field bits<32> Inst;
+ Format Form = f;
let Namespace = "Mips";
- bits<6> opcode;
+ bits<6> Opcode = 0;
- // Top 5 bits are the 'opcode' field
- let Inst{31-26} = opcode;
+ // Top 6 bits are the 'opcode' field
+ let Inst{31-26} = Opcode;
- dag OutOperandList = outs;
- dag InOperandList = ins;
+ let OutOperandList = outs;
+ let InOperandList = ins;
let AsmString = asmstr;
let Pattern = pattern;
let Itinerary = itin;
+
+ //
+ // Attributes specific to Mips instructions...
+ //
+ bits<4> FormBits = Form.Value;
+
+ // TSFlags layout should be kept in sync with MipsInstrInfo.h.
+ let TSFlags{3-0} = FormBits;
}
// Mips Pseudo Instructions Format
class MipsPseudo<dag outs, dag ins, string asmstr, list<dag> pattern>:
- MipsInst<outs, ins, asmstr, pattern, IIPseudo> {
+ MipsInst<outs, ins, asmstr, pattern, IIPseudo, Pseudo> {
+ let isCodeGenOnly = 1;
let isPseudo = 1;
}
@@ -54,7 +79,7 @@ class MipsPseudo<dag outs, dag ins, string asmstr, list<dag> pattern>:
class FR<bits<6> op, bits<6> _funct, dag outs, dag ins, string asmstr,
list<dag> pattern, InstrItinClass itin>:
- MipsInst<outs, ins, asmstr, pattern, itin>
+ MipsInst<outs, ins, asmstr, pattern, itin, FrmR>
{
bits<5> rd;
bits<5> rs;
@@ -62,7 +87,7 @@ class FR<bits<6> op, bits<6> _funct, dag outs, dag ins, string asmstr,
bits<5> shamt;
bits<6> funct;
- let opcode = op;
+ let Opcode = op;
let funct = _funct;
let Inst{25-21} = rs;
@@ -77,13 +102,13 @@ class FR<bits<6> op, bits<6> _funct, dag outs, dag ins, string asmstr,
//===----------------------------------------------------------------------===//
class FI<bits<6> op, dag outs, dag ins, string asmstr, list<dag> pattern,
- InstrItinClass itin>: MipsInst<outs, ins, asmstr, pattern, itin>
+ InstrItinClass itin>: MipsInst<outs, ins, asmstr, pattern, itin, FrmI>
{
bits<5> rt;
bits<5> rs;
bits<16> imm16;
- let opcode = op;
+ let Opcode = op;
let Inst{25-21} = rs;
let Inst{20-16} = rt;
@@ -92,13 +117,13 @@ class FI<bits<6> op, dag outs, dag ins, string asmstr, list<dag> pattern,
class CBranchBase<bits<6> op, dag outs, dag ins, string asmstr,
list<dag> pattern, InstrItinClass itin>:
- MipsInst<outs, ins, asmstr, pattern, itin>
+ MipsInst<outs, ins, asmstr, pattern, itin, FrmI>
{
bits<5> rs;
bits<5> rt;
bits<16> imm16;
- let opcode = op;
+ let Opcode = op;
let Inst{25-21} = rs;
let Inst{20-16} = rt;
@@ -110,11 +135,11 @@ class CBranchBase<bits<6> op, dag outs, dag ins, string asmstr,
//===----------------------------------------------------------------------===//
class FJ<bits<6> op, dag outs, dag ins, string asmstr, list<dag> pattern,
- InstrItinClass itin>: MipsInst<outs, ins, asmstr, pattern, itin>
+ InstrItinClass itin>: MipsInst<outs, ins, asmstr, pattern, itin, FrmJ>
{
bits<26> addr;
- let opcode = op;
+ let Opcode = op;
let Inst{25-0} = addr;
}
@@ -138,7 +163,7 @@ class FJ<bits<6> op, dag outs, dag ins, string asmstr, list<dag> pattern,
class FFR<bits<6> op, bits<6> _funct, bits<5> _fmt, dag outs, dag ins,
string asmstr, list<dag> pattern> :
- MipsInst<outs, ins, asmstr, pattern, NoItinerary>
+ MipsInst<outs, ins, asmstr, pattern, NoItinerary, FrmFR>
{
bits<5> fd;
bits<5> fs;
@@ -146,7 +171,7 @@ class FFR<bits<6> op, bits<6> _funct, bits<5> _fmt, dag outs, dag ins,
bits<5> fmt;
bits<6> funct;
- let opcode = op;
+ let Opcode = op;
let funct = _funct;
let fmt = _fmt;
@@ -162,13 +187,13 @@ class FFR<bits<6> op, bits<6> _funct, bits<5> _fmt, dag outs, dag ins,
//===----------------------------------------------------------------------===//
class FFI<bits<6> op, dag outs, dag ins, string asmstr, list<dag> pattern>:
- MipsInst<outs, ins, asmstr, pattern, NoItinerary>
+ MipsInst<outs, ins, asmstr, pattern, NoItinerary, FrmFI>
{
bits<5> ft;
bits<5> base;
bits<16> imm16;
- let opcode = op;
+ let Opcode = op;
let Inst{25-21} = base;
let Inst{20-16} = ft;
@@ -180,14 +205,14 @@ class FFI<bits<6> op, dag outs, dag ins, string asmstr, list<dag> pattern>:
//===----------------------------------------------------------------------===//
class FCC<bits<5> _fmt, dag outs, dag ins, string asmstr, list<dag> pattern> :
- MipsInst<outs, ins, asmstr, pattern, NoItinerary>
+ MipsInst<outs, ins, asmstr, pattern, NoItinerary, FrmOther>
{
bits<5> fs;
bits<5> ft;
bits<4> cc;
bits<5> fmt;
- let opcode = 0x11;
+ let Opcode = 0x11;
let fmt = _fmt;
let Inst{25-21} = fmt;
@@ -201,18 +226,18 @@ class FCC<bits<5> _fmt, dag outs, dag ins, string asmstr, list<dag> pattern> :
class FCMOV<bits<1> _tf, dag outs, dag ins, string asmstr,
list<dag> pattern> :
- MipsInst<outs, ins, asmstr, pattern, NoItinerary>
+ MipsInst<outs, ins, asmstr, pattern, NoItinerary, FrmOther>
{
bits<5> rd;
bits<5> rs;
- bits<3> N;
+ bits<3> cc;
bits<1> tf;
- let opcode = 0;
+ let Opcode = 0;
let tf = _tf;
let Inst{25-21} = rs;
- let Inst{20-18} = N;
+ let Inst{20-18} = cc;
let Inst{17} = 0;
let Inst{16} = tf;
let Inst{15-11} = rd;
@@ -222,20 +247,20 @@ class FCMOV<bits<1> _tf, dag outs, dag ins, string asmstr,
class FFCMOV<bits<5> _fmt, bits<1> _tf, dag outs, dag ins, string asmstr,
list<dag> pattern> :
- MipsInst<outs, ins, asmstr, pattern, NoItinerary>
+ MipsInst<outs, ins, asmstr, pattern, NoItinerary, FrmOther>
{
bits<5> fd;
bits<5> fs;
- bits<3> N;
+ bits<3> cc;
bits<5> fmt;
bits<1> tf;
- let opcode = 17;
+ let Opcode = 17;
let fmt = _fmt;
let tf = _tf;
let Inst{25-21} = fmt;
- let Inst{20-18} = N;
+ let Inst{20-18} = cc;
let Inst{17} = 0;
let Inst{16} = tf;
let Inst{15-11} = fs;
diff --git a/lib/Target/Mips/MipsInstrInfo.td b/lib/Target/Mips/MipsInstrInfo.td
index 06b7de7..3fbd41e 100644
--- a/lib/Target/Mips/MipsInstrInfo.td
+++ b/lib/Target/Mips/MipsInstrInfo.td
@@ -153,6 +153,7 @@ def uimm16 : Operand<i32> {
def mem : Operand<i32> {
let PrintMethod = "printMemOperand";
let MIOperandInfo = (ops CPURegs, simm16);
+ let EncoderMethod = "getMemEncoding";
}
def mem64 : Operand<i64> {
@@ -163,6 +164,17 @@ def mem64 : Operand<i64> {
def mem_ea : Operand<i32> {
let PrintMethod = "printMemOperandEA";
let MIOperandInfo = (ops CPURegs, simm16);
+ let EncoderMethod = "getMemEncoding";
+}
+
+// size operand of ext instruction
+def size_ext : Operand<i32> {
+ let EncoderMethod = "getSizeExtEncoding";
+}
+
+// size operand of ins instruction
+def size_ins : Operand<i32> {
+ let EncoderMethod = "getSizeInsEncoding";
}
// Transformation Function - get the lower 16 bits.
@@ -271,14 +283,14 @@ class ArithOverflowR<bits<6> op, bits<6> func, string instr_asm,
// Arithmetic and logical instructions with 2 register operands.
class ArithLogicI<bits<6> op, string instr_asm, SDNode OpNode,
Operand Od, PatLeaf imm_type, RegisterClass RC> :
- FI<op, (outs RC:$rt), (ins RC:$rs, Od:$i),
- !strconcat(instr_asm, "\t$rt, $rs, $i"),
- [(set RC:$rt, (OpNode RC:$rs, imm_type:$i))], IIAlu>;
+ FI<op, (outs RC:$rt), (ins RC:$rs, Od:$imm16),
+ !strconcat(instr_asm, "\t$rt, $rs, $imm16"),
+ [(set RC:$rt, (OpNode RC:$rs, imm_type:$imm16))], IIAlu>;
class ArithOverflowI<bits<6> op, string instr_asm, SDNode OpNode,
Operand Od, PatLeaf imm_type, RegisterClass RC> :
- FI<op, (outs RC:$rt), (ins RC:$rs, Od:$i),
- !strconcat(instr_asm, "\t$rt, $rs, $i"), [], IIAlu>;
+ FI<op, (outs RC:$rt), (ins RC:$rs, Od:$imm16),
+ !strconcat(instr_asm, "\t$rt, $rs, $imm16"), [], IIAlu>;
// Arithmetic Multiply ADD/SUB
let rd = 0, shamt = 0, Defs = [HI, LO], Uses = [HI, LO] in
@@ -319,16 +331,23 @@ class LogicR_shift_rotate_reg<bits<6> func, bits<5> isRotate, string instr_asm,
// Load Upper Imediate
class LoadUpper<bits<6> op, string instr_asm>:
- FI<op, (outs CPURegs:$rt), (ins uimm16:$imm),
- !strconcat(instr_asm, "\t$rt, $imm"), [], IIAlu> {
+ FI<op, (outs CPURegs:$rt), (ins uimm16:$imm16),
+ !strconcat(instr_asm, "\t$rt, $imm16"), [], IIAlu> {
let rs = 0;
}
+class FMem<bits<6> op, dag outs, dag ins, string asmstr, list<dag> pattern,
+ InstrItinClass itin>: FFI<op, outs, ins, asmstr, pattern> {
+ bits<21> addr;
+ let Inst{25-21} = addr{20-16};
+ let Inst{15-0} = addr{15-0};
+}
+
// Memory Load/Store
let canFoldAsLoad = 1 in
class LoadM<bits<6> op, string instr_asm, PatFrag OpNode, RegisterClass RC,
Operand MemOpnd, bit Pseudo>:
- FI<op, (outs RC:$rt), (ins MemOpnd:$addr),
+ FMem<op, (outs RC:$rt), (ins MemOpnd:$addr),
!strconcat(instr_asm, "\t$rt, $addr"),
[(set RC:$rt, (OpNode addr:$addr))], IILoad> {
let isPseudo = Pseudo;
@@ -336,7 +355,7 @@ class LoadM<bits<6> op, string instr_asm, PatFrag OpNode, RegisterClass RC,
class StoreM<bits<6> op, string instr_asm, PatFrag OpNode, RegisterClass RC,
Operand MemOpnd, bit Pseudo>:
- FI<op, (outs), (ins RC:$rt, MemOpnd:$addr),
+ FMem<op, (outs), (ins RC:$rt, MemOpnd:$addr),
!strconcat(instr_asm, "\t$rt, $addr"),
[(OpNode RC:$rt, addr:$addr)], IIStore> {
let isPseudo = Pseudo;
@@ -380,9 +399,9 @@ multiclass StoreM64<bits<6> op, string instr_asm, PatFrag OpNode,
// Conditional Branch
class CBranch<bits<6> op, string instr_asm, PatFrag cond_op, RegisterClass RC>:
- CBranchBase<op, (outs), (ins RC:$rs, RC:$rt, brtarget:$offset),
- !strconcat(instr_asm, "\t$rs, $rt, $offset"),
- [(brcond (i32 (cond_op RC:$rs, RC:$rt)), bb:$offset)], IIBranch> {
+ CBranchBase<op, (outs), (ins RC:$rs, RC:$rt, brtarget:$imm16),
+ !strconcat(instr_asm, "\t$rs, $rt, $imm16"),
+ [(brcond (i32 (cond_op RC:$rs, RC:$rt)), bb:$imm16)], IIBranch> {
let isBranch = 1;
let isTerminator = 1;
let hasDelaySlot = 1;
@@ -390,9 +409,9 @@ class CBranch<bits<6> op, string instr_asm, PatFrag cond_op, RegisterClass RC>:
class CBranchZero<bits<6> op, bits<5> _rt, string instr_asm, PatFrag cond_op,
RegisterClass RC>:
- CBranchBase<op, (outs), (ins RC:$rs, brtarget:$offset),
- !strconcat(instr_asm, "\t$rs, $offset"),
- [(brcond (i32 (cond_op RC:$rs, 0)), bb:$offset)], IIBranch> {
+ CBranchBase<op, (outs), (ins RC:$rs, brtarget:$imm16),
+ !strconcat(instr_asm, "\t$rs, $imm16"),
+ [(brcond (i32 (cond_op RC:$rs, 0)), bb:$imm16)], IIBranch> {
let rt = _rt;
let isBranch = 1;
let isTerminator = 1;
@@ -411,9 +430,9 @@ class SetCC_R<bits<6> op, bits<6> func, string instr_asm, PatFrag cond_op,
class SetCC_I<bits<6> op, string instr_asm, PatFrag cond_op, Operand Od,
PatLeaf imm_type, RegisterClass RC>:
- FI<op, (outs CPURegs:$rd), (ins RC:$rs, Od:$i),
- !strconcat(instr_asm, "\t$rd, $rs, $i"),
- [(set CPURegs:$rd, (cond_op RC:$rs, imm_type:$i))],
+ FI<op, (outs CPURegs:$rt), (ins RC:$rs, Od:$imm16),
+ !strconcat(instr_asm, "\t$rt, $rs, $imm16"),
+ [(set CPURegs:$rt, (cond_op RC:$rs, imm_type:$imm16))],
IIAlu>;
// Unconditional branch
@@ -450,10 +469,8 @@ let isCall=1, hasDelaySlot=1,
}
class BranchLink<string instr_asm>:
- FI<0x1, (outs), (ins CPURegs:$rs, brtarget:$target, variable_ops),
- !strconcat(instr_asm, "\t$rs, $target"), [], IIBranch> {
- let rt = 0;
- }
+ FI<0x1, (outs), (ins CPURegs:$rs, brtarget:$imm16, variable_ops),
+ !strconcat(instr_asm, "\t$rs, $imm16"), [], IIBranch>;
}
// Mul, Div
@@ -493,7 +510,7 @@ class MoveToLOHI<bits<6> func, string instr_asm>:
}
class EffectiveAddress<string instr_asm> :
- FI<0x09, (outs CPURegs:$rt), (ins mem_ea:$addr),
+ FMem<0x09, (outs CPURegs:$rt), (ins mem_ea:$addr),
instr_asm, [(set CPURegs:$rt, addr:$addr)], IIAlu>;
// Count Leading Ones/Zeros in Word
@@ -507,7 +524,7 @@ class CountLeading<bits<6> func, string instr_asm, list<dag> pattern>:
// Sign Extend in Register.
class SignExtInReg<bits<5> sa, string instr_asm, ValueType vt>:
- FR<0x3f, 0x20, (outs CPURegs:$rd), (ins CPURegs:$rt),
+ FR<0x1f, 0x20, (outs CPURegs:$rd), (ins CPURegs:$rt),
!strconcat(instr_asm, "\t$rd, $rt"),
[(set CPURegs:$rd, (sext_inreg CPURegs:$rt, vt))], NoItinerary> {
let rs = 0;
@@ -685,20 +702,22 @@ defm USW : StoreM32<0x2b, "usw", store_u, 1>;
let hasSideEffects = 1 in
def SYNC : MipsInst<(outs), (ins i32imm:$stype), "sync $stype",
- [(MipsSync imm:$stype)], NoItinerary>
+ [(MipsSync imm:$stype)], NoItinerary, FrmOther>
{
- let opcode = 0;
+ bits<5> stype;
+ let Opcode = 0;
let Inst{25-11} = 0;
+ let Inst{10-6} = stype;
let Inst{5-0} = 15;
}
/// Load-linked, Store-conditional
let mayLoad = 1 in
- def LL : FI<0x30, (outs CPURegs:$dst), (ins mem:$addr),
- "ll\t$dst, $addr", [], IILoad>;
-let mayStore = 1, Constraints = "$src = $dst" in
- def SC : FI<0x38, (outs CPURegs:$dst), (ins CPURegs:$src, mem:$addr),
- "sc\t$src, $addr", [], IIStore>;
+ def LL : FMem<0x30, (outs CPURegs:$rt), (ins mem:$addr),
+ "ll\t$rt, $addr", [], IILoad>;
+let mayStore = 1, Constraints = "$rt = $dst" in
+ def SC : FMem<0x38, (outs CPURegs:$dst), (ins CPURegs:$rt, mem:$addr),
+ "sc\t$rt, $addr", [], IIStore>;
/// Jump and Branch Instructions
def J : JumpFJ<0x02, "j">;
@@ -710,15 +729,17 @@ def BEQ : CBranch<0x04, "beq", seteq, CPURegs>;
def BNE : CBranch<0x05, "bne", setne, CPURegs>;
def BGEZ : CBranchZero<0x01, 1, "bgez", setge, CPURegs>;
def BGTZ : CBranchZero<0x07, 0, "bgtz", setgt, CPURegs>;
-def BLEZ : CBranchZero<0x07, 0, "blez", setle, CPURegs>;
+def BLEZ : CBranchZero<0x06, 0, "blez", setle, CPURegs>;
def BLTZ : CBranchZero<0x01, 0, "bltz", setlt, CPURegs>;
-def BGEZAL : BranchLink<"bgezal">;
-def BLTZAL : BranchLink<"bltzal">;
+let rt=0x11 in
+ def BGEZAL : BranchLink<"bgezal">;
+let rt=0x10 in
+ def BLTZAL : BranchLink<"bltzal">;
let isReturn=1, isTerminator=1, hasDelaySlot=1,
- isBarrier=1, hasCtrlDep=1, rs=0, rt=0, shamt=0 in
- def RET : FR <0x00, 0x02, (outs), (ins CPURegs:$target),
+ isBarrier=1, hasCtrlDep=1, rd=0, rt=0, shamt=0 in
+ def RET : FR <0x00, 0x08, (outs), (ins CPURegs:$target),
"jr\t$target", [(MipsRet CPURegs:$target)], IIBranch>;
/// Multiply and Divide Instructions.
@@ -797,14 +818,14 @@ def MUL : ArithLogicR<0x1c, 0x02, "mul", mul, IIImul, CPURegs, 1>,
def RDHWR : ReadHardware;
def EXT : ExtIns<0, "ext", (outs CPURegs:$rt),
- (ins CPURegs:$rs, uimm16:$pos, uimm16:$sz),
+ (ins CPURegs:$rs, uimm16:$pos, size_ext:$sz),
[(set CPURegs:$rt,
(MipsExt CPURegs:$rs, immZExt5:$pos, immZExt5:$sz))],
NoItinerary>;
let Constraints = "$src = $rt" in
def INS : ExtIns<4, "ins", (outs CPURegs:$rt),
- (ins CPURegs:$rs, uimm16:$pos, uimm16:$sz, CPURegs:$src),
+ (ins CPURegs:$rs, uimm16:$pos, size_ins:$sz, CPURegs:$src),
[(set CPURegs:$rt,
(MipsIns CPURegs:$rs, immZExt5:$pos, immZExt5:$sz,
CPURegs:$src))],
diff --git a/lib/Target/Mips/MipsJITInfo.cpp b/lib/Target/Mips/MipsJITInfo.cpp
index 28c2b48..e3f6a75 100644
--- a/lib/Target/Mips/MipsJITInfo.cpp
+++ b/lib/Target/Mips/MipsJITInfo.cpp
@@ -57,11 +57,11 @@ void MipsCompilationCallback();
".globl " ASMPREFIX "MipsCompilationCallback\n"
ASMPREFIX "MipsCompilationCallback:\n"
".ent " ASMPREFIX "MipsCompilationCallback\n"
- ".frame $29, 32, $31\n"
+ ".frame $sp, 32, $ra\n"
".set noreorder\n"
".cpload $t9\n"
- "addiu $sp, $sp, -60\n"
+ "addiu $sp, $sp, -64\n"
".cprestore 16\n"
// Save argument registers a0, a1, a2, a3, f12, f14 since they may contain
@@ -76,8 +76,8 @@ void MipsCompilationCallback();
"sw $a3, 32($sp)\n"
"sw $ra, 36($sp)\n"
"sw $t8, 40($sp)\n"
- "sdc1 $f12, 44($sp)\n"
- "sdc1 $f14, 52($sp)\n"
+ "sdc1 $f12, 48($sp)\n"
+ "sdc1 $f14, 56($sp)\n"
// t8 points at the end of function stub. Pass the beginning of the stub
// to the MipsCompilationCallbackC.
@@ -92,9 +92,9 @@ void MipsCompilationCallback();
"lw $a3, 32($sp)\n"
"lw $ra, 36($sp)\n"
"lw $t8, 40($sp)\n"
- "ldc1 $f12, 44($sp)\n"
- "ldc1 $f14, 52($sp)\n"
- "addiu $sp, $sp, 60\n"
+ "ldc1 $f12, 48($sp)\n"
+ "ldc1 $f14, 56($sp)\n"
+ "addiu $sp, $sp, 64\n"
// Jump to the (newly modified) stub to invoke the real function.
"addiu $t8, $t8, -16\n"
diff --git a/lib/Target/PowerPC/PPCFrameLowering.cpp b/lib/Target/PowerPC/PPCFrameLowering.cpp
index 7dead10..0b85fea 100644
--- a/lib/Target/PowerPC/PPCFrameLowering.cpp
+++ b/lib/Target/PowerPC/PPCFrameLowering.cpp
@@ -490,10 +490,8 @@ void PPCFrameLowering::emitPrologue(MachineFunction &MF) const {
// This is a bit of a hack: CR2LT, CR2GT, CR2EQ and CR2UN are just
// subregisters of CR2. We just need to emit a move of CR2.
- if (Reg == PPC::CR2LT || Reg == PPC::CR2GT || Reg == PPC::CR2EQ)
+ if (PPC::CRBITRCRegisterClass->contains(Reg))
continue;
- if (Reg == PPC::CR2UN)
- Reg = PPC::CR2;
MachineLocation CSDst(MachineLocation::VirtualFP, Offset);
MachineLocation CSSrc(Reg);
diff --git a/lib/Target/X86/X86CodeEmitter.cpp b/lib/Target/X86/X86CodeEmitter.cpp
index aeff03a..f939510 100644
--- a/lib/Target/X86/X86CodeEmitter.cpp
+++ b/lib/Target/X86/X86CodeEmitter.cpp
@@ -589,6 +589,13 @@ void Emitter<CodeEmitter>::emitMemModRMByte(const MachineInstr &MI,
}
}
+static const MCInstrDesc *UpdateOp(MachineInstr &MI, const X86InstrInfo *II,
+ unsigned Opcode) {
+ const MCInstrDesc *Desc = &II->get(Opcode);
+ MI.setDesc(*Desc);
+ return Desc;
+}
+
template<class CodeEmitter>
void Emitter<CodeEmitter>::emitInstruction(MachineInstr &MI,
const MCInstrDesc *Desc) {
@@ -596,15 +603,23 @@ void Emitter<CodeEmitter>::emitInstruction(MachineInstr &MI,
// If this is a pseudo instruction, lower it.
switch (Desc->getOpcode()) {
- case X86::ADD16rr_DB: Desc = &II->get(X86::OR16rr); MI.setDesc(*Desc);break;
- case X86::ADD32rr_DB: Desc = &II->get(X86::OR32rr); MI.setDesc(*Desc);break;
- case X86::ADD64rr_DB: Desc = &II->get(X86::OR64rr); MI.setDesc(*Desc);break;
- case X86::ADD16ri_DB: Desc = &II->get(X86::OR16ri); MI.setDesc(*Desc);break;
- case X86::ADD32ri_DB: Desc = &II->get(X86::OR32ri); MI.setDesc(*Desc);break;
- case X86::ADD64ri32_DB:Desc = &II->get(X86::OR64ri32);MI.setDesc(*Desc);break;
- case X86::ADD16ri8_DB: Desc = &II->get(X86::OR16ri8);MI.setDesc(*Desc);break;
- case X86::ADD32ri8_DB: Desc = &II->get(X86::OR32ri8);MI.setDesc(*Desc);break;
- case X86::ADD64ri8_DB: Desc = &II->get(X86::OR64ri8);MI.setDesc(*Desc);break;
+ case X86::ADD16rr_DB: Desc = UpdateOp(MI, II, X86::OR16rr); break;
+ case X86::ADD32rr_DB: Desc = UpdateOp(MI, II, X86::OR32rr); break;
+ case X86::ADD64rr_DB: Desc = UpdateOp(MI, II, X86::OR64rr); break;
+ case X86::ADD16ri_DB: Desc = UpdateOp(MI, II, X86::OR16ri); break;
+ case X86::ADD32ri_DB: Desc = UpdateOp(MI, II, X86::OR32ri); break;
+ case X86::ADD64ri32_DB: Desc = UpdateOp(MI, II, X86::OR64ri32); break;
+ case X86::ADD16ri8_DB: Desc = UpdateOp(MI, II, X86::OR16ri8); break;
+ case X86::ADD32ri8_DB: Desc = UpdateOp(MI, II, X86::OR32ri8); break;
+ case X86::ADD64ri8_DB: Desc = UpdateOp(MI, II, X86::OR64ri8); break;
+ case X86::ACQUIRE_MOV8rm: Desc = UpdateOp(MI, II, X86::MOV8rm); break;
+ case X86::ACQUIRE_MOV16rm: Desc = UpdateOp(MI, II, X86::MOV16rm); break;
+ case X86::ACQUIRE_MOV32rm: Desc = UpdateOp(MI, II, X86::MOV32rm); break;
+ case X86::ACQUIRE_MOV64rm: Desc = UpdateOp(MI, II, X86::MOV64rm); break;
+ case X86::RELEASE_MOV8mr: Desc = UpdateOp(MI, II, X86::MOV8mr); break;
+ case X86::RELEASE_MOV16mr: Desc = UpdateOp(MI, II, X86::MOV16mr); break;
+ case X86::RELEASE_MOV32mr: Desc = UpdateOp(MI, II, X86::MOV32mr); break;
+ case X86::RELEASE_MOV64mr: Desc = UpdateOp(MI, II, X86::MOV64mr); break;
}
diff --git a/lib/Transforms/InstCombine/InstructionCombining.cpp b/lib/Transforms/InstCombine/InstructionCombining.cpp
index 92874b9..c15b805 100644
--- a/lib/Transforms/InstCombine/InstructionCombining.cpp
+++ b/lib/Transforms/InstCombine/InstructionCombining.cpp
@@ -2025,9 +2025,10 @@ bool InstCombiner::DoOneIteration(Function &F, unsigned Iteration) {
BasicBlock *InstParent = I->getParent();
BasicBlock::iterator InsertPos = I;
- if (!isa<PHINode>(Result)) // If combining a PHI, don't insert
- while (isa<PHINode>(InsertPos)) // middle of a block of PHIs.
- ++InsertPos;
+ // If we replace a PHI with something that isn't a PHI, fix up the
+ // insertion point.
+ if (!isa<PHINode>(Result) && isa<PHINode>(InsertPos))
+ InsertPos = InstParent->getFirstInsertionPt();
InstParent->getInstList().insert(InsertPos, Result);
OpenPOWER on IntegriCloud