Bug 1531798 - Avoid deadlock when dumping a profile while the IOInterposer is active, r=gerald,mstange.
authorFlorian Quèze <florian@queze.net>
Tue, 05 Mar 2019 12:01:33 +0000
changeset 520241 ae40216d31b37aa4a597d3e5c52f31c73bce746b
parent 520240 9b7d9eccb34e0593c0b13e163469c37d396ccaee
child 520242 c0ef24484dfeb9e9c8b66e66c804a3f0922869ba
push id10862
push userffxbld-merge
push dateMon, 11 Mar 2019 13:01:11 +0000
treeherdermozilla-beta@a2e7f5c935da [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersgerald, mstange
bugs1531798
milestone67.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1531798 - Avoid deadlock when dumping a profile while the IOInterposer is active, r=gerald,mstange. Differential Revision: https://phabricator.services.mozilla.com/D21712
tools/profiler/core/platform.cpp
--- a/tools/profiler/core/platform.cpp
+++ b/tools/profiler/core/platform.cpp
@@ -772,23 +772,43 @@ class ActivePS {
           MOZ_RELEASE_ASSERT(bufferPosition,
                              "should have unregistered this page");
           return *bufferPosition < bufferRangeStart;
         });
   }
 
 #if !defined(RELEASE_OR_BETA)
   static void UnregisterIOInterposer(PSLockRef) {
-    if (!sInstance->mInterposeObserver) return;
+    if (!sInstance->mInterposeObserver) {
+      return;
+    }
 
     IOInterposer::Unregister(IOInterposeObserver::OpAll,
                              sInstance->mInterposeObserver);
 
     sInstance->mInterposeObserver = nullptr;
   }
+
+  static void PauseIOInterposer(PSLockRef) {
+    if (!sInstance->mInterposeObserver) {
+      return;
+    }
+
+    IOInterposer::Unregister(IOInterposeObserver::OpAll,
+                             sInstance->mInterposeObserver);
+  }
+
+  static void ResumeIOInterposer(PSLockRef) {
+    if (!sInstance->mInterposeObserver) {
+      return;
+    }
+
+    IOInterposer::Register(IOInterposeObserver::OpAll,
+                           sInstance->mInterposeObserver);
+  }
 #endif
 
   static void ClearExpiredExitProfiles(PSLockRef) {
     uint64_t bufferRangeStart = sInstance->mBuffer->mRangeStart;
     // Discard exit profiles that were gathered before our buffer RangeStart.
     sInstance->mExitProfiles.RemoveElementsBy(
         [bufferRangeStart](const ExitProfile& aExitProfile) {
           return aExitProfile.mBufferPositionAtGatherTime < bufferRangeStart;
@@ -2087,18 +2107,25 @@ bool profiler_stream_json_for_this_proce
   MOZ_RELEASE_ASSERT(CorePS::Exists());
 
   PSAutoLock lock(gPSMutex);
 
   if (!ActivePS::Exists(lock)) {
     return false;
   }
 
+#if !defined(RELEASE_OR_BETA)
+  ActivePS::PauseIOInterposer(lock);
+#endif
+
   locked_profiler_stream_json_for_this_process(lock, aWriter, aSinceTime,
                                                aIsShuttingDown);
+#if !defined(RELEASE_OR_BETA)
+  ActivePS::ResumeIOInterposer(lock);
+#endif
 
   return true;
 }
 
 // END saving/streaming code
 ////////////////////////////////////////////////////////////////////////
 
 static void PrintUsageThenExit(int aExitCode) {