diff options
author | Hal Finkel <hfinkel@anl.gov> | 2014-09-07 22:58:14 +0000 |
---|---|---|
committer | Hal Finkel <hfinkel@anl.gov> | 2014-09-07 22:58:14 +0000 |
commit | bcc06085a894aa52f094e12a8cfdd36ae1f175af (patch) | |
tree | 5d932a55113890c2447f77376b89f3e48f36c8b0 /clang/lib/CodeGen/CGExpr.cpp | |
parent | cebf0cc210edeb839894b0e93da1c5787bd5b68b (diff) | |
download | bcm5719-llvm-bcc06085a894aa52f094e12a8cfdd36ae1f175af.tar.gz bcm5719-llvm-bcc06085a894aa52f094e12a8cfdd36ae1f175af.zip |
Add __builtin_assume and __builtin_assume_aligned using @llvm.assume.
This makes use of the recently-added @llvm.assume intrinsic to implement a
__builtin_assume(bool) intrinsic (to provide additional information to the
optimizer). This hooks up __assume in MS-compatibility mode to mirror
__builtin_assume (the semantics have been intentionally kept compatible), and
implements GCC's __builtin_assume_aligned as assume((p - o) & mask == 0). LLVM
now contains special logic to deal with assumptions of this form.
llvm-svn: 217349
Diffstat (limited to 'clang/lib/CodeGen/CGExpr.cpp')
-rw-r--r-- | clang/lib/CodeGen/CGExpr.cpp | 28 |
1 files changed, 28 insertions, 0 deletions
diff --git a/clang/lib/CodeGen/CGExpr.cpp b/clang/lib/CodeGen/CGExpr.cpp index fc9e60d1329..426ec7496c4 100644 --- a/clang/lib/CodeGen/CGExpr.cpp +++ b/clang/lib/CodeGen/CGExpr.cpp @@ -711,6 +711,34 @@ EmitComplexPrePostIncDec(const UnaryOperator *E, LValue LV, return isPre ? IncVal : InVal; } +void CodeGenFunction::EmitAlignmentAssumption(llvm::Value *PtrValue, + unsigned Alignment, + llvm::Value *OffsetValue) { + llvm::Value *PtrIntValue = + Builder.CreatePtrToInt(PtrValue, IntPtrTy, "ptrint"); + + llvm::Value *Mask = llvm::ConstantInt::get(IntPtrTy, + Alignment > 0 ? Alignment - 1 : 0); + if (OffsetValue) { + bool IsOffsetZero = false; + if (llvm::ConstantInt *CI = dyn_cast<llvm::ConstantInt>(OffsetValue)) + IsOffsetZero = CI->isZero(); + + if (!IsOffsetZero) { + if (OffsetValue->getType() != IntPtrTy) + OffsetValue = Builder.CreateIntCast(OffsetValue, IntPtrTy, + /*isSigned*/true, "offsetcast"); + PtrIntValue = Builder.CreateSub(PtrIntValue, OffsetValue, "offsetptr"); + } + } + + llvm::Value *Zero = llvm::ConstantInt::get(IntPtrTy, 0); + llvm::Value *MaskedPtr = Builder.CreateAnd(PtrIntValue, Mask, "maskedptr"); + llvm::Value *InvCond = Builder.CreateICmpEQ(MaskedPtr, Zero, "maskcond"); + + llvm::Value *FnAssume = CGM.getIntrinsic(llvm::Intrinsic::assume); + Builder.CreateCall(FnAssume, InvCond); +} //===----------------------------------------------------------------------===// // LValue Expression Emission |