diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2019-01-19 10:04:05 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2019-01-19 10:04:05 +0000 |
commit | 676fbe8105eeb6ff4bb2ed261cb212fcfdbe7b63 (patch) | |
tree | 02a1ac369cb734d0abfa5000dd86e5b7797e6a74 /lib/CodeGen/CGAtomic.cpp | |
parent | c7e70c433efc6953dc3888b9fbf9f3512d7da2b0 (diff) |
Diffstat (limited to 'lib/CodeGen/CGAtomic.cpp')
-rw-r--r-- | lib/CodeGen/CGAtomic.cpp | 28 |
1 files changed, 19 insertions, 9 deletions
diff --git a/lib/CodeGen/CGAtomic.cpp b/lib/CodeGen/CGAtomic.cpp index b34bcdc1fc38d..24056a449def4 100644 --- a/lib/CodeGen/CGAtomic.cpp +++ b/lib/CodeGen/CGAtomic.cpp @@ -18,7 +18,7 @@ #include "TargetInfo.h" #include "clang/AST/ASTContext.h" #include "clang/CodeGen/CGFunctionInfo.h" -#include "clang/Sema/SemaDiagnostic.h" +#include "clang/Frontend/FrontendDiagnostic.h" #include "llvm/ADT/DenseMap.h" #include "llvm/IR/DataLayout.h" #include "llvm/IR/Intrinsics.h" @@ -765,11 +765,15 @@ RValue CodeGenFunction::EmitAtomicExpr(AtomicExpr *E) { std::tie(sizeChars, alignChars) = getContext().getTypeInfoInChars(AtomicTy); uint64_t Size = sizeChars.getQuantity(); unsigned MaxInlineWidthInBits = getTarget().getMaxAtomicInlineWidth(); - bool UseLibcall = ((Ptr.getAlignment() % sizeChars) != 0 || - getContext().toBits(sizeChars) > MaxInlineWidthInBits); - if (UseLibcall) - CGM.getDiags().Report(E->getLocStart(), diag::warn_atomic_op_misaligned); + bool Oversized = getContext().toBits(sizeChars) > MaxInlineWidthInBits; + bool Misaligned = (Ptr.getAlignment() % sizeChars) != 0; + bool UseLibcall = Misaligned | Oversized; + + if (UseLibcall) { + CGM.getDiags().Report(E->getBeginLoc(), diag::warn_atomic_op_misaligned) + << !Oversized; + } llvm::Value *Order = EmitScalarExpr(E->getOrder()); llvm::Value *Scope = @@ -923,6 +927,15 @@ RValue CodeGenFunction::EmitAtomicExpr(AtomicExpr *E) { UseOptimizedLibcall = true; break; + case AtomicExpr::AO__atomic_load: + case AtomicExpr::AO__atomic_store: + case AtomicExpr::AO__atomic_exchange: + case AtomicExpr::AO__atomic_compare_exchange: + // Use the generic version if we don't know that the operand will be + // suitably aligned for the optimized version. + if (Misaligned) + break; + LLVM_FALLTHROUGH; case AtomicExpr::AO__c11_atomic_load: case AtomicExpr::AO__c11_atomic_store: case AtomicExpr::AO__c11_atomic_exchange: @@ -934,14 +947,11 @@ RValue CodeGenFunction::EmitAtomicExpr(AtomicExpr *E) { case AtomicExpr::AO__opencl_atomic_compare_exchange_weak: case AtomicExpr::AO__opencl_atomic_compare_exchange_strong: case AtomicExpr::AO__atomic_load_n: - case AtomicExpr::AO__atomic_load: case AtomicExpr::AO__atomic_store_n: - case AtomicExpr::AO__atomic_store: case AtomicExpr::AO__atomic_exchange_n: - case AtomicExpr::AO__atomic_exchange: case AtomicExpr::AO__atomic_compare_exchange_n: - case AtomicExpr::AO__atomic_compare_exchange: // Only use optimized library calls for sizes for which they exist. + // FIXME: Size == 16 optimized library functions exist too. if (Size == 1 || Size == 2 || Size == 4 || Size == 8) UseOptimizedLibcall = true; break; |