AliasAnalysisCounter.cpp revision 1bc76d48d476446f226f06f0aced7efb268f2536
170e332d34b795f1645953c35747e345f88b8688bChris Lattner//===- AliasAnalysisCounter.cpp - Alias Analysis Query Counter ------------===//
22b37d7cf28b1382420b5e4007042feeb66d21ac8Misha Brukman//
3b576c94c15af9a440f69d9d03c2afead7971118cJohn Criswell//                     The LLVM Compiler Infrastructure
4b576c94c15af9a440f69d9d03c2afead7971118cJohn Criswell//
54ee451de366474b9c228b4e5fa573795a715216dChris Lattner// This file is distributed under the University of Illinois Open Source
64ee451de366474b9c228b4e5fa573795a715216dChris Lattner// License. See LICENSE.TXT for details.
72b37d7cf28b1382420b5e4007042feeb66d21ac8Misha Brukman//
8b576c94c15af9a440f69d9d03c2afead7971118cJohn Criswell//===----------------------------------------------------------------------===//
970e332d34b795f1645953c35747e345f88b8688bChris Lattner//
1070e332d34b795f1645953c35747e345f88b8688bChris Lattner// This file implements a pass which can be used to count how many alias queries
1170e332d34b795f1645953c35747e345f88b8688bChris Lattner// are being made and how the alias analysis implementation being used responds.
1270e332d34b795f1645953c35747e345f88b8688bChris Lattner//
1370e332d34b795f1645953c35747e345f88b8688bChris Lattner//===----------------------------------------------------------------------===//
1470e332d34b795f1645953c35747e345f88b8688bChris Lattner
15534927d82de6d1be0f6e939263eeb309ad135661Jeff Cohen#include "llvm/Analysis/Passes.h"
1670e332d34b795f1645953c35747e345f88b8688bChris Lattner#include "llvm/Pass.h"
17cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner#include "llvm/Analysis/AliasAnalysis.h"
18cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner#include "llvm/Assembly/Writer.h"
19cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner#include "llvm/Support/CommandLine.h"
2020638dc948b0d81d6c9bf70dde0137d7d43b02ddDavid Greene#include "llvm/Support/Debug.h"
21c25e7581b9b8088910da31702d4ca21c4734c6d7Torok Edwin#include "llvm/Support/ErrorHandling.h"
22bdff548e4dd577a72094d57b282de4e765643b96Chris Lattner#include "llvm/Support/raw_ostream.h"
23381bf79ae17a77fedb902b87aea7e55be9b793aaChris Lattnerusing namespace llvm;
24d0fde30ce850b78371fd1386338350591f9ff494Brian Gaeke
25844731a7f1909f55935e3514c9e713a62d67662eDan Gohmanstatic cl::opt<bool>
260819cfb1e6333cc8554e567ae0c885c11821eec6Chris LattnerPrintAll("count-aa-print-all-queries", cl::ReallyHidden, cl::init(true));
27844731a7f1909f55935e3514c9e713a62d67662eDan Gohmanstatic cl::opt<bool>
28844731a7f1909f55935e3514c9e713a62d67662eDan GohmanPrintAllFailures("count-aa-print-all-failed-queries", cl::ReallyHidden);
29cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner
30844731a7f1909f55935e3514c9e713a62d67662eDan Gohmannamespace {
316726b6d75a8b679068a58cb954ba97cf9d1690baNick Lewycky  class AliasAnalysisCounter : public ModulePass, public AliasAnalysis {
32a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner    unsigned No, May, Must;
33d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner    unsigned NoMR, JustRef, JustMod, MR;
34a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner    const char *Name;
35cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner    Module *M;
36a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner  public:
371997473cf72957d0e70322e2fe6fe2ab141c58a6Devang Patel    static char ID; // Class identification, replacement for typeinfo
38ae73dc1448d25b02cabc7c64c86c64371453dda8Dan Gohman    AliasAnalysisCounter() : ModulePass(&ID) {
39d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner      No = May = Must = 0;
40d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner      NoMR = JustRef = JustMod = MR = 0;
41d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner    }
42d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner
43d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner    void printLine(const char *Desc, unsigned Val, unsigned Sum) {
444850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene      errs() <<  "  " << Val << " " << Desc << " responses ("
45791102fb1192ac9483274e54cbc42480c9b1af10Chris Lattner             << Val*100/Sum << "%)\n";
46d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner    }
47a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner    ~AliasAnalysisCounter() {
48d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner      unsigned AASum = No+May+Must;
49d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner      unsigned MRSum = NoMR+JustRef+JustMod+MR;
50d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner      if (AASum + MRSum) { // Print a report if any counted queries occurred...
514850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene        errs() << "\n===== Alias Analysis Counter Report =====\n"
52791102fb1192ac9483274e54cbc42480c9b1af10Chris Lattner               << "  Analysis counted: " << Name << "\n"
53791102fb1192ac9483274e54cbc42480c9b1af10Chris Lattner               << "  " << AASum << " Total Alias Queries Performed\n";
54efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner        if (AASum) {
55efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner          printLine("no alias",     No, AASum);
56efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner          printLine("may alias",   May, AASum);
57efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner          printLine("must alias", Must, AASum);
584850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene          errs() << "  Alias Analysis Counter Summary: " << No*100/AASum << "%/"
59791102fb1192ac9483274e54cbc42480c9b1af10Chris Lattner                 << May*100/AASum << "%/" << Must*100/AASum<<"%\n\n";
60efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner        }
61d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner
624850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene        errs() << "  " << MRSum    << " Total Mod/Ref Queries Performed\n";
63efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner        if (MRSum) {
64efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner          printLine("no mod/ref",    NoMR, MRSum);
65efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner          printLine("ref",        JustRef, MRSum);
66efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner          printLine("mod",        JustMod, MRSum);
67efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner          printLine("mod/ref",         MR, MRSum);
684850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene          errs() << "  Mod/Ref Analysis Counter Summary: " <<NoMR*100/MRSum
69791102fb1192ac9483274e54cbc42480c9b1af10Chris Lattner                 << "%/" << JustRef*100/MRSum << "%/" << JustMod*100/MRSum
70791102fb1192ac9483274e54cbc42480c9b1af10Chris Lattner                 << "%/" << MR*100/MRSum <<"%\n\n";
71efa095e41830bdbbc4eb0c4ff423fe483f2de0e2Chris Lattner        }
72a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner      }
73a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner    }
74a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner
75b12914bfc0f76a7a48357162d5f4c39a1343e69bChris Lattner    bool runOnModule(Module &M) {
76cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner      this->M = &M;
77d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner      InitializeAliasAnalysis(this);
78a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner      Name = dynamic_cast<Pass*>(&getAnalysis<AliasAnalysis>())->getPassName();
79a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner      return false;
80a89feb55e04fd4f25d7c09fb0c119fc9250b5b5aChris Lattner    }
8170e332d34b795f1645953c35747e345f88b8688bChris Lattner
8270e332d34b795f1645953c35747e345f88b8688bChris Lattner    virtual void getAnalysisUsage(AnalysisUsage &AU) const {
83d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner      AliasAnalysis::getAnalysisUsage(AU);
8470e332d34b795f1645953c35747e345f88b8688bChris Lattner      AU.addRequired<AliasAnalysis>();
8570e332d34b795f1645953c35747e345f88b8688bChris Lattner      AU.setPreservesAll();
8670e332d34b795f1645953c35747e345f88b8688bChris Lattner    }
8770e332d34b795f1645953c35747e345f88b8688bChris Lattner
881bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner    /// getAdjustedAnalysisPointer - This method is used when a pass implements
891bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner    /// an analysis interface through multiple inheritance.  If needed, it
901bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner    /// should override this to adjust the this pointer as needed for the
911bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner    /// specified pass info.
921bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner    virtual void *getAdjustedAnalysisPointer(const PassInfo *PI) {
931bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner      if (PI->isPassID(&AliasAnalysis::ID))
941bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner        return (AliasAnalysis*)this;
951bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner      return this;
961bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner    }
971bc76d48d476446f226f06f0aced7efb268f2536Chris Lattner
98b79d79297d7115e89776155c92eeb5e7ba518a01Chris Lattner    // FIXME: We could count these too...
99b79d79297d7115e89776155c92eeb5e7ba518a01Chris Lattner    bool pointsToConstantMemory(const Value *P) {
100b79d79297d7115e89776155c92eeb5e7ba518a01Chris Lattner      return getAnalysis<AliasAnalysis>().pointsToConstantMemory(P);
101b79d79297d7115e89776155c92eeb5e7ba518a01Chris Lattner    }
1022b37d7cf28b1382420b5e4007042feeb66d21ac8Misha Brukman
10370e332d34b795f1645953c35747e345f88b8688bChris Lattner    // Forwarding functions: just delegate to a real AA implementation, counting
10470e332d34b795f1645953c35747e345f88b8688bChris Lattner    // the number of responses...
105d80651df46b397fba19a89bf9e074dffaacbfa8bChris Lattner    AliasResult alias(const Value *V1, unsigned V1Size,
106cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner                      const Value *V2, unsigned V2Size);
107cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner
108cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner    ModRefResult getModRefInfo(CallSite CS, Value *P, unsigned Size);
1094a7ebfa4111305ea22fc753d4f029eed88149662Reid Spencer    ModRefResult getModRefInfo(CallSite CS1, CallSite CS2) {
1104a7ebfa4111305ea22fc753d4f029eed88149662Reid Spencer      return AliasAnalysis::getModRefInfo(CS1,CS2);
1114a7ebfa4111305ea22fc753d4f029eed88149662Reid Spencer    }
11270e332d34b795f1645953c35747e345f88b8688bChris Lattner  };
11370e332d34b795f1645953c35747e345f88b8688bChris Lattner}
114534927d82de6d1be0f6e939263eeb309ad135661Jeff Cohen
115844731a7f1909f55935e3514c9e713a62d67662eDan Gohmanchar AliasAnalysisCounter::ID = 0;
116844731a7f1909f55935e3514c9e713a62d67662eDan Gohmanstatic RegisterPass<AliasAnalysisCounter>
117844731a7f1909f55935e3514c9e713a62d67662eDan GohmanX("count-aa", "Count Alias Analysis Query Responses", false, true);
118844731a7f1909f55935e3514c9e713a62d67662eDan Gohmanstatic RegisterAnalysisGroup<AliasAnalysis> Y(X);
119844731a7f1909f55935e3514c9e713a62d67662eDan Gohman
120534927d82de6d1be0f6e939263eeb309ad135661Jeff CohenModulePass *llvm::createAliasAnalysisCounterPass() {
121534927d82de6d1be0f6e939263eeb309ad135661Jeff Cohen  return new AliasAnalysisCounter();
122534927d82de6d1be0f6e939263eeb309ad135661Jeff Cohen}
123cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner
1242b37d7cf28b1382420b5e4007042feeb66d21ac8Misha BrukmanAliasAnalysis::AliasResult
125cf9f20189f55d4036df598c88371e13512b075b2Chris LattnerAliasAnalysisCounter::alias(const Value *V1, unsigned V1Size,
126cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner                            const Value *V2, unsigned V2Size) {
127cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  AliasResult R = getAnalysis<AliasAnalysis>().alias(V1, V1Size, V2, V2Size);
1282b37d7cf28b1382420b5e4007042feeb66d21ac8Misha Brukman
129cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  const char *AliasString;
130cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  switch (R) {
131c23197a26f34f559ea9797de51e187087c039c42Torok Edwin  default: llvm_unreachable("Unknown alias type!");
132cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  case NoAlias:   No++;   AliasString = "No alias"; break;
133cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  case MayAlias:  May++;  AliasString = "May alias"; break;
134cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  case MustAlias: Must++; AliasString = "Must alias"; break;
135cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  }
136cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner
137cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  if (PrintAll || (PrintAllFailures && R == MayAlias)) {
1384850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    errs() << AliasString << ":\t";
1394850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    errs() << "[" << V1Size << "B] ";
1404850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    WriteAsOperand(errs(), V1, true, M);
1414850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    errs() << ", ";
1424850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    errs() << "[" << V2Size << "B] ";
1434850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    WriteAsOperand(errs(), V2, true, M);
1444850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    errs() << "\n";
145cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  }
146cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner
147cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  return R;
148cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner}
149cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner
1502b37d7cf28b1382420b5e4007042feeb66d21ac8Misha BrukmanAliasAnalysis::ModRefResult
151cf9f20189f55d4036df598c88371e13512b075b2Chris LattnerAliasAnalysisCounter::getModRefInfo(CallSite CS, Value *P, unsigned Size) {
152cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  ModRefResult R = getAnalysis<AliasAnalysis>().getModRefInfo(CS, P, Size);
153cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner
154cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  const char *MRString;
155cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  switch (R) {
156c23197a26f34f559ea9797de51e187087c039c42Torok Edwin  default:       llvm_unreachable("Unknown mod/ref type!");
157cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  case NoModRef: NoMR++;     MRString = "NoModRef"; break;
158cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  case Ref:      JustRef++;  MRString = "JustRef"; break;
159cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  case Mod:      JustMod++;  MRString = "JustMod"; break;
160cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  case ModRef:   MR++;       MRString = "ModRef"; break;
161cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  }
162cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner
163cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  if (PrintAll || (PrintAllFailures && R == ModRef)) {
1644850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    errs() << MRString << ":  Ptr: ";
1654850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    errs() << "[" << Size << "B] ";
1664850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    WriteAsOperand(errs(), P, true, M);
1674850a89b77e7dc677c2b73508f2a4c10386c844fDavid Greene    errs() << "\t<->" << *CS.getInstruction();
168cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  }
169cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner  return R;
170cf9f20189f55d4036df598c88371e13512b075b2Chris Lattner}
171