@@ -53,7 +53,7 @@ void SSAUpdaterBulk::AddAvailableValue(unsigned Var, BasicBlock *BB, Value *V) {
5353 LLVM_DEBUG (dbgs () << " SSAUpdater: Var=" << Var
5454 << " : added new available value " << *V << " in "
5555 << BB->getName () << " \n " );
56- Rewrites[Var].Defines [BB] = V ;
56+ Rewrites[Var].Defines . emplace_back (BB, V) ;
5757}
5858
5959// / Record a use of the symbolic value. This use will be updated with a
@@ -65,21 +65,6 @@ void SSAUpdaterBulk::AddUse(unsigned Var, Use *U) {
6565 Rewrites[Var].Uses .push_back (U);
6666}
6767
68- // Compute value at the given block BB. We either should already know it, or we
69- // should be able to recursively reach it going up dominator tree.
70- Value *SSAUpdaterBulk::computeValueAt (BasicBlock *BB, RewriteInfo &R,
71- DominatorTree *DT) {
72- if (!R.Defines .count (BB)) {
73- if (DT->isReachableFromEntry (BB) && PredCache.get (BB).size ()) {
74- BasicBlock *IDom = DT->getNode (BB)->getIDom ()->getBlock ();
75- Value *V = computeValueAt (IDom, R, DT);
76- R.Defines [BB] = V;
77- } else
78- R.Defines [BB] = UndefValue::get (R.Ty );
79- }
80- return R.Defines [BB];
81- }
82-
8368// / Given sets of UsingBlocks and DefBlocks, compute the set of LiveInBlocks.
8469// / This is basically a subgraph limited by DefBlocks and UsingBlocks.
8570static void
@@ -117,11 +102,19 @@ ComputeLiveInBlocks(const SmallPtrSetImpl<BasicBlock *> &UsingBlocks,
117102 }
118103}
119104
105+ struct BBValueInfo {
106+ Value *LiveInValue = nullptr ;
107+ Value *LiveOutValue = nullptr ;
108+ };
109+
120110// / Perform all the necessary updates, including new PHI-nodes insertion and the
121111// / requested uses update.
122112void SSAUpdaterBulk::RewriteAllUses (DominatorTree *DT,
123113 SmallVectorImpl<PHINode *> *InsertedPHIs) {
114+ DenseMap<BasicBlock *, BBValueInfo> BBInfos;
124115 for (auto &R : Rewrites) {
116+ BBInfos.clear ();
117+
125118 // Compute locations for new phi-nodes.
126119 // For that we need to initialize DefBlocks from definitions in R.Defines,
127120 // UsingBlocks from uses in R.Uses, then compute LiveInBlocks, and then use
@@ -132,8 +125,8 @@ void SSAUpdaterBulk::RewriteAllUses(DominatorTree *DT,
132125 << " use(s)\n " );
133126
134127 SmallPtrSet<BasicBlock *, 2 > DefBlocks;
135- for (auto &Def : R.Defines )
136- DefBlocks.insert (Def. first );
128+ for (auto [BB, V] : R.Defines )
129+ DefBlocks.insert (BB );
137130 IDF.setDefiningBlocks (DefBlocks);
138131
139132 SmallPtrSet<BasicBlock *, 2 > UsingBlocks;
@@ -143,34 +136,82 @@ void SSAUpdaterBulk::RewriteAllUses(DominatorTree *DT,
143136 SmallVector<BasicBlock *, 32 > IDFBlocks;
144137 SmallPtrSet<BasicBlock *, 32 > LiveInBlocks;
145138 ComputeLiveInBlocks (UsingBlocks, DefBlocks, LiveInBlocks, PredCache);
146- IDF.resetLiveInBlocks ();
147139 IDF.setLiveInBlocks (LiveInBlocks);
148140 IDF.calculate (IDFBlocks);
149141
142+ // Reserve sufficient buckets to prevent map growth. [1]
143+ BBInfos.reserve (LiveInBlocks.size () + DefBlocks.size ());
144+
145+ for (auto [BB, V] : R.Defines )
146+ BBInfos[BB].LiveOutValue = V;
147+
150148 // We've computed IDF, now insert new phi-nodes there.
151- SmallVector<PHINode *, 4 > InsertedPHIsForVar;
152149 for (auto *FrontierBB : IDFBlocks) {
153150 IRBuilder<> B (FrontierBB, FrontierBB->begin ());
154151 PHINode *PN = B.CreatePHI (R.Ty , 0 , R.Name );
155- R.Defines [FrontierBB] = PN;
156- InsertedPHIsForVar.push_back (PN);
152+ BBInfos[FrontierBB].LiveInValue = PN;
157153 if (InsertedPHIs)
158154 InsertedPHIs->push_back (PN);
159155 }
160156
157+ // IsLiveOut indicates whether we are computing live-out values (true) or
158+ // live-in values (false).
159+ auto ComputeValue = [&](BasicBlock *BB, bool IsLiveOut) -> Value * {
160+ auto *BBInfo = &BBInfos[BB];
161+
162+ if (IsLiveOut && BBInfo->LiveOutValue )
163+ return BBInfo->LiveOutValue ;
164+
165+ if (BBInfo->LiveInValue )
166+ return BBInfo->LiveInValue ;
167+
168+ SmallVector<BBValueInfo *, 4 > Stack = {BBInfo};
169+ Value *V = nullptr ;
170+
171+ while (DT->isReachableFromEntry (BB) && !PredCache.get (BB).empty () &&
172+ (BB = DT->getNode (BB)->getIDom ()->getBlock ())) {
173+ BBInfo = &BBInfos[BB];
174+
175+ if (BBInfo->LiveOutValue ) {
176+ V = BBInfo->LiveOutValue ;
177+ break ;
178+ }
179+
180+ if (BBInfo->LiveInValue ) {
181+ V = BBInfo->LiveInValue ;
182+ break ;
183+ }
184+
185+ Stack.emplace_back (BBInfo);
186+ }
187+
188+ if (!V)
189+ V = UndefValue::get (R.Ty );
190+
191+ for (auto *BBInfo : Stack)
192+ // Loop above can insert new entries into the BBInfos map: assume the
193+ // map shouldn't grow due to [1] and BBInfo references are valid.
194+ BBInfo->LiveInValue = V;
195+
196+ return V;
197+ };
198+
161199 // Fill in arguments of the inserted PHIs.
162- for (auto *PN : InsertedPHIsForVar ) {
163- BasicBlock *PBB = PN-> getParent ( );
164- for (BasicBlock *Pred : PredCache.get (PBB ))
165- PN ->addIncoming (computeValueAt (Pred, R, DT ), Pred);
200+ for (auto *BB : IDFBlocks ) {
201+ auto *PHI = cast<PHINode>(&BB-> front () );
202+ for (BasicBlock *Pred : PredCache.get (BB ))
203+ PHI ->addIncoming (ComputeValue (Pred, /* IsLiveOut= */ true ), Pred);
166204 }
167205
168206 // Rewrite actual uses with the inserted definitions.
169207 SmallPtrSet<Use *, 4 > ProcessedUses;
170208 for (Use *U : R.Uses ) {
171209 if (!ProcessedUses.insert (U).second )
172210 continue ;
173- Value *V = computeValueAt (getUserBB (U), R, DT);
211+
212+ auto *User = cast<Instruction>(U->getUser ());
213+ BasicBlock *BB = getUserBB (U);
214+ Value *V = ComputeValue (BB, /* IsLiveOut=*/ BB != User->getParent ());
174215 Value *OldVal = U->get ();
175216 assert (OldVal && " Invalid use!" );
176217 // Notify that users of the existing value that it is being replaced.
0 commit comments