ARM64: add constraints to various FastISel operations

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@206284 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Tim Northover 2014-04-15 13:59:53 +00:00
parent 03eecdccff
commit 1291807e03
3 changed files with 23 additions and 10 deletions

View File

@ -225,7 +225,7 @@ unsigned ARM64FastISel::ARM64MaterializeFP(const ConstantFP *CFP, MVT VT) {
Align = DL.getTypeAllocSize(CFP->getType()); Align = DL.getTypeAllocSize(CFP->getType());
unsigned Idx = MCP.getConstantPoolIndex(cast<Constant>(CFP), Align); unsigned Idx = MCP.getConstantPoolIndex(cast<Constant>(CFP), Align);
unsigned ADRPReg = createResultReg(&ARM64::GPR64RegClass); unsigned ADRPReg = createResultReg(&ARM64::GPR64commonRegClass);
BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::ADRP), BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::ADRP),
ADRPReg).addConstantPoolIndex(Idx, 0, ARM64II::MO_PAGE); ADRPReg).addConstantPoolIndex(Idx, 0, ARM64II::MO_PAGE);
@ -253,25 +253,28 @@ unsigned ARM64FastISel::ARM64MaterializeGV(const GlobalValue *GV) {
EVT DestEVT = TLI.getValueType(GV->getType(), true); EVT DestEVT = TLI.getValueType(GV->getType(), true);
if (!DestEVT.isSimple()) if (!DestEVT.isSimple())
return 0; return 0;
MVT DestVT = DestEVT.getSimpleVT();
unsigned ADRPReg = createResultReg(&ARM64::GPR64RegClass); unsigned ADRPReg = createResultReg(&ARM64::GPR64commonRegClass);
unsigned ResultReg = createResultReg(TLI.getRegClassFor(DestVT)); unsigned ResultReg;
if (OpFlags & ARM64II::MO_GOT) { if (OpFlags & ARM64II::MO_GOT) {
// ADRP + LDRX // ADRP + LDRX
BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::ADRP), BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::ADRP),
ADRPReg) ADRPReg)
.addGlobalAddress(GV, 0, ARM64II::MO_GOT | ARM64II::MO_PAGE); .addGlobalAddress(GV, 0, ARM64II::MO_GOT | ARM64II::MO_PAGE);
ResultReg = createResultReg(&ARM64::GPR64RegClass);
BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::LDRXui), BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::LDRXui),
ResultReg) ResultReg)
.addReg(ADRPReg) .addReg(ADRPReg)
.addGlobalAddress(GV, 0, ARM64II::MO_GOT | ARM64II::MO_PAGEOFF | .addGlobalAddress(GV, 0, ARM64II::MO_GOT | ARM64II::MO_PAGEOFF |
ARM64II::MO_NC); ARM64II::MO_NC);
} else { } else {
// ADRP + ADDX // ADRP + ADDX
BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::ADRP), BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::ADRP),
ADRPReg).addGlobalAddress(GV, 0, ARM64II::MO_PAGE); ADRPReg).addGlobalAddress(GV, 0, ARM64II::MO_PAGE);
ResultReg = createResultReg(&ARM64::GPR64spRegClass);
BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::ADDXri), BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(ARM64::ADDXri),
ResultReg) ResultReg)
.addReg(ADRPReg) .addReg(ADRPReg)
@ -1117,7 +1120,8 @@ bool ARM64FastISel::SelectFPToInt(const Instruction *I, bool Signed) {
else else
Opc = (DestVT == MVT::i32) ? ARM64::FCVTZUUWSr : ARM64::FCVTZUUXSr; Opc = (DestVT == MVT::i32) ? ARM64::FCVTZUUWSr : ARM64::FCVTZUUXSr;
} }
unsigned ResultReg = createResultReg(TLI.getRegClassFor(DestVT)); unsigned ResultReg = createResultReg(
DestVT == MVT::i32 ? &ARM64::GPR32RegClass : &ARM64::GPR64RegClass);
BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(Opc), ResultReg) BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(Opc), ResultReg)
.addReg(SrcReg); .addReg(SrcReg);
UpdateValueMap(I, ResultReg); UpdateValueMap(I, ResultReg);
@ -1143,6 +1147,9 @@ bool ARM64FastISel::SelectIntToFP(const Instruction *I, bool Signed) {
return false; return false;
} }
MRI.constrainRegClass(SrcReg, SrcVT == MVT::i64 ? &ARM64::GPR64RegClass
: &ARM64::GPR32RegClass);
unsigned Opc; unsigned Opc;
if (SrcVT == MVT::i64) { if (SrcVT == MVT::i64) {
if (Signed) if (Signed)

View File

@ -1,4 +1,8 @@
; RUN: llc -verify-machineinstrs < %s -mtriple=aarch64-none-linux-gnu -O0 | FileCheck %s ; RUN: llc -verify-machineinstrs < %s -mtriple=aarch64-none-linux-gnu -O0 | FileCheck %s
; RUN: llc -verify-machineinstrs < %s -mtriple=arm64-apple-ios7.0 -O0
; (The O0 test is to make sure FastISel still constrains its operands properly
; and the verifier doesn't trigger).
@var32 = global i32 0 @var32 = global i32 0
@var64 = global i64 0 @var64 = global i64 0

View File

@ -7,8 +7,9 @@
@.str3 = private unnamed_addr constant [7 x i8] c"%f %u\0A\00", align 1 @.str3 = private unnamed_addr constant [7 x i8] c"%f %u\0A\00", align 1
define void @testDouble(double %d) ssp { define void @testDouble(double %d) ssp {
; CHECK: fcvtzu x{{.}}, d{{.}} ; CHECK-LABEL: testDouble:
; CHECK: fcvtzu w{{.}}, d{{.}} ; CHECK: fcvtzu x{{[0-9]+}}, d{{[0-9]+}}
; CHECK: fcvtzu w{{[0-9]+}}, d{{[0-9]+}}
entry: entry:
%d.addr = alloca double, align 8 %d.addr = alloca double, align 8
store double %d, double* %d.addr, align 8 store double %d, double* %d.addr, align 8
@ -26,8 +27,9 @@ entry:
declare i32 @printf(i8*, ...) declare i32 @printf(i8*, ...)
define void @testFloat(float %f) ssp { define void @testFloat(float %f) ssp {
; CHECK: fcvtzu x{{.}}, s{{.}} ; CHECK-LABEL: testFloat:
; CHECK: fcvtzu w{{.}}, s{{.}} ; CHECK: fcvtzu x{{[0-9]+}}, s{{[0-9]+}}
; CHECK: fcvtzu w{{[0-9]+}}, s{{[0-9]+}}
entry: entry:
%f.addr = alloca float, align 4 %f.addr = alloca float, align 4
store float %f, float* %f.addr, align 4 store float %f, float* %f.addr, align 4