1 //===- ConstantProp.cpp - Code to perform Simple Constant Propagation -----===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 // This file implements constant propagation and merging:
11 // Specifically, this:
12 // * Converts instructions like "add int 1, 2" into 3
15 // * This pass has a habit of making definitions be dead. It is a good idea
16 // to run a DIE pass sometime after running this pass.
18 //===----------------------------------------------------------------------===//
20 #include "llvm/ADT/SmallPtrSet.h"
21 #include "llvm/ADT/SmallVector.h"
22 #include "llvm/ADT/Statistic.h"
23 #include "llvm/Analysis/ConstantFolding.h"
24 #include "llvm/Analysis/TargetLibraryInfo.h"
25 #include "llvm/IR/Constant.h"
26 #include "llvm/IR/InstIterator.h"
27 #include "llvm/IR/Instruction.h"
28 #include "llvm/Pass.h"
29 #include "llvm/Support/DebugCounter.h"
30 #include "llvm/Transforms/Scalar.h"
31 #include "llvm/Transforms/Utils/Local.h"
34 #define DEBUG_TYPE "constprop"
36 STATISTIC(NumInstKilled
, "Number of instructions killed");
37 DEBUG_COUNTER(CPCounter
, "constprop-transform",
38 "Controls which instructions are killed");
41 struct ConstantPropagation
: public FunctionPass
{
42 static char ID
; // Pass identification, replacement for typeid
43 ConstantPropagation() : FunctionPass(ID
) {
44 initializeConstantPropagationPass(*PassRegistry::getPassRegistry());
47 bool runOnFunction(Function
&F
) override
;
49 void getAnalysisUsage(AnalysisUsage
&AU
) const override
{
51 AU
.addRequired
<TargetLibraryInfoWrapperPass
>();
56 char ConstantPropagation::ID
= 0;
57 INITIALIZE_PASS_BEGIN(ConstantPropagation
, "constprop",
58 "Simple constant propagation", false, false)
59 INITIALIZE_PASS_DEPENDENCY(TargetLibraryInfoWrapperPass
)
60 INITIALIZE_PASS_END(ConstantPropagation
, "constprop",
61 "Simple constant propagation", false, false)
63 FunctionPass
*llvm::createConstantPropagationPass() {
64 return new ConstantPropagation();
67 bool ConstantPropagation::runOnFunction(Function
&F
) {
71 // Initialize the worklist to all of the instructions ready to process...
72 SmallPtrSet
<Instruction
*, 16> WorkList
;
73 // The SmallVector of WorkList ensures that we do iteration at stable order.
74 // We use two containers rather than one SetVector, since remove is
75 // linear-time, and we don't care enough to remove from Vec.
76 SmallVector
<Instruction
*, 16> WorkListVec
;
77 for (Instruction
&I
: instructions(&F
)) {
79 WorkListVec
.push_back(&I
);
83 const DataLayout
&DL
= F
.getParent()->getDataLayout();
84 TargetLibraryInfo
*TLI
=
85 &getAnalysis
<TargetLibraryInfoWrapperPass
>().getTLI();
87 while (!WorkList
.empty()) {
88 SmallVector
<Instruction
*, 16> NewWorkListVec
;
89 for (auto *I
: WorkListVec
) {
90 WorkList
.erase(I
); // Remove element from the worklist...
92 if (!I
->use_empty()) // Don't muck with dead instructions...
93 if (Constant
*C
= ConstantFoldInstruction(I
, DL
, TLI
)) {
94 if (!DebugCounter::shouldExecute(CPCounter
))
97 // Add all of the users of this instruction to the worklist, they might
98 // be constant propagatable now...
99 for (User
*U
: I
->users()) {
100 // If user not in the set, then add it to the vector.
101 if (WorkList
.insert(cast
<Instruction
>(U
)).second
)
102 NewWorkListVec
.push_back(cast
<Instruction
>(U
));
105 // Replace all of the uses of a variable with uses of the constant.
106 I
->replaceAllUsesWith(C
);
108 if (isInstructionTriviallyDead(I
, TLI
)) {
109 I
->eraseFromParent();
113 // We made a change to the function...
117 WorkListVec
= std::move(NewWorkListVec
);