diff options
Diffstat (limited to 'llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp')
-rw-r--r-- | llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp | 32 |
1 files changed, 30 insertions, 2 deletions
diff --git a/llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp b/llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp index c6dc50143c0..2e1c1abf5b6 100644 --- a/llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp +++ b/llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp @@ -544,7 +544,7 @@ SDNode *PPCDAGToDAGISel::SelectBitfieldInsert(SDNode *N) { // Predict the number of instructions that would be generated by calling // SelectInt64(N). -static unsigned SelectInt64Count(int64_t Imm) { +static unsigned SelectInt64CountDirect(int64_t Imm) { // Assume no remaining bits. unsigned Remainder = 0; // Assume no shift required. @@ -602,9 +602,21 @@ static unsigned SelectInt64Count(int64_t Imm) { return Result; } +static unsigned SelectInt64Count(int64_t Imm) { + unsigned DirectCount = SelectInt64CountDirect(Imm); + + // If might be cheaper to materialize the bit-inverted constant, and then + // flip the bits (which takes one nor instruction). + unsigned NotDirectCount = SelectInt64CountDirect(~(uint64_t) Imm) + 1; + if (NotDirectCount < DirectCount) + return NotDirectCount; + + return DirectCount; +} + // Select a 64-bit constant. For cost-modeling purposes, SelectInt64Count // (above) needs to be kept in sync with this function. -static SDNode *SelectInt64(SelectionDAG *CurDAG, SDLoc dl, int64_t Imm) { +static SDNode *SelectInt64Direct(SelectionDAG *CurDAG, SDLoc dl, int64_t Imm) { // Assume no remaining bits. unsigned Remainder = 0; // Assume no shift required. @@ -678,6 +690,22 @@ static SDNode *SelectInt64(SelectionDAG *CurDAG, SDLoc dl, int64_t Imm) { return Result; } +static SDNode *SelectInt64(SelectionDAG *CurDAG, SDLoc dl, int64_t Imm) { + unsigned DirectCount = SelectInt64CountDirect(Imm); + + // If might be cheaper to materialize the bit-inverted constant, and then + // flip the bits (which takes one nor instruction). + unsigned NotDirectCount = SelectInt64CountDirect(~(uint64_t) Imm) + 1; + if (NotDirectCount < DirectCount) { + SDValue NotDirectVal = + SDValue(SelectInt64Direct(CurDAG, dl, ~(uint64_t) Imm), 0); + return CurDAG->getMachineNode(PPC::NOR8, dl, MVT::i64, NotDirectVal, + NotDirectVal); + } + + return SelectInt64Direct(CurDAG, dl, Imm); +} + // Select a 64-bit constant. static SDNode *SelectInt64(SelectionDAG *CurDAG, SDNode *N) { SDLoc dl(N); |