summaryrefslogtreecommitdiffstats
path: root/llvm
diff options
context:
space:
mode:
authorJuergen Ributzka <juergen@apple.com>2014-08-15 18:55:55 +0000
committerJuergen Ributzka <juergen@apple.com>2014-08-15 18:55:55 +0000
commit6597d319fe470c81f07ac196ca458e9ab6ca6934 (patch)
treee451e561f79fd3a8053eb97580a0e29e5f5146bd /llvm
parent6bca986ef1177233517365ea88a0cf925f882eb3 (diff)
downloadbcm5719-llvm-6597d319fe470c81f07ac196ca458e9ab6ca6934.tar.gz
bcm5719-llvm-6597d319fe470c81f07ac196ca458e9ab6ca6934.zip
[FastISel][AArch64] Fix a latent bug in floating-point materialization.
The floating-point value positive zero (+0.0) is a valid immedate value according to isFPImmLegal. As a result AArch64 FastISel went ahead and used the immediate version of fmov to materialize the constant. The problem is that the immediate version of fmov cannot encode an imediate for postive zero. Instead a fmov from the zero register was supposed to be used in this case. This fix adds handling for this special case and uses fmov from the zero register to materialize a positive zero (negative zeroes go to the constant pool). There is no test case for this, because this code is currently dead. It will be enabled in a future commit and I will add a test case in a separate commit after that. This fixes <rdar://problem/18027157>. llvm-svn: 215753
Diffstat (limited to 'llvm')
-rw-r--r--llvm/lib/Target/AArch64/AArch64FastISel.cpp11
1 files changed, 10 insertions, 1 deletions
diff --git a/llvm/lib/Target/AArch64/AArch64FastISel.cpp b/llvm/lib/Target/AArch64/AArch64FastISel.cpp
index 603c76f0c26..5114acaec41 100644
--- a/llvm/lib/Target/AArch64/AArch64FastISel.cpp
+++ b/llvm/lib/Target/AArch64/AArch64FastISel.cpp
@@ -230,10 +230,19 @@ unsigned AArch64FastISel::AArch64MaterializeFP(const ConstantFP *CFP, MVT VT) {
// This checks to see if we can use FMOV instructions to materialize
// a constant, otherwise we have to materialize via the constant pool.
if (TLI.isFPImmLegal(Val, VT)) {
+ unsigned ResultReg = createResultReg(TLI.getRegClassFor(VT));
+ // Positive zero (+0.0) has to be materialized with a fmov from the zero
+ // register, because the immediate version of fmov cannot encode zero.
+ if (Val.isPosZero()) {
+ unsigned ZReg = Is64Bit ? AArch64::XZR : AArch64::WZR;
+ unsigned Opc = Is64Bit ? AArch64::FMOVDr : AArch64::FMOVSr;
+ BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(Opc), ResultReg)
+ .addReg(ZReg, getKillRegState(true));
+ return ResultReg;
+ }
int Imm = Is64Bit ? AArch64_AM::getFP64Imm(Val)
: AArch64_AM::getFP32Imm(Val);
unsigned Opc = Is64Bit ? AArch64::FMOVDi : AArch64::FMOVSi;
- unsigned ResultReg = createResultReg(TLI.getRegClassFor(VT));
BuildMI(*FuncInfo.MBB, FuncInfo.InsertPt, DbgLoc, TII.get(Opc), ResultReg)
.addImm(Imm);
return ResultReg;
OpenPOWER on IntegriCloud