Computer Laboratory

tesla::FieldReferenceInstrumenter Class Reference

Detailed Description

Converts calls to TESLA pseudo-assertions into instrumentation sites.

Definition at line 52 of file FieldReference.h.

#include "FieldReference.h"

+ Inheritance diagram for tesla::FieldReferenceInstrumenter:
+ Collaboration diagram for tesla::FieldReferenceInstrumenter:

Public Member Functions

 FieldReferenceInstrumenter (const Manifest &M, bool SuppressDI)
 
const char * getPassName () const
 
 ~FieldReferenceInstrumenter ()
 
virtual bool runOnModule (llvm::Module &M)
 
- Public Member Functions inherited from tesla::Instrumenter
 Instrumenter (const Manifest &M, bool SuppressDI)
 
virtual ~Instrumenter ()
 

Static Public Attributes

static char ID = 0
 

Additional Inherited Members

- Protected Attributes inherited from tesla::Instrumenter
const ManifestM
 TESLA manifest that describes automata. More...
 
const bool SuppressDebugInstr
 Don't produce debug instrumentation (e.g., printf() statements). More...
 

Constructor & Destructor Documentation

tesla::FieldReferenceInstrumenter::FieldReferenceInstrumenter ( const Manifest M,
bool  SuppressDI 
)
inline

Definition at line 56 of file FieldReference.h.

57  : Instrumenter(M, SuppressDI), ModulePass(ID) {}
tesla::FieldReferenceInstrumenter::~FieldReferenceInstrumenter ( )

Definition at line 91 of file FieldReference.cpp.

91  {
92  for (auto& i : Instrumentation)
93  delete i.second;
94 }

Member Function Documentation

const char* tesla::FieldReferenceInstrumenter::getPassName ( ) const
inline

Definition at line 58 of file FieldReference.h.

58 { return "field reference instrumenter"; }
bool tesla::FieldReferenceInstrumenter::runOnModule ( llvm::Module &  M)
virtual

Definition at line 97 of file FieldReference.cpp.

References tesla::Cast(), tesla::FieldAnnotation::completeFieldName(), tesla::debug, tesla::LLVM_PTR_ANNOTATION, and tesla::panic().

97  {
98  debug
99  << "===================================================================\n"
100  << __PRETTY_FUNCTION__ << "\n"
101  << "-------------------------------------------------------------------\n"
102  << "module: " << Mod.getModuleIdentifier() << "\n";
103 
104  this->Mod = &Mod;
105 
106  //
107  // First, find all struct fields that we want to instrument.
108  //
109  for (auto *Root : M.RootAutomata())
110  BuildInstrumentation(*M.FindAutomaton(Root->identifier()));
111 
112  debug << "instrumentation:\n";
113  for (auto& i : Instrumentation) {
114  debug << " " << i.getKey() << " -> ";
115  i.getValue()->getTarget()->getType()->print(debug);
116  debug << "\n";
117  }
118 
119  debug
120  << "-------------------------------------------------------------------\n"
121  << "looking for field references...\n"
122  ;
123 
124  //
125  // Then, iterate through all uses of the LLVM pointer annotation and look
126  // for structure accesses.
127  //
128  std::map<LoadInst*,FieldInstrumentation*> Loads;
129  std::map<StoreInst*,FieldInstrumentation*> Stores;
130 
131  //
132  // Look through all of the functions that start with llvm.ptr.annotation.
133  //
134  for (Function& Fn : Mod.getFunctionList()) {
135  if (!Fn.getName().startswith(LLVM_PTR_ANNOTATION))
136  continue;
137 
138  for (auto i = Fn.use_begin(); i != Fn.use_end(); i++) {
139  // We should be able to do some parsing of all annotations.
140  OwningPtr<PtrAnnotation> A(PtrAnnotation::Interpret(*i));
141  assert(A);
142 
143  // We only care about struct field annotations; ignore everything else.
144  auto *Annotation = dyn_cast<FieldAnnotation>(A.get());
145  if (!Annotation)
146  continue;
147 
148  // Not every struct field will have instrumentation defined for it.
149  auto Name = Annotation->completeFieldName();
150  auto *Instr = Instrumentation[Name];
151  if (Instr == NULL)
152  continue;
153 
154  for (User *U : *Annotation) {
155  auto *Cast = dyn_cast<CastInst>(U);
156  if (!Cast) {
157  U->dump();
158  panic("annotation user not a bitcast", false);
159  }
160 
161  for (auto k = Cast->use_begin(); k != Cast->use_end(); k++) {
162  if (auto *Load = dyn_cast<LoadInst>(*k))
163  Loads.insert(std::make_pair(Load, Instr));
164 
165  else if (auto *Store = dyn_cast<StoreInst>(*k))
166  Stores.insert(std::make_pair(Store, Instr));
167 
168  else {
169  k->dump();
170  panic("expected load or store with annotated value", false);
171  }
172  }
173  }
174  }
175  }
176 
177  for (auto i : Loads)
178  InstrumentLoad(i.first, i.second);
179 
180  for (auto i : Stores)
181  InstrumentStore(i.first, i.second);
182 
183  return true;
184 }

+ Here is the call graph for this function:

Member Data Documentation

char tesla::FieldReferenceInstrumenter::ID = 0
static

Definition at line 55 of file FieldReference.h.


The documentation for this class was generated from the following files: