Bug 1415762 - Cancel VRListener task when CompositorVsyncScheduler is going to destroy; r?dvander draft
authorDaosheng Mu <daoshengmu@gmail.com>
Mon, 13 Nov 2017 11:33:33 +0800
changeset 701154 5fe63db9404945de69749baa9cfaa5ecbade1109
parent 700338 dd08f8b19cc32da161811abb2f7093e0f5392e69
child 741105 bf6905d030e7c1f4e1e253fd43db3ea5893891d1
push id90091
push userbmo:dmu@mozilla.com
push dateTue, 21 Nov 2017 09:29:45 +0000
reviewersdvander
bugs1415762
milestone59.0a1
Bug 1415762 - Cancel VRListener task when CompositorVsyncScheduler is going to destroy; r?dvander MozReview-Commit-ID: CB5JrDGZTu1
gfx/layers/ipc/CompositorVsyncScheduler.cpp
gfx/layers/ipc/CompositorVsyncScheduler.h
gfx/vr/VRThread.h
--- a/gfx/layers/ipc/CompositorVsyncScheduler.cpp
+++ b/gfx/layers/ipc/CompositorVsyncScheduler.cpp
@@ -112,32 +112,34 @@ CompositorVsyncScheduler::Destroy()
   }
   MOZ_ASSERT(CompositorThreadHolder::IsInCompositorThread());
   UnobserveVsync();
   mVsyncObserver->Destroy();
   mVsyncObserver = nullptr;
 
   CancelCurrentSetNeedsCompositeTask();
   CancelCurrentCompositeTask();
+  CancelCurrentVRTask();
 }
 
 void
 CompositorVsyncScheduler::PostCompositeTask(TimeStamp aCompositeTimestamp)
 {
   // can be called from the compositor or vsync thread
   MonitorAutoLock lock(mCurrentCompositeTaskMonitor);
   if (mCurrentCompositeTask == nullptr && CompositorThreadHolder::Loop()) {
     RefPtr<CancelableRunnable> task = NewCancelableRunnableMethod<TimeStamp>(
       "layers::CompositorVsyncScheduler::Composite",
       this,
       &CompositorVsyncScheduler::Composite,
       aCompositeTimestamp);
     mCurrentCompositeTask = task;
     ScheduleTask(task.forget(), 0);
   }
+  MonitorAutoLock lockVR(mCurrentVRListenerTaskMonitor);
   if (mCurrentVRListenerTask == nullptr && VRListenerThreadHolder::Loop()) {
     RefPtr<CancelableRunnable> task = NewCancelableRunnableMethod<TimeStamp>(
       "layers::CompositorVsyncScheduler::DispatchVREvents",
       this,
       &CompositorVsyncScheduler::DispatchVREvents,
       aCompositeTimestamp);
     mCurrentVRListenerTask = task;
     MOZ_ASSERT(VRListenerThreadHolder::Loop());
@@ -238,16 +240,28 @@ CompositorVsyncScheduler::CancelCurrentC
   MonitorAutoLock lock(mCurrentCompositeTaskMonitor);
   if (mCurrentCompositeTask) {
     mCurrentCompositeTask->Cancel();
     mCurrentCompositeTask = nullptr;
   }
 }
 
 void
+CompositorVsyncScheduler::CancelCurrentVRTask()
+{
+  // This function is only called by CompositorVsyncScheduler::Destroy().
+  MOZ_ASSERT(CompositorThreadHolder::IsInCompositorThread());
+  MonitorAutoLock lockVR(mCurrentVRListenerTaskMonitor);
+  if (mCurrentVRListenerTask) {
+    mCurrentVRListenerTask->Cancel();
+    mCurrentVRListenerTask = nullptr;
+  }
+}
+
+void
 CompositorVsyncScheduler::Composite(TimeStamp aVsyncTimestamp)
 {
   MOZ_ASSERT(CompositorThreadHolder::IsInCompositorThread());
   {
     MonitorAutoLock lock(mCurrentCompositeTaskMonitor);
     mCurrentCompositeTask = nullptr;
   }
 
--- a/gfx/layers/ipc/CompositorVsyncScheduler.h
+++ b/gfx/layers/ipc/CompositorVsyncScheduler.h
@@ -78,16 +78,17 @@ private:
   virtual ~CompositorVsyncScheduler();
 
   void NotifyCompositeTaskExecuted();
   void ObserveVsync();
   void UnobserveVsync();
   void DispatchTouchEvents(TimeStamp aVsyncTimestamp);
   void DispatchVREvents(TimeStamp aVsyncTimestamp);
   void CancelCurrentSetNeedsCompositeTask();
+  void CancelCurrentVRTask();
 
   class Observer final : public VsyncObserver
   {
   public:
     explicit Observer(CompositorVsyncScheduler* aOwner);
     virtual bool NotifyVsync(TimeStamp aVsyncTimestamp) override;
     void Destroy();
   private:
--- a/gfx/vr/VRThread.h
+++ b/gfx/vr/VRThread.h
@@ -22,17 +22,17 @@ public:
 
   base::Thread* GetThread() const {
     return mThread;
   }
 
   static VRListenerThreadHolder* GetSingleton();
 
   static bool IsActive() {
-    return !!GetSingleton();
+    return GetSingleton() && Loop();
   }
 
   static void Start();
   static void Shutdown();
   static MessageLoop* Loop();
   static bool IsInVRListenerThread();
 
 private: