mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-06-20 10:24:12 +00:00
PPCInstrInfo::optimizeCompareInstr should not optimize FP compares
The floating-point record forms on PPC don't set the condition register bits based on a comparison with zero (like the integer record forms do), but rather based on the exception status bits. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@181423 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
@ -1096,8 +1096,11 @@ bool PPCInstrInfo::optimizeCompareInstr(MachineInstr *CmpInstr,
|
|||||||
|
|
||||||
int OpC = CmpInstr->getOpcode();
|
int OpC = CmpInstr->getOpcode();
|
||||||
unsigned CRReg = CmpInstr->getOperand(0).getReg();
|
unsigned CRReg = CmpInstr->getOperand(0).getReg();
|
||||||
bool isFP = OpC == PPC::FCMPUS || OpC == PPC::FCMPUD;
|
|
||||||
unsigned CRRecReg = isFP ? PPC::CR1 : PPC::CR0;
|
// FP record forms set CR1 based on the execption status bits, not a
|
||||||
|
// comparison with zero.
|
||||||
|
if (OpC == PPC::FCMPUS || OpC == PPC::FCMPUD)
|
||||||
|
return false;
|
||||||
|
|
||||||
// The record forms set the condition register based on a signed comparison
|
// The record forms set the condition register based on a signed comparison
|
||||||
// with zero (so says the ISA manual). This is not as straightforward as it
|
// with zero (so says the ISA manual). This is not as straightforward as it
|
||||||
@ -1140,9 +1143,9 @@ bool PPCInstrInfo::optimizeCompareInstr(MachineInstr *CmpInstr,
|
|||||||
equalityOnly = true;
|
equalityOnly = true;
|
||||||
} else
|
} else
|
||||||
return false;
|
return false;
|
||||||
} else if (!isFP)
|
} else
|
||||||
equalityOnly = is64BitUnsignedCompare;
|
equalityOnly = is64BitUnsignedCompare;
|
||||||
} else if (!isFP)
|
} else
|
||||||
equalityOnly = is32BitUnsignedCompare;
|
equalityOnly = is32BitUnsignedCompare;
|
||||||
|
|
||||||
if (equalityOnly) {
|
if (equalityOnly) {
|
||||||
@ -1211,8 +1214,8 @@ bool PPCInstrInfo::optimizeCompareInstr(MachineInstr *CmpInstr,
|
|||||||
unsigned IOpC = Instr.getOpcode();
|
unsigned IOpC = Instr.getOpcode();
|
||||||
|
|
||||||
if (&*I != CmpInstr && (
|
if (&*I != CmpInstr && (
|
||||||
Instr.modifiesRegister(CRRecReg, TRI) ||
|
Instr.modifiesRegister(PPC::CR0, TRI) ||
|
||||||
Instr.readsRegister(CRRecReg, TRI)))
|
Instr.readsRegister(PPC::CR0, TRI)))
|
||||||
// This instruction modifies or uses the record condition register after
|
// This instruction modifies or uses the record condition register after
|
||||||
// the one we want to change. While we could do this transformation, it
|
// the one we want to change. While we could do this transformation, it
|
||||||
// would likely not be profitable. This transformation removes one
|
// would likely not be profitable. This transformation removes one
|
||||||
@ -1232,15 +1235,6 @@ bool PPCInstrInfo::optimizeCompareInstr(MachineInstr *CmpInstr,
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isFP && (IOpC == PPC::FSUB || IOpC == PPC::FSUBS) &&
|
|
||||||
((Instr.getOperand(1).getReg() == SrcReg &&
|
|
||||||
Instr.getOperand(2).getReg() == SrcReg2) ||
|
|
||||||
(Instr.getOperand(1).getReg() == SrcReg2 &&
|
|
||||||
Instr.getOperand(2).getReg() == SrcReg))) {
|
|
||||||
Sub = &*I;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (I == B)
|
if (I == B)
|
||||||
// The 'and' is below the comparison instruction.
|
// The 'and' is below the comparison instruction.
|
||||||
return false;
|
return false;
|
||||||
@ -1286,8 +1280,7 @@ bool PPCInstrInfo::optimizeCompareInstr(MachineInstr *CmpInstr,
|
|||||||
|
|
||||||
// The operands to subf are the opposite of sub, so only in the fixed-point
|
// The operands to subf are the opposite of sub, so only in the fixed-point
|
||||||
// case, invert the order.
|
// case, invert the order.
|
||||||
if (!isFP)
|
ShouldSwap = !ShouldSwap;
|
||||||
ShouldSwap = !ShouldSwap;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ShouldSwap)
|
if (ShouldSwap)
|
||||||
@ -1326,7 +1319,7 @@ bool PPCInstrInfo::optimizeCompareInstr(MachineInstr *CmpInstr,
|
|||||||
MachineBasicBlock::iterator MII = MI;
|
MachineBasicBlock::iterator MII = MI;
|
||||||
BuildMI(*MI->getParent(), llvm::next(MII), MI->getDebugLoc(),
|
BuildMI(*MI->getParent(), llvm::next(MII), MI->getDebugLoc(),
|
||||||
get(TargetOpcode::COPY), CRReg)
|
get(TargetOpcode::COPY), CRReg)
|
||||||
.addReg(CRRecReg, MIOpC != NewOpC ? RegState::Kill : 0);
|
.addReg(PPC::CR0, MIOpC != NewOpC ? RegState::Kill : 0);
|
||||||
|
|
||||||
if (MIOpC != NewOpC) {
|
if (MIOpC != NewOpC) {
|
||||||
// We need to be careful here: we're replacing one instruction with
|
// We need to be careful here: we're replacing one instruction with
|
||||||
|
@ -118,7 +118,7 @@ entry:
|
|||||||
ret double %cond
|
ret double %cond
|
||||||
|
|
||||||
; CHECK: @food
|
; CHECK: @food
|
||||||
; CHECK: fsub. 0, 1, 2
|
; CHECK-NOT: fsub. 0, 1, 2
|
||||||
; CHECK: stfd 0, 0(5)
|
; CHECK: stfd 0, 0(5)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -131,7 +131,7 @@ entry:
|
|||||||
ret float %cond
|
ret float %cond
|
||||||
|
|
||||||
; CHECK: @foof
|
; CHECK: @foof
|
||||||
; CHECK: fsubs. 0, 1, 2
|
; CHECK-NOT: fsubs. 0, 1, 2
|
||||||
; CHECK: stfs 0, 0(5)
|
; CHECK: stfs 0, 0(5)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user