[ASAN] Add doFinalization to reset state
authorKeno Fischer <kfischer@college.harvard.edu>
Sat, 5 Dec 2015 14:42:34 +0000 (14:42 +0000)
committerKeno Fischer <kfischer@college.harvard.edu>
Sat, 5 Dec 2015 14:42:34 +0000 (14:42 +0000)
Summary: If the same pass manager is used for multiple modules ASAN
complains about GlobalsMD being initialized twice. Fix this by
resetting GlobalsMD in a new doFinalization method to allow this
use case.

Reviewers: kcc

Subscribers: llvm-commits

Differential Revision: http://reviews.llvm.org/D14962

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@254851 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Transforms/Instrumentation/AddressSanitizer.cpp
test/Instrumentation/AddressSanitizer/twice.ll [new file with mode: 0644]

index dea94a5..a9df5e5 100644 (file)
@@ -280,6 +280,11 @@ class GlobalsMetadata {
 
   GlobalsMetadata() : inited_(false) {}
 
+  void reset() {
+    inited_ = false;
+    Entries.clear();
+  }
+
   void init(Module &M) {
     assert(!inited_);
     inited_ = true;
@@ -450,6 +455,7 @@ struct AddressSanitizer : public FunctionPass {
   bool maybeInsertAsanInitAtFunctionEntry(Function &F);
   void markEscapedLocalAllocas(Function &F);
   bool doInitialization(Module &M) override;
+  bool doFinalization(Module &M) override;
   static char ID;  // Pass identification, replacement for typeid
 
   DominatorTree &getDominatorTree() const { return *DT; }
@@ -1521,6 +1527,11 @@ bool AddressSanitizer::doInitialization(Module &M) {
   return true;
 }
 
+bool AddressSanitizer::doFinalization(Module &M) {
+  GlobalsMD.reset();
+  return false;
+}
+
 bool AddressSanitizer::maybeInsertAsanInitAtFunctionEntry(Function &F) {
   // For each NSObject descendant having a +load method, this method is invoked
   // by the ObjC runtime before any of the static constructors is called.
diff --git a/test/Instrumentation/AddressSanitizer/twice.ll b/test/Instrumentation/AddressSanitizer/twice.ll
new file mode 100644 (file)
index 0000000..9f7826f
--- /dev/null
@@ -0,0 +1,8 @@
+; Check that the address sanitizer pass can be reused
+; RUN: opt < %s -S -run-twice -asan
+
+define void @foo(i64* %b) nounwind uwtable sanitize_address {
+  entry:
+  store i64 0, i64* %b, align 1
+  ret void
+}