diff options
| -rw-r--r-- | llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp | 9 | ||||
| -rw-r--r-- | llvm/test/CodeGen/PowerPC/peephole-align.ll | 8 | 
2 files changed, 12 insertions, 5 deletions
diff --git a/llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp b/llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp index f30aecf3000..23ee3e7312f 100644 --- a/llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp +++ b/llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp @@ -4370,10 +4370,15 @@ void PPCDAGToDAGISel::PeepholePPC64() {      }      SDValue ImmOpnd = Base.getOperand(1); -    int MaxDisplacement = 0; + +    // On PPC64, the TOC base pointer is guaranteed by the ABI only to have +    // 8-byte alignment, and so we can only use offsets less than 8 (otherwise, +    // we might have needed different @ha relocation values for the offset +    // pointers). +    int MaxDisplacement = 7;      if (GlobalAddressSDNode *GA = dyn_cast<GlobalAddressSDNode>(ImmOpnd)) {        const GlobalValue *GV = GA->getGlobal(); -      MaxDisplacement = GV->getAlignment() - 1; +      MaxDisplacement = std::min((int) GV->getAlignment() - 1, MaxDisplacement);      }      int Offset = N->getConstantOperandVal(FirstOp); diff --git a/llvm/test/CodeGen/PowerPC/peephole-align.ll b/llvm/test/CodeGen/PowerPC/peephole-align.ll index cb0dde91242..1be84170734 100644 --- a/llvm/test/CodeGen/PowerPC/peephole-align.ll +++ b/llvm/test/CodeGen/PowerPC/peephole-align.ll @@ -208,12 +208,13 @@ entry:  ; CHECK-LABEL: test_d2:  ; CHECK: addis [[REGSTRUCT:[0-9]+]], 2, d2v@toc@ha +; CHECK: addi [[BASEV:[0-9]+]], [[REGSTRUCT]], d2v@toc@l  ; CHECK-DAG: ld [[REG0_0:[0-9]+]], d2v@toc@l([[REGSTRUCT]]) -; CHECK-DAG: ld [[REG1_0:[0-9]+]], d2v@toc@l+8([[REGSTRUCT]]) +; CHECK-DAG: ld [[REG1_0:[0-9]+]], 8([[BASEV]])  ; CHECK-DAG: addi [[REG0_1:[0-9]+]], [[REG0_0]], 1  ; CHECK-DAG: addi [[REG1_1:[0-9]+]], [[REG1_0]], 2  ; CHECK-DAG: std [[REG0_1]], d2v@toc@l([[REGSTRUCT]]) -; CHECK-DAG: std [[REG1_1]], d2v@toc@l+8([[REGSTRUCT]]) +; CHECK-DAG: std [[REG1_1]], 8([[BASEV]])  define void @test_d2() nounwind {  entry: @@ -229,7 +230,8 @@ entry:  ; register 3 is the return value, so it should be chosen  ; CHECK-LABEL: test_singleuse:  ; CHECK: addis 3, 2, d2v@toc@ha -; CHECK: ld 3, d2v@toc@l+8(3) +; CHECK: addi 3, 3, d2v@toc@l +; CHECK: ld 3, 8(3)  define i64 @test_singleuse() nounwind {  entry:    %0 = load i64, i64* getelementptr inbounds (%struct.d2, %struct.d2* @d2v, i32 0, i32 1), align 8  | 

