@@ -115,13 +115,11 @@ static bool markLoopInfo(Module &M, Function *marker, function_ref<LoopInfo &(Fu
115115
116116 LoopInfo &LI = GetLI (*I->getParent ()->getParent ());
117117 Loop *L = LI.getLoopFor (I->getParent ());
118- I->removeFromParent ();
119118 if (!L)
120119 continue ;
121120
122121 LLVM_DEBUG (dbgs () << " LSL: loopinfo marker found\n " );
123122 bool simd = false ;
124- bool ivdep = false ;
125123 SmallVector<Metadata *, 8 > MDs;
126124
127125 BasicBlock *Lh = L->getHeader ();
@@ -144,8 +142,6 @@ static bool markLoopInfo(Module &M, Function *marker, function_ref<LoopInfo &(Fu
144142 if (S->getString ().startswith (" julia" )) {
145143 if (S->getString ().equals (" julia.simdloop" ))
146144 simd = true ;
147- if (S->getString ().equals (" julia.ivdep" ))
148- ivdep = true ;
149145 continue ;
150146 }
151147 }
@@ -154,7 +150,9 @@ static bool markLoopInfo(Module &M, Function *marker, function_ref<LoopInfo &(Fu
154150 }
155151 }
156152
157- LLVM_DEBUG (dbgs () << " LSL: simd: " << simd << " ivdep: " << ivdep << " \n " );
153+ LLVM_DEBUG (dbgs () << " LSL: simd: " << simd << " \n " );
154+ if (!simd)
155+ continue ;
158156
159157 MDNode *n = L->getLoopID ();
160158 if (n) {
@@ -173,40 +171,62 @@ static bool markLoopInfo(Module &M, Function *marker, function_ref<LoopInfo &(Fu
173171
174172 MDNode *m = MDNode::get (Lh->getContext (), ArrayRef<Metadata *>(LoopID));
175173
176- // If ivdep is true we assume that there is no memory dependency between loop iterations
174+ // mark the inner-most loop is free of memory dependency within julia ivdep scope.
177175 // This is a fairly strong assumption and does often not hold true for generic code.
178- if (ivdep) {
179- // Mark memory references so that Loop::isAnnotatedParallel will return true for this loop.
180- for (BasicBlock *BB : L->blocks ()) {
181- for (Instruction &I : *BB) {
182- if (I.mayReadOrWriteMemory ()) {
183- I.setMetadata (LLVMContext::MD_mem_parallel_loop_access, m);
184- }
185- }
176+ int ivdep = 0 ;
177+ for (BasicBlock *BB : L->blocks ()) {
178+ for (Instruction &I : *BB) {
179+ if (I.hasMetadataOtherThanDebugLoc ()) {
180+ if (MDNode *JLMD= I.getMetadata (" julia.ivdepscope" )) {
181+ ToDelete.push_back (&I);
182+ LLVM_DEBUG (dbgs () << " LSL: found julia.ivdepscope " );
183+ if (JLMD->getNumOperands () < 1 )
184+ continue ;
185+ if (MDString *S = dyn_cast<MDString>(JLMD->getOperand (0 ))) {
186+ LLVM_DEBUG (dbgs () << S->getString () << " \n " );
187+ if (S->getString ().equals (" begin" ))
188+ ivdep += 1 ;
189+ else
190+ ivdep -= 1 ;
191+ }
192+ }
193+ }
194+ if (ivdep > 0 &&I.mayReadOrWriteMemory ()) {
195+ I.setMetadata (LLVMContext::MD_mem_parallel_loop_access, m);
196+ }
186197 }
187- assert (L->isAnnotatedParallel ());
188198 }
189-
190- if (simd) {
191- // Mark floating-point reductions as okay to reassociate/commute.
192- for (BasicBlock::iterator I = Lh-> begin (), E = Lh-> end (); I != E; ++I) {
193- if (PHINode *Phi = dyn_cast<PHINode>(I))
194- enableUnsafeAlgebraIfReduction (Phi, L);
195- else
196- break ;
197- }
199+ // if ivdep != 0
200+ // thrown() ??
201+
202+ // Mark floating-point reductions as okay to reassociate/commute.
203+ for (BasicBlock::iterator I = Lh-> begin (), E = Lh-> end (); I != E; ++I) {
204+ if (PHINode *Phi = dyn_cast<PHINode>(I))
205+ enableUnsafeAlgebraIfReduction (Phi, L);
206+ else
207+ break ;
198208 }
199209
200210 Changed = true ;
201211 }
202212
203213 for (Instruction *I : ToDelete)
204- I->deleteValue ();
214+ I->eraseFromParent ();
205215 marker->eraseFromParent ();
206216
207217 return Changed;
208218}
209219
220+ static void eraseIvdepScope (Module &M, Function *marker)
221+ {
222+ for (User *U : marker->users ()) {
223+ Instruction *I = cast<Instruction>(U);
224+ // remove "ivdepscope" from unreachable branch to make error message clearer.
225+ if (isa<UnreachableInst>(I -> getParent () -> back ()))
226+ I -> eraseFromParent ();
227+ }
228+ }
229+
210230} // end anonymous namespace
211231
212232
@@ -223,7 +243,12 @@ PreservedAnalyses LowerSIMDLoop::run(Module &M, ModuleAnalysisManager &AM)
223243 Function *loopinfo_marker = M.getFunction (" julia.loopinfo_marker" );
224244
225245 if (!loopinfo_marker)
246+ {
247+ Function *ivdepscope = M.getFunction (" julia.ivdepscope" );
248+ if (ivdepscope)
249+ eraseIvdepScope (M, ivdepscope);
226250 return PreservedAnalyses::all ();
251+ }
227252
228253 FunctionAnalysisManager &FAM =
229254 AM.getResult <FunctionAnalysisManagerModuleProxy>(M).getManager ();
@@ -258,6 +283,11 @@ class LowerSIMDLoopLegacy : public ModulePass {
258283
259284 if (loopinfo_marker)
260285 Changed |= markLoopInfo (M, loopinfo_marker, GetLI);
286+ else {
287+ Function *ivdepscope = M.getFunction (" julia.ivdepscope" );
288+ if (ivdepscope)
289+ eraseIvdepScope (M, ivdepscope);
290+ }
261291
262292 return Changed;
263293 }
0 commit comments