mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-01-12 17:32:19 +00:00
teach instcombine to optimize pointer difference idioms involving constant
expressions. This is a step towards comment #4 in PR3351. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@92401 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
3376718505
commit
f2ebc682d1
@ -437,7 +437,7 @@ m_SelectCst(const Cond &C) {
|
|||||||
// Matchers for CastInst classes
|
// Matchers for CastInst classes
|
||||||
//
|
//
|
||||||
|
|
||||||
template<typename Op_t, typename Class>
|
template<typename Op_t, unsigned Opcode>
|
||||||
struct CastClass_match {
|
struct CastClass_match {
|
||||||
Op_t Op;
|
Op_t Op;
|
||||||
|
|
||||||
@ -445,15 +445,26 @@ struct CastClass_match {
|
|||||||
|
|
||||||
template<typename OpTy>
|
template<typename OpTy>
|
||||||
bool match(OpTy *V) {
|
bool match(OpTy *V) {
|
||||||
if (Class *I = dyn_cast<Class>(V))
|
if (CastInst *I = dyn_cast<CastInst>(V))
|
||||||
return Op.match(I->getOperand(0));
|
return I->getOpcode() == Opcode && Op.match(I->getOperand(0));
|
||||||
|
if (ConstantExpr *CE = dyn_cast<ConstantExpr>(V))
|
||||||
|
return CE->getOpcode() == Opcode && Op.match(CE->getOperand(0));
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename Class, typename OpTy>
|
/// m_PtrToInt
|
||||||
inline CastClass_match<OpTy, Class> m_Cast(const OpTy &Op) {
|
template<typename OpTy>
|
||||||
return CastClass_match<OpTy, Class>(Op);
|
inline CastClass_match<OpTy, Instruction::PtrToInt>
|
||||||
|
m_PtrToInt(const OpTy &Op) {
|
||||||
|
return CastClass_match<OpTy, Instruction::PtrToInt>(Op);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// m_Trunc
|
||||||
|
template<typename OpTy>
|
||||||
|
inline CastClass_match<OpTy, Instruction::Trunc>
|
||||||
|
m_Trunc(const OpTy &Op) {
|
||||||
|
return CastClass_match<OpTy, Instruction::Trunc>(Op);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2950,19 +2950,15 @@ Instruction *InstCombiner::visitSub(BinaryOperator &I) {
|
|||||||
// &A[10] - &A[0]: we should compile this to "10".
|
// &A[10] - &A[0]: we should compile this to "10".
|
||||||
if (TD) {
|
if (TD) {
|
||||||
Value *LHSOp, *RHSOp;
|
Value *LHSOp, *RHSOp;
|
||||||
if (match(Op0, m_Cast<PtrToIntInst>(m_Value(LHSOp))) &&
|
if (match(Op0, m_PtrToInt(m_Value(LHSOp))) &&
|
||||||
match(Op1, m_Cast<PtrToIntInst>(m_Value(RHSOp))))
|
match(Op1, m_PtrToInt(m_Value(RHSOp))))
|
||||||
if (Value *Res = OptimizePointerDifference(LHSOp, RHSOp, I.getType()))
|
if (Value *Res = OptimizePointerDifference(LHSOp, RHSOp, I.getType()))
|
||||||
return ReplaceInstUsesWith(I, Res);
|
return ReplaceInstUsesWith(I, Res);
|
||||||
|
|
||||||
// trunc(p)-trunc(q) -> trunc(p-q)
|
// trunc(p)-trunc(q) -> trunc(p-q)
|
||||||
if (TruncInst *LHST = dyn_cast<TruncInst>(Op0))
|
if (match(Op0, m_Trunc(m_PtrToInt(m_Value(LHSOp)))) &&
|
||||||
if (TruncInst *RHST = dyn_cast<TruncInst>(Op1))
|
match(Op1, m_Trunc(m_PtrToInt(m_Value(RHSOp)))))
|
||||||
if (PtrToIntInst *LHS = dyn_cast<PtrToIntInst>(LHST->getOperand(0)))
|
if (Value *Res = OptimizePointerDifference(LHSOp, RHSOp, I.getType()))
|
||||||
if (PtrToIntInst *RHS = dyn_cast<PtrToIntInst>(RHST->getOperand(0)))
|
|
||||||
if (Value *Res = OptimizePointerDifference(LHS->getOperand(0),
|
|
||||||
RHS->getOperand(0),
|
|
||||||
I.getType()))
|
|
||||||
return ReplaceInstUsesWith(I, Res);
|
return ReplaceInstUsesWith(I, Res);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -248,3 +248,15 @@ define i64 @test24a(i8* %P, i64 %A){
|
|||||||
; CHECK-NEXT: ret i64
|
; CHECK-NEXT: ret i64
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Arr = external global [42 x i16]
|
||||||
|
|
||||||
|
define i64 @test24b(i8* %P, i64 %A){
|
||||||
|
%B = getelementptr inbounds [42 x i16]* @Arr, i64 0, i64 %A
|
||||||
|
%C = ptrtoint i16* %B to i64
|
||||||
|
%G = sub i64 %C, ptrtoint ([42 x i16]* @Arr to i64)
|
||||||
|
ret i64 %G
|
||||||
|
; CHECK: @test24b
|
||||||
|
; CHECK-NEXT: shl i64 %A, 1
|
||||||
|
; CHECK-NEXT: ret i64
|
||||||
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user