Bug 1118841 - Implement the RefreshTimerVsyncDispatcher. r=kats

This commit is contained in:
JerryShih 2015-01-07 18:17:36 -08:00
parent a74c56f36f
commit 79c505b503
3 changed files with 102 additions and 22 deletions

View File

@ -7,6 +7,7 @@
#include "gfxPlatform.h"
#include "mozilla/TimeStamp.h"
#include "mozilla/VsyncDispatcher.h"
#include "MainThreadUtils.h"
using namespace mozilla;
using namespace mozilla::gfx;

View File

@ -3,35 +3,30 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "MainThreadUtils.h"
#include "VsyncDispatcher.h"
#include "mozilla/ClearOnShutdown.h"
#include "mozilla/layers/CompositorParent.h"
#include "gfxPrefs.h"
#include "gfxPlatform.h"
#include "VsyncSource.h"
#include "gfxPlatform.h"
#include "mozilla/layers/CompositorParent.h"
#ifdef MOZ_ENABLE_PROFILER_SPS
#include "GeckoProfiler.h"
#include "ProfilerMarkers.h"
#endif
#ifdef MOZ_WIDGET_GONK
#include "GeckoTouchDispatcher.h"
#endif
using namespace mozilla::layers;
namespace mozilla {
CompositorVsyncDispatcher::CompositorVsyncDispatcher()
: mCompositorObserverLock("CompositorObserverLock")
{
MOZ_ASSERT(XRE_IsParentProcess());
MOZ_ASSERT(NS_IsMainThread());
gfxPlatform::GetPlatform()->GetHardwareVsync()->AddCompositorVsyncDispatcher(this);
}
CompositorVsyncDispatcher::~CompositorVsyncDispatcher()
{
MOZ_ASSERT(XRE_IsParentProcess());
// We auto remove this vsync dispatcher from the vsync source in the nsBaseWidget
MOZ_ASSERT(NS_IsMainThread());
}
@ -42,12 +37,12 @@ CompositorVsyncDispatcher::NotifyVsync(TimeStamp aVsyncTimestamp)
// In hardware vsync thread
#ifdef MOZ_ENABLE_PROFILER_SPS
if (profiler_is_active()) {
CompositorParent::PostInsertVsyncProfilerMarker(aVsyncTimestamp);
layers::CompositorParent::PostInsertVsyncProfilerMarker(aVsyncTimestamp);
}
#endif
MutexAutoLock lock(mCompositorObserverLock);
if (gfxPrefs::VsyncAlignedCompositor() && mCompositorVsyncObserver) {
if (mCompositorVsyncObserver) {
mCompositorVsyncObserver->NotifyVsync(aVsyncTimestamp);
}
}
@ -55,7 +50,7 @@ CompositorVsyncDispatcher::NotifyVsync(TimeStamp aVsyncTimestamp)
void
CompositorVsyncDispatcher::SetCompositorVsyncObserver(VsyncObserver* aVsyncObserver)
{
MOZ_ASSERT(CompositorParent::IsInCompositorThread());
MOZ_ASSERT(layers::CompositorParent::IsInCompositorThread());
MutexAutoLock lock(mCompositorObserverLock);
mCompositorVsyncObserver = aVsyncObserver;
}
@ -70,4 +65,57 @@ CompositorVsyncDispatcher::Shutdown()
MOZ_ASSERT(NS_IsMainThread());
gfxPlatform::GetPlatform()->GetHardwareVsync()->RemoveCompositorVsyncDispatcher(this);
}
RefreshTimerVsyncDispatcher::RefreshTimerVsyncDispatcher()
: mRefreshTimersLock("RefreshTimers lock")
{
MOZ_ASSERT(XRE_IsParentProcess());
MOZ_ASSERT(NS_IsMainThread());
}
RefreshTimerVsyncDispatcher::~RefreshTimerVsyncDispatcher()
{
MOZ_ASSERT(XRE_IsParentProcess());
MOZ_ASSERT(NS_IsMainThread());
}
void
RefreshTimerVsyncDispatcher::NotifyVsync(TimeStamp aVsyncTimestamp)
{
MutexAutoLock lock(mRefreshTimersLock);
for (size_t i = 0; i < mChildRefreshTimers.Length(); i++) {
mChildRefreshTimers[i]->NotifyVsync(aVsyncTimestamp);
}
if (mParentRefreshTimer) {
mParentRefreshTimer->NotifyVsync(aVsyncTimestamp);
}
}
void
RefreshTimerVsyncDispatcher::SetParentRefreshTimer(VsyncObserver* aVsyncObserver)
{
MutexAutoLock lock(mRefreshTimersLock);
mParentRefreshTimer = aVsyncObserver;
}
void
RefreshTimerVsyncDispatcher::AddChildRefreshTimer(VsyncObserver* aVsyncObserver)
{
MutexAutoLock lock(mRefreshTimersLock);
MOZ_ASSERT(aVsyncObserver);
if (!mChildRefreshTimers.Contains(aVsyncObserver)) {
mChildRefreshTimers.AppendElement(aVsyncObserver);
}
}
void
RefreshTimerVsyncDispatcher::RemoveChildRefreshTimer(VsyncObserver* aVsyncObserver)
{
MutexAutoLock lock(mRefreshTimersLock);
MOZ_ASSERT(aVsyncObserver);
mChildRefreshTimers.RemoveElement(aVsyncObserver);
}
} // namespace mozilla

View File

@ -6,18 +6,13 @@
#ifndef mozilla_widget_VsyncDispatcher_h
#define mozilla_widget_VsyncDispatcher_h
#include "base/message_loop.h"
#include "mozilla/Mutex.h"
#include "mozilla/TimeStamp.h"
#include "nsISupportsImpl.h"
#include "nsTArray.h"
#include "ThreadSafeRefcountingWithMainThreadDestruction.h"
#include "nsRefPtr.h"
namespace mozilla {
class TimeStamp;
namespace layers {
class CompositorVsyncObserver;
}
class VsyncObserver
{
@ -25,7 +20,10 @@ class VsyncObserver
public:
// The method called when a vsync occurs. Return true if some work was done.
// Vsync notifications will occur on the hardware vsync thread
// In general, this vsync notification will occur on the hardware vsync
// thread from VsyncSource. But it might also be called on PVsync ipc thread
// if this notification is cross process. Thus all observer should check the
// thread model before handling the real task.
virtual bool NotifyVsync(TimeStamp aVsyncTimestamp) = 0;
protected:
@ -33,9 +31,11 @@ protected:
virtual ~VsyncObserver() {}
}; // VsyncObserver
// Used to dispatch vsync events in the parent process to compositors
class CompositorVsyncDispatcher MOZ_FINAL
{
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(CompositorVsyncDispatcher)
public:
CompositorVsyncDispatcher();
@ -53,10 +53,41 @@ public:
private:
virtual ~CompositorVsyncDispatcher();
Mutex mCompositorObserverLock;
nsRefPtr<VsyncObserver> mCompositorVsyncObserver;
};
// Dispatch vsync event to ipc actor parent and chrome RefreshTimer.
class RefreshTimerVsyncDispatcher MOZ_FINAL
{
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(RefreshTimerVsyncDispatcher)
public:
RefreshTimerVsyncDispatcher();
// Please check CompositorVsyncDispatcher::NotifyVsync().
void NotifyVsync(TimeStamp aVsyncTimestamp);
// Set chrome process's RefreshTimer to this dispatcher.
// This function can be called from any thread.
void SetParentRefreshTimer(VsyncObserver* aVsyncObserver);
// Add or remove the content process' RefreshTimer to this dispatcher. This
// will be a no-op for AddChildRefreshTimer() if the observer is already
// registered.
// These functions can be called from any thread.
void AddChildRefreshTimer(VsyncObserver* aVsyncObserver);
void RemoveChildRefreshTimer(VsyncObserver* aVsyncObserver);
private:
virtual ~RefreshTimerVsyncDispatcher();
Mutex mRefreshTimersLock;
nsRefPtr<VsyncObserver> mParentRefreshTimer;
nsTArray<nsRefPtr<VsyncObserver>> mChildRefreshTimers;
};
} // namespace mozilla
#endif // __mozilla_widget_VsyncDispatcher_h
#endif // mozilla_widget_VsyncDispatcher_h