003 File Manager
Current Path:
/usr/src/contrib/llvm-project/llvm/lib/Transforms/Scalar
usr
/
src
/
contrib
/
llvm-project
/
llvm
/
lib
/
Transforms
/
Scalar
/
📁
..
📄
ADCE.cpp
(24.71 KB)
📄
AlignmentFromAssumptions.cpp
(15.9 KB)
📄
BDCE.cpp
(7.42 KB)
📄
CallSiteSplitting.cpp
(21.43 KB)
📄
ConstantHoisting.cpp
(38.95 KB)
📄
ConstantProp.cpp
(4.13 KB)
📄
CorrelatedValuePropagation.cpp
(32.36 KB)
📄
DCE.cpp
(6.84 KB)
📄
DeadStoreElimination.cpp
(91.51 KB)
📄
DivRemPairs.cpp
(15.01 KB)
📄
EarlyCSE.cpp
(57.05 KB)
📄
FlattenCFGPass.cpp
(2.74 KB)
📄
Float2Int.cpp
(18.19 KB)
📄
GVN.cpp
(100.11 KB)
📄
GVNHoist.cpp
(44.85 KB)
📄
GVNSink.cpp
(29.97 KB)
📄
GuardWidening.cpp
(32.36 KB)
📄
IVUsersPrinter.cpp
(839 B)
📄
IndVarSimplify.cpp
(113.49 KB)
📄
InductiveRangeCheckElimination.cpp
(72.96 KB)
📄
InferAddressSpaces.cpp
(44.22 KB)
📄
InstSimplifyPass.cpp
(5.39 KB)
📄
JumpThreading.cpp
(115.06 KB)
📄
LICM.cpp
(92.71 KB)
📄
LoopAccessAnalysisPrinter.cpp
(977 B)
📄
LoopDataPrefetch.cpp
(14.54 KB)
📄
LoopDeletion.cpp
(11.37 KB)
📄
LoopDistribute.cpp
(40.25 KB)
📄
LoopFuse.cpp
(68.6 KB)
📄
LoopIdiomRecognize.cpp
(69.09 KB)
📄
LoopInstSimplify.cpp
(9.38 KB)
📄
LoopInterchange.cpp
(60.65 KB)
📄
LoopLoadElimination.cpp
(26.71 KB)
📄
LoopPassManager.cpp
(4.02 KB)
📄
LoopPredication.cpp
(49.21 KB)
📄
LoopRerollPass.cpp
(58.54 KB)
📄
LoopRotation.cpp
(4.79 KB)
📄
LoopSimplifyCFG.cpp
(28.59 KB)
📄
LoopSink.cpp
(14.93 KB)
📄
LoopStrengthReduce.cpp
(216.88 KB)
📄
LoopUnrollAndJamPass.cpp
(21.07 KB)
📄
LoopUnrollPass.cpp
(60.73 KB)
📄
LoopUnswitch.cpp
(64.17 KB)
📄
LoopVersioningLICM.cpp
(23.65 KB)
📄
LowerAtomic.cpp
(5.12 KB)
📄
LowerConstantIntrinsics.cpp
(5.8 KB)
📄
LowerExpectIntrinsic.cpp
(15 KB)
📄
LowerGuardIntrinsic.cpp
(2.82 KB)
📄
LowerMatrixIntrinsics.cpp
(73.36 KB)
📄
LowerWidenableCondition.cpp
(2.75 KB)
📄
MakeGuardsExplicit.cpp
(3.83 KB)
📄
MemCpyOptimizer.cpp
(52.16 KB)
📄
MergeICmps.cpp
(35.61 KB)
📄
MergedLoadStoreMotion.cpp
(15.18 KB)
📄
NaryReassociate.cpp
(19.86 KB)
📄
NewGVN.cpp
(170.95 KB)
📄
PartiallyInlineLibCalls.cpp
(6.22 KB)
📄
PlaceSafepoints.cpp
(27.5 KB)
📄
Reassociate.cpp
(95.61 KB)
📄
Reg2Mem.cpp
(4.34 KB)
📄
RewriteStatepointsForGC.cpp
(116.35 KB)
📄
SCCP.cpp
(76.12 KB)
📄
SROA.cpp
(183.83 KB)
📄
Scalar.cpp
(10.08 KB)
📄
Scalarizer.cpp
(32.93 KB)
📄
SeparateConstOffsetFromGEP.cpp
(52.99 KB)
📄
SimpleLoopUnswitch.cpp
(124.57 KB)
📄
SimplifyCFGPass.cpp
(12.31 KB)
📄
Sink.cpp
(10.81 KB)
📄
SpeculateAroundPHIs.cpp
(35.69 KB)
📄
SpeculativeExecution.cpp
(11.54 KB)
📄
StraightLineStrengthReduce.cpp
(28.92 KB)
📄
StructurizeCFG.cpp
(32.49 KB)
📄
TailRecursionElimination.cpp
(34.9 KB)
📄
WarnMissedTransforms.cpp
(6.14 KB)
Editing: LowerAtomic.cpp
//===- LowerAtomic.cpp - Lower atomic intrinsics --------------------------===// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // // This pass lowers atomic intrinsics to non-atomic form for use in a known // non-preemptible environment. // //===----------------------------------------------------------------------===// #include "llvm/Transforms/Scalar/LowerAtomic.h" #include "llvm/IR/Function.h" #include "llvm/IR/IRBuilder.h" #include "llvm/InitializePasses.h" #include "llvm/Pass.h" #include "llvm/Transforms/Scalar.h" using namespace llvm; #define DEBUG_TYPE "loweratomic" static bool LowerAtomicCmpXchgInst(AtomicCmpXchgInst *CXI) { IRBuilder<> Builder(CXI); Value *Ptr = CXI->getPointerOperand(); Value *Cmp = CXI->getCompareOperand(); Value *Val = CXI->getNewValOperand(); LoadInst *Orig = Builder.CreateLoad(Val->getType(), Ptr); Value *Equal = Builder.CreateICmpEQ(Orig, Cmp); Value *Res = Builder.CreateSelect(Equal, Val, Orig); Builder.CreateStore(Res, Ptr); Res = Builder.CreateInsertValue(UndefValue::get(CXI->getType()), Orig, 0); Res = Builder.CreateInsertValue(Res, Equal, 1); CXI->replaceAllUsesWith(Res); CXI->eraseFromParent(); return true; } static bool LowerAtomicRMWInst(AtomicRMWInst *RMWI) { IRBuilder<> Builder(RMWI); Value *Ptr = RMWI->getPointerOperand(); Value *Val = RMWI->getValOperand(); LoadInst *Orig = Builder.CreateLoad(Val->getType(), Ptr); Value *Res = nullptr; switch (RMWI->getOperation()) { default: llvm_unreachable("Unexpected RMW operation"); case AtomicRMWInst::Xchg: Res = Val; break; case AtomicRMWInst::Add: Res = Builder.CreateAdd(Orig, Val); break; case AtomicRMWInst::Sub: Res = Builder.CreateSub(Orig, Val); break; case AtomicRMWInst::And: Res = Builder.CreateAnd(Orig, Val); break; case AtomicRMWInst::Nand: Res = Builder.CreateNot(Builder.CreateAnd(Orig, Val)); break; case AtomicRMWInst::Or: Res = Builder.CreateOr(Orig, Val); break; case AtomicRMWInst::Xor: Res = Builder.CreateXor(Orig, Val); break; case AtomicRMWInst::Max: Res = Builder.CreateSelect(Builder.CreateICmpSLT(Orig, Val), Val, Orig); break; case AtomicRMWInst::Min: Res = Builder.CreateSelect(Builder.CreateICmpSLT(Orig, Val), Orig, Val); break; case AtomicRMWInst::UMax: Res = Builder.CreateSelect(Builder.CreateICmpULT(Orig, Val), Val, Orig); break; case AtomicRMWInst::UMin: Res = Builder.CreateSelect(Builder.CreateICmpULT(Orig, Val), Orig, Val); break; case AtomicRMWInst::FAdd: Res = Builder.CreateFAdd(Orig, Val); break; case AtomicRMWInst::FSub: Res = Builder.CreateFSub(Orig, Val); break; } Builder.CreateStore(Res, Ptr); RMWI->replaceAllUsesWith(Orig); RMWI->eraseFromParent(); return true; } static bool LowerFenceInst(FenceInst *FI) { FI->eraseFromParent(); return true; } static bool LowerLoadInst(LoadInst *LI) { LI->setAtomic(AtomicOrdering::NotAtomic); return true; } static bool LowerStoreInst(StoreInst *SI) { SI->setAtomic(AtomicOrdering::NotAtomic); return true; } static bool runOnBasicBlock(BasicBlock &BB) { bool Changed = false; for (Instruction &Inst : make_early_inc_range(BB)) { if (FenceInst *FI = dyn_cast<FenceInst>(&Inst)) Changed |= LowerFenceInst(FI); else if (AtomicCmpXchgInst *CXI = dyn_cast<AtomicCmpXchgInst>(&Inst)) Changed |= LowerAtomicCmpXchgInst(CXI); else if (AtomicRMWInst *RMWI = dyn_cast<AtomicRMWInst>(&Inst)) Changed |= LowerAtomicRMWInst(RMWI); else if (LoadInst *LI = dyn_cast<LoadInst>(&Inst)) { if (LI->isAtomic()) LowerLoadInst(LI); } else if (StoreInst *SI = dyn_cast<StoreInst>(&Inst)) { if (SI->isAtomic()) LowerStoreInst(SI); } } return Changed; } static bool lowerAtomics(Function &F) { bool Changed = false; for (BasicBlock &BB : F) { Changed |= runOnBasicBlock(BB); } return Changed; } PreservedAnalyses LowerAtomicPass::run(Function &F, FunctionAnalysisManager &) { if (lowerAtomics(F)) return PreservedAnalyses::none(); return PreservedAnalyses::all(); } namespace { class LowerAtomicLegacyPass : public FunctionPass { public: static char ID; LowerAtomicLegacyPass() : FunctionPass(ID) { initializeLowerAtomicLegacyPassPass(*PassRegistry::getPassRegistry()); } bool runOnFunction(Function &F) override { // Don't skip optnone functions; atomics still need to be lowered. FunctionAnalysisManager DummyFAM; auto PA = Impl.run(F, DummyFAM); return !PA.areAllPreserved(); } private: LowerAtomicPass Impl; }; } char LowerAtomicLegacyPass::ID = 0; INITIALIZE_PASS(LowerAtomicLegacyPass, "loweratomic", "Lower atomic intrinsics to non-atomic form", false, false) Pass *llvm::createLowerAtomicPass() { return new LowerAtomicLegacyPass(); }
Upload File
Create Folder