1 //===- AliasSetTracker.cpp - Alias Sets Tracker implementation-------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file implements the AliasSetTracker and AliasSet classes. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #include "llvm/Analysis/AliasSetTracker.h" 15 #include "llvm/Analysis/AliasAnalysis.h" 16 #include "llvm/IR/DataLayout.h" 17 #include "llvm/IR/InstIterator.h" 18 #include "llvm/IR/Instructions.h" 19 #include "llvm/IR/IntrinsicInst.h" 20 #include "llvm/IR/Module.h" 21 #include "llvm/IR/LLVMContext.h" 22 #include "llvm/IR/Type.h" 23 #include "llvm/Pass.h" 24 #include "llvm/Support/Debug.h" 25 #include "llvm/Support/ErrorHandling.h" 26 #include "llvm/Support/raw_ostream.h" 27 using namespace llvm; 28 29 /// mergeSetIn - Merge the specified alias set into this alias set. 30 /// 31 void AliasSet::mergeSetIn(AliasSet &AS, AliasSetTracker &AST) { 32 assert(!AS.Forward && "Alias set is already forwarding!"); 33 assert(!Forward && "This set is a forwarding set!!"); 34 35 // Update the alias and access types of this set... 36 Access |= AS.Access; 37 Alias |= AS.Alias; 38 Volatile |= AS.Volatile; 39 40 if (Alias == SetMustAlias) { 41 // Check that these two merged sets really are must aliases. Since both 42 // used to be must-alias sets, we can just check any pointer from each set 43 // for aliasing. 44 AliasAnalysis &AA = AST.getAliasAnalysis(); 45 PointerRec *L = getSomePointer(); 46 PointerRec *R = AS.getSomePointer(); 47 48 // If the pointers are not a must-alias pair, this set becomes a may alias. 49 if (AA.alias(MemoryLocation(L->getValue(), L->getSize(), L->getAAInfo()), 50 MemoryLocation(R->getValue(), R->getSize(), R->getAAInfo())) != 51 MustAlias) 52 Alias = SetMayAlias; 53 } 54 55 bool ASHadUnknownInsts = !AS.UnknownInsts.empty(); 56 if (UnknownInsts.empty()) { // Merge call sites... 57 if (ASHadUnknownInsts) { 58 std::swap(UnknownInsts, AS.UnknownInsts); 59 addRef(); 60 } 61 } else if (ASHadUnknownInsts) { 62 UnknownInsts.insert(UnknownInsts.end(), AS.UnknownInsts.begin(), AS.UnknownInsts.end()); 63 AS.UnknownInsts.clear(); 64 } 65 66 AS.Forward = this; // Forward across AS now... 67 addRef(); // AS is now pointing to us... 68 69 // Merge the list of constituent pointers... 70 if (AS.PtrList) { 71 *PtrListEnd = AS.PtrList; 72 AS.PtrList->setPrevInList(PtrListEnd); 73 PtrListEnd = AS.PtrListEnd; 74 75 AS.PtrList = nullptr; 76 AS.PtrListEnd = &AS.PtrList; 77 assert(*AS.PtrListEnd == nullptr && "End of list is not null?"); 78 } 79 if (ASHadUnknownInsts) 80 AS.dropRef(AST); 81 } 82 83 void AliasSetTracker::removeAliasSet(AliasSet *AS) { 84 if (AliasSet *Fwd = AS->Forward) { 85 Fwd->dropRef(*this); 86 AS->Forward = nullptr; 87 } 88 AliasSets.erase(AS); 89 } 90 91 void AliasSet::removeFromTracker(AliasSetTracker &AST) { 92 assert(RefCount == 0 && "Cannot remove non-dead alias set from tracker!"); 93 AST.removeAliasSet(this); 94 } 95 96 void AliasSet::addPointer(AliasSetTracker &AST, PointerRec &Entry, 97 uint64_t Size, const AAMDNodes &AAInfo, 98 bool KnownMustAlias) { 99 assert(!Entry.hasAliasSet() && "Entry already in set!"); 100 101 // Check to see if we have to downgrade to _may_ alias. 102 if (isMustAlias() && !KnownMustAlias) 103 if (PointerRec *P = getSomePointer()) { 104 AliasAnalysis &AA = AST.getAliasAnalysis(); 105 AliasResult Result = 106 AA.alias(MemoryLocation(P->getValue(), P->getSize(), P->getAAInfo()), 107 MemoryLocation(Entry.getValue(), Size, AAInfo)); 108 if (Result != MustAlias) 109 Alias = SetMayAlias; 110 else // First entry of must alias must have maximum size! 111 P->updateSizeAndAAInfo(Size, AAInfo); 112 assert(Result != NoAlias && "Cannot be part of must set!"); 113 } 114 115 Entry.setAliasSet(this); 116 Entry.updateSizeAndAAInfo(Size, AAInfo); 117 118 // Add it to the end of the list... 119 assert(*PtrListEnd == nullptr && "End of list is not null?"); 120 *PtrListEnd = &Entry; 121 PtrListEnd = Entry.setPrevInList(PtrListEnd); 122 assert(*PtrListEnd == nullptr && "End of list is not null?"); 123 addRef(); // Entry points to alias set. 124 } 125 126 void AliasSet::addUnknownInst(Instruction *I, AliasAnalysis &AA) { 127 if (UnknownInsts.empty()) 128 addRef(); 129 UnknownInsts.emplace_back(I); 130 131 if (!I->mayWriteToMemory()) { 132 Alias = SetMayAlias; 133 Access |= RefAccess; 134 return; 135 } 136 137 // FIXME: This should use mod/ref information to make this not suck so bad 138 Alias = SetMayAlias; 139 Access = ModRefAccess; 140 } 141 142 /// aliasesPointer - Return true if the specified pointer "may" (or must) 143 /// alias one of the members in the set. 144 /// 145 bool AliasSet::aliasesPointer(const Value *Ptr, uint64_t Size, 146 const AAMDNodes &AAInfo, 147 AliasAnalysis &AA) const { 148 if (Alias == SetMustAlias) { 149 assert(UnknownInsts.empty() && "Illegal must alias set!"); 150 151 // If this is a set of MustAliases, only check to see if the pointer aliases 152 // SOME value in the set. 153 PointerRec *SomePtr = getSomePointer(); 154 assert(SomePtr && "Empty must-alias set??"); 155 return AA.alias(MemoryLocation(SomePtr->getValue(), SomePtr->getSize(), 156 SomePtr->getAAInfo()), 157 MemoryLocation(Ptr, Size, AAInfo)); 158 } 159 160 // If this is a may-alias set, we have to check all of the pointers in the set 161 // to be sure it doesn't alias the set... 162 for (iterator I = begin(), E = end(); I != E; ++I) 163 if (AA.alias(MemoryLocation(Ptr, Size, AAInfo), 164 MemoryLocation(I.getPointer(), I.getSize(), I.getAAInfo()))) 165 return true; 166 167 // Check the unknown instructions... 168 if (!UnknownInsts.empty()) { 169 for (unsigned i = 0, e = UnknownInsts.size(); i != e; ++i) 170 if (AA.getModRefInfo(UnknownInsts[i], 171 MemoryLocation(Ptr, Size, AAInfo)) != MRI_NoModRef) 172 return true; 173 } 174 175 return false; 176 } 177 178 bool AliasSet::aliasesUnknownInst(const Instruction *Inst, 179 AliasAnalysis &AA) const { 180 if (!Inst->mayReadOrWriteMemory()) 181 return false; 182 183 for (unsigned i = 0, e = UnknownInsts.size(); i != e; ++i) { 184 ImmutableCallSite C1(getUnknownInst(i)), C2(Inst); 185 if (!C1 || !C2 || AA.getModRefInfo(C1, C2) != MRI_NoModRef || 186 AA.getModRefInfo(C2, C1) != MRI_NoModRef) 187 return true; 188 } 189 190 for (iterator I = begin(), E = end(); I != E; ++I) 191 if (AA.getModRefInfo(Inst, MemoryLocation(I.getPointer(), I.getSize(), 192 I.getAAInfo())) != MRI_NoModRef) 193 return true; 194 195 return false; 196 } 197 198 void AliasSetTracker::clear() { 199 // Delete all the PointerRec entries. 200 for (PointerMapType::iterator I = PointerMap.begin(), E = PointerMap.end(); 201 I != E; ++I) 202 I->second->eraseFromList(); 203 204 PointerMap.clear(); 205 206 // The alias sets should all be clear now. 207 AliasSets.clear(); 208 } 209 210 211 /// mergeAliasSetsForPointer - Given a pointer, merge all alias sets that may 212 /// alias the pointer. Return the unified set, or nullptr if no set that aliases 213 /// the pointer was found. 214 AliasSet *AliasSetTracker::mergeAliasSetsForPointer(const Value *Ptr, 215 uint64_t Size, 216 const AAMDNodes &AAInfo) { 217 AliasSet *FoundSet = nullptr; 218 for (iterator I = begin(), E = end(); I != E;) { 219 iterator Cur = I++; 220 if (Cur->Forward || !Cur->aliasesPointer(Ptr, Size, AAInfo, AA)) continue; 221 222 if (!FoundSet) { // If this is the first alias set ptr can go into. 223 FoundSet = &*Cur; // Remember it. 224 } else { // Otherwise, we must merge the sets. 225 FoundSet->mergeSetIn(*Cur, *this); // Merge in contents. 226 } 227 } 228 229 return FoundSet; 230 } 231 232 /// containsPointer - Return true if the specified location is represented by 233 /// this alias set, false otherwise. This does not modify the AST object or 234 /// alias sets. 235 bool AliasSetTracker::containsPointer(const Value *Ptr, uint64_t Size, 236 const AAMDNodes &AAInfo) const { 237 for (const_iterator I = begin(), E = end(); I != E; ++I) 238 if (!I->Forward && I->aliasesPointer(Ptr, Size, AAInfo, AA)) 239 return true; 240 return false; 241 } 242 243 bool AliasSetTracker::containsUnknown(const Instruction *Inst) const { 244 for (const_iterator I = begin(), E = end(); I != E; ++I) 245 if (!I->Forward && I->aliasesUnknownInst(Inst, AA)) 246 return true; 247 return false; 248 } 249 250 AliasSet *AliasSetTracker::findAliasSetForUnknownInst(Instruction *Inst) { 251 AliasSet *FoundSet = nullptr; 252 for (iterator I = begin(), E = end(); I != E;) { 253 iterator Cur = I++; 254 if (Cur->Forward || !Cur->aliasesUnknownInst(Inst, AA)) 255 continue; 256 if (!FoundSet) // If this is the first alias set ptr can go into. 257 FoundSet = &*Cur; // Remember it. 258 else if (!Cur->Forward) // Otherwise, we must merge the sets. 259 FoundSet->mergeSetIn(*Cur, *this); // Merge in contents. 260 } 261 return FoundSet; 262 } 263 264 265 266 267 /// getAliasSetForPointer - Return the alias set that the specified pointer 268 /// lives in. 269 AliasSet &AliasSetTracker::getAliasSetForPointer(Value *Pointer, uint64_t Size, 270 const AAMDNodes &AAInfo, 271 bool *New) { 272 AliasSet::PointerRec &Entry = getEntryFor(Pointer); 273 274 // Check to see if the pointer is already known. 275 if (Entry.hasAliasSet()) { 276 // If the size changed, we may need to merge several alias sets. 277 // Note that we can *not* return the result of mergeAliasSetsForPointer 278 // due to a quirk of alias analysis behavior. Since alias(undef, undef) 279 // is NoAlias, mergeAliasSetsForPointer(undef, ...) will not find the 280 // the right set for undef, even if it exists. 281 if (Entry.updateSizeAndAAInfo(Size, AAInfo)) 282 mergeAliasSetsForPointer(Pointer, Size, AAInfo); 283 // Return the set! 284 return *Entry.getAliasSet(*this)->getForwardedTarget(*this); 285 } 286 287 if (AliasSet *AS = mergeAliasSetsForPointer(Pointer, Size, AAInfo)) { 288 // Add it to the alias set it aliases. 289 AS->addPointer(*this, Entry, Size, AAInfo); 290 return *AS; 291 } 292 293 if (New) *New = true; 294 // Otherwise create a new alias set to hold the loaded pointer. 295 AliasSets.push_back(new AliasSet()); 296 AliasSets.back().addPointer(*this, Entry, Size, AAInfo); 297 return AliasSets.back(); 298 } 299 300 bool AliasSetTracker::add(Value *Ptr, uint64_t Size, const AAMDNodes &AAInfo) { 301 bool NewPtr; 302 addPointer(Ptr, Size, AAInfo, AliasSet::NoAccess, NewPtr); 303 return NewPtr; 304 } 305 306 307 bool AliasSetTracker::add(LoadInst *LI) { 308 if (isStrongerThanMonotonic(LI->getOrdering())) return addUnknown(LI); 309 310 AAMDNodes AAInfo; 311 LI->getAAMetadata(AAInfo); 312 313 AliasSet::AccessLattice Access = AliasSet::RefAccess; 314 bool NewPtr; 315 const DataLayout &DL = LI->getModule()->getDataLayout(); 316 AliasSet &AS = addPointer(LI->getOperand(0), 317 DL.getTypeStoreSize(LI->getType()), 318 AAInfo, Access, NewPtr); 319 if (LI->isVolatile()) AS.setVolatile(); 320 return NewPtr; 321 } 322 323 bool AliasSetTracker::add(StoreInst *SI) { 324 if (isStrongerThanMonotonic(SI->getOrdering())) return addUnknown(SI); 325 326 AAMDNodes AAInfo; 327 SI->getAAMetadata(AAInfo); 328 329 AliasSet::AccessLattice Access = AliasSet::ModAccess; 330 bool NewPtr; 331 const DataLayout &DL = SI->getModule()->getDataLayout(); 332 Value *Val = SI->getOperand(0); 333 AliasSet &AS = addPointer(SI->getOperand(1), 334 DL.getTypeStoreSize(Val->getType()), 335 AAInfo, Access, NewPtr); 336 if (SI->isVolatile()) AS.setVolatile(); 337 return NewPtr; 338 } 339 340 bool AliasSetTracker::add(VAArgInst *VAAI) { 341 AAMDNodes AAInfo; 342 VAAI->getAAMetadata(AAInfo); 343 344 bool NewPtr; 345 addPointer(VAAI->getOperand(0), MemoryLocation::UnknownSize, AAInfo, 346 AliasSet::ModRefAccess, NewPtr); 347 return NewPtr; 348 } 349 350 bool AliasSetTracker::add(MemSetInst *MSI) { 351 AAMDNodes AAInfo; 352 MSI->getAAMetadata(AAInfo); 353 354 bool NewPtr; 355 uint64_t Len; 356 357 if (ConstantInt *C = dyn_cast<ConstantInt>(MSI->getLength())) 358 Len = C->getZExtValue(); 359 else 360 Len = MemoryLocation::UnknownSize; 361 362 AliasSet &AS = 363 addPointer(MSI->getRawDest(), Len, AAInfo, AliasSet::ModAccess, NewPtr); 364 if (MSI->isVolatile()) 365 AS.setVolatile(); 366 return NewPtr; 367 } 368 369 bool AliasSetTracker::addUnknown(Instruction *Inst) { 370 if (isa<DbgInfoIntrinsic>(Inst)) 371 return true; // Ignore DbgInfo Intrinsics. 372 if (!Inst->mayReadOrWriteMemory()) 373 return true; // doesn't alias anything 374 375 AliasSet *AS = findAliasSetForUnknownInst(Inst); 376 if (AS) { 377 AS->addUnknownInst(Inst, AA); 378 return false; 379 } 380 AliasSets.push_back(new AliasSet()); 381 AS = &AliasSets.back(); 382 AS->addUnknownInst(Inst, AA); 383 return true; 384 } 385 386 bool AliasSetTracker::add(Instruction *I) { 387 // Dispatch to one of the other add methods. 388 if (LoadInst *LI = dyn_cast<LoadInst>(I)) 389 return add(LI); 390 if (StoreInst *SI = dyn_cast<StoreInst>(I)) 391 return add(SI); 392 if (VAArgInst *VAAI = dyn_cast<VAArgInst>(I)) 393 return add(VAAI); 394 if (MemSetInst *MSI = dyn_cast<MemSetInst>(I)) 395 return add(MSI); 396 return addUnknown(I); 397 // FIXME: add support of memcpy and memmove. 398 } 399 400 void AliasSetTracker::add(BasicBlock &BB) { 401 for (auto &I : BB) 402 add(&I); 403 } 404 405 void AliasSetTracker::add(const AliasSetTracker &AST) { 406 assert(&AA == &AST.AA && 407 "Merging AliasSetTracker objects with different Alias Analyses!"); 408 409 // Loop over all of the alias sets in AST, adding the pointers contained 410 // therein into the current alias sets. This can cause alias sets to be 411 // merged together in the current AST. 412 for (const_iterator I = AST.begin(), E = AST.end(); I != E; ++I) { 413 if (I->Forward) continue; // Ignore forwarding alias sets 414 415 AliasSet &AS = const_cast<AliasSet&>(*I); 416 417 // If there are any call sites in the alias set, add them to this AST. 418 for (unsigned i = 0, e = AS.UnknownInsts.size(); i != e; ++i) 419 add(AS.UnknownInsts[i]); 420 421 // Loop over all of the pointers in this alias set. 422 bool X; 423 for (AliasSet::iterator ASI = AS.begin(), E = AS.end(); ASI != E; ++ASI) { 424 AliasSet &NewAS = addPointer(ASI.getPointer(), ASI.getSize(), 425 ASI.getAAInfo(), 426 (AliasSet::AccessLattice)AS.Access, X); 427 if (AS.isVolatile()) NewAS.setVolatile(); 428 } 429 } 430 } 431 432 /// remove - Remove the specified (potentially non-empty) alias set from the 433 /// tracker. 434 void AliasSetTracker::remove(AliasSet &AS) { 435 // Drop all call sites. 436 if (!AS.UnknownInsts.empty()) 437 AS.dropRef(*this); 438 AS.UnknownInsts.clear(); 439 440 // Clear the alias set. 441 unsigned NumRefs = 0; 442 while (!AS.empty()) { 443 AliasSet::PointerRec *P = AS.PtrList; 444 445 Value *ValToRemove = P->getValue(); 446 447 // Unlink and delete entry from the list of values. 448 P->eraseFromList(); 449 450 // Remember how many references need to be dropped. 451 ++NumRefs; 452 453 // Finally, remove the entry. 454 PointerMap.erase(ValToRemove); 455 } 456 457 // Stop using the alias set, removing it. 458 AS.RefCount -= NumRefs; 459 if (AS.RefCount == 0) 460 AS.removeFromTracker(*this); 461 } 462 463 bool 464 AliasSetTracker::remove(Value *Ptr, uint64_t Size, const AAMDNodes &AAInfo) { 465 AliasSet *AS = mergeAliasSetsForPointer(Ptr, Size, AAInfo); 466 if (!AS) return false; 467 remove(*AS); 468 return true; 469 } 470 471 bool AliasSetTracker::remove(LoadInst *LI) { 472 const DataLayout &DL = LI->getModule()->getDataLayout(); 473 uint64_t Size = DL.getTypeStoreSize(LI->getType()); 474 475 AAMDNodes AAInfo; 476 LI->getAAMetadata(AAInfo); 477 478 AliasSet *AS = mergeAliasSetsForPointer(LI->getOperand(0), Size, AAInfo); 479 if (!AS) return false; 480 remove(*AS); 481 return true; 482 } 483 484 bool AliasSetTracker::remove(StoreInst *SI) { 485 const DataLayout &DL = SI->getModule()->getDataLayout(); 486 uint64_t Size = DL.getTypeStoreSize(SI->getOperand(0)->getType()); 487 488 AAMDNodes AAInfo; 489 SI->getAAMetadata(AAInfo); 490 491 AliasSet *AS = mergeAliasSetsForPointer(SI->getOperand(1), Size, AAInfo); 492 if (!AS) return false; 493 remove(*AS); 494 return true; 495 } 496 497 bool AliasSetTracker::remove(VAArgInst *VAAI) { 498 AAMDNodes AAInfo; 499 VAAI->getAAMetadata(AAInfo); 500 501 AliasSet *AS = mergeAliasSetsForPointer(VAAI->getOperand(0), 502 MemoryLocation::UnknownSize, AAInfo); 503 if (!AS) return false; 504 remove(*AS); 505 return true; 506 } 507 508 bool AliasSetTracker::remove(MemSetInst *MSI) { 509 AAMDNodes AAInfo; 510 MSI->getAAMetadata(AAInfo); 511 uint64_t Len; 512 513 if (ConstantInt *C = dyn_cast<ConstantInt>(MSI->getLength())) 514 Len = C->getZExtValue(); 515 else 516 Len = MemoryLocation::UnknownSize; 517 518 AliasSet *AS = mergeAliasSetsForPointer(MSI->getRawDest(), Len, AAInfo); 519 if (!AS) 520 return false; 521 remove(*AS); 522 return true; 523 } 524 525 bool AliasSetTracker::removeUnknown(Instruction *I) { 526 if (!I->mayReadOrWriteMemory()) 527 return false; // doesn't alias anything 528 529 AliasSet *AS = findAliasSetForUnknownInst(I); 530 if (!AS) return false; 531 remove(*AS); 532 return true; 533 } 534 535 bool AliasSetTracker::remove(Instruction *I) { 536 // Dispatch to one of the other remove methods... 537 if (LoadInst *LI = dyn_cast<LoadInst>(I)) 538 return remove(LI); 539 if (StoreInst *SI = dyn_cast<StoreInst>(I)) 540 return remove(SI); 541 if (VAArgInst *VAAI = dyn_cast<VAArgInst>(I)) 542 return remove(VAAI); 543 if (MemSetInst *MSI = dyn_cast<MemSetInst>(I)) 544 return remove(MSI); 545 return removeUnknown(I); 546 // FIXME: add support of memcpy and memmove. 547 } 548 549 550 // deleteValue method - This method is used to remove a pointer value from the 551 // AliasSetTracker entirely. It should be used when an instruction is deleted 552 // from the program to update the AST. If you don't use this, you would have 553 // dangling pointers to deleted instructions. 554 // 555 void AliasSetTracker::deleteValue(Value *PtrVal) { 556 // If this is a call instruction, remove the callsite from the appropriate 557 // AliasSet (if present). 558 if (Instruction *Inst = dyn_cast<Instruction>(PtrVal)) { 559 if (Inst->mayReadOrWriteMemory()) { 560 // Scan all the alias sets to see if this call site is contained. 561 for (iterator I = begin(), E = end(); I != E;) { 562 iterator Cur = I++; 563 if (!Cur->Forward) 564 Cur->removeUnknownInst(*this, Inst); 565 } 566 } 567 } 568 569 // First, look up the PointerRec for this pointer. 570 PointerMapType::iterator I = PointerMap.find_as(PtrVal); 571 if (I == PointerMap.end()) return; // Noop 572 573 // If we found one, remove the pointer from the alias set it is in. 574 AliasSet::PointerRec *PtrValEnt = I->second; 575 AliasSet *AS = PtrValEnt->getAliasSet(*this); 576 577 // Unlink and delete from the list of values. 578 PtrValEnt->eraseFromList(); 579 580 // Stop using the alias set. 581 AS->dropRef(*this); 582 583 PointerMap.erase(I); 584 } 585 586 // copyValue - This method should be used whenever a preexisting value in the 587 // program is copied or cloned, introducing a new value. Note that it is ok for 588 // clients that use this method to introduce the same value multiple times: if 589 // the tracker already knows about a value, it will ignore the request. 590 // 591 void AliasSetTracker::copyValue(Value *From, Value *To) { 592 // First, look up the PointerRec for this pointer. 593 PointerMapType::iterator I = PointerMap.find_as(From); 594 if (I == PointerMap.end()) 595 return; // Noop 596 assert(I->second->hasAliasSet() && "Dead entry?"); 597 598 AliasSet::PointerRec &Entry = getEntryFor(To); 599 if (Entry.hasAliasSet()) return; // Already in the tracker! 600 601 // Add it to the alias set it aliases... 602 I = PointerMap.find_as(From); 603 AliasSet *AS = I->second->getAliasSet(*this); 604 AS->addPointer(*this, Entry, I->second->getSize(), 605 I->second->getAAInfo(), 606 true); 607 } 608 609 610 611 //===----------------------------------------------------------------------===// 612 // AliasSet/AliasSetTracker Printing Support 613 //===----------------------------------------------------------------------===// 614 615 void AliasSet::print(raw_ostream &OS) const { 616 OS << " AliasSet[" << (const void*)this << ", " << RefCount << "] "; 617 OS << (Alias == SetMustAlias ? "must" : "may") << " alias, "; 618 switch (Access) { 619 case NoAccess: OS << "No access "; break; 620 case RefAccess: OS << "Ref "; break; 621 case ModAccess: OS << "Mod "; break; 622 case ModRefAccess: OS << "Mod/Ref "; break; 623 default: llvm_unreachable("Bad value for Access!"); 624 } 625 if (isVolatile()) OS << "[volatile] "; 626 if (Forward) 627 OS << " forwarding to " << (void*)Forward; 628 629 630 if (!empty()) { 631 OS << "Pointers: "; 632 for (iterator I = begin(), E = end(); I != E; ++I) { 633 if (I != begin()) OS << ", "; 634 I.getPointer()->printAsOperand(OS << "("); 635 OS << ", " << I.getSize() << ")"; 636 } 637 } 638 if (!UnknownInsts.empty()) { 639 OS << "\n " << UnknownInsts.size() << " Unknown instructions: "; 640 for (unsigned i = 0, e = UnknownInsts.size(); i != e; ++i) { 641 if (i) OS << ", "; 642 UnknownInsts[i]->printAsOperand(OS); 643 } 644 } 645 OS << "\n"; 646 } 647 648 void AliasSetTracker::print(raw_ostream &OS) const { 649 OS << "Alias Set Tracker: " << AliasSets.size() << " alias sets for " 650 << PointerMap.size() << " pointer values.\n"; 651 for (const_iterator I = begin(), E = end(); I != E; ++I) 652 I->print(OS); 653 OS << "\n"; 654 } 655 656 #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) 657 LLVM_DUMP_METHOD void AliasSet::dump() const { print(dbgs()); } 658 LLVM_DUMP_METHOD void AliasSetTracker::dump() const { print(dbgs()); } 659 #endif 660 661 //===----------------------------------------------------------------------===// 662 // ASTCallbackVH Class Implementation 663 //===----------------------------------------------------------------------===// 664 665 void AliasSetTracker::ASTCallbackVH::deleted() { 666 assert(AST && "ASTCallbackVH called with a null AliasSetTracker!"); 667 AST->deleteValue(getValPtr()); 668 // this now dangles! 669 } 670 671 void AliasSetTracker::ASTCallbackVH::allUsesReplacedWith(Value *V) { 672 AST->copyValue(getValPtr(), V); 673 } 674 675 AliasSetTracker::ASTCallbackVH::ASTCallbackVH(Value *V, AliasSetTracker *ast) 676 : CallbackVH(V), AST(ast) {} 677 678 AliasSetTracker::ASTCallbackVH & 679 AliasSetTracker::ASTCallbackVH::operator=(Value *V) { 680 return *this = ASTCallbackVH(V, AST); 681 } 682 683 //===----------------------------------------------------------------------===// 684 // AliasSetPrinter Pass 685 //===----------------------------------------------------------------------===// 686 687 namespace { 688 class AliasSetPrinter : public FunctionPass { 689 AliasSetTracker *Tracker; 690 public: 691 static char ID; // Pass identification, replacement for typeid 692 AliasSetPrinter() : FunctionPass(ID) { 693 initializeAliasSetPrinterPass(*PassRegistry::getPassRegistry()); 694 } 695 696 void getAnalysisUsage(AnalysisUsage &AU) const override { 697 AU.setPreservesAll(); 698 AU.addRequired<AAResultsWrapperPass>(); 699 } 700 701 bool runOnFunction(Function &F) override { 702 auto &AAWP = getAnalysis<AAResultsWrapperPass>(); 703 Tracker = new AliasSetTracker(AAWP.getAAResults()); 704 705 for (inst_iterator I = inst_begin(F), E = inst_end(F); I != E; ++I) 706 Tracker->add(&*I); 707 Tracker->print(errs()); 708 delete Tracker; 709 return false; 710 } 711 }; 712 } 713 714 char AliasSetPrinter::ID = 0; 715 INITIALIZE_PASS_BEGIN(AliasSetPrinter, "print-alias-sets", 716 "Alias Set Printer", false, true) 717 INITIALIZE_PASS_DEPENDENCY(AAResultsWrapperPass) 718 INITIALIZE_PASS_END(AliasSetPrinter, "print-alias-sets", 719 "Alias Set Printer", false, true) 720