author | JW Wang <jwwang@mozilla.com> |
Mon, 01 Aug 2016 14:39:39 +0800 | |
changeset 349604 | 31c69994270f3e26a1fac3661d4a40496bf90283 |
parent 349603 | 2eafd00d43790e42fb5801dfe5be4498579c25c5 |
child 349605 | 5eaaa9b300cccd09f52b245315ce9bdda176795f |
push id | 6570 |
push user | raliiev@mozilla.com |
push date | Mon, 14 Nov 2016 12:26:13 +0000 |
treeherder | mozilla-beta@f455459b2ae5 [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | jya |
bugs | 1283724 |
milestone | 51.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
|
dom/media/MediaDecoder.cpp | file | annotate | diff | comparison | revisions | |
dom/media/MediaDecoder.h | file | annotate | diff | comparison | revisions |
--- a/dom/media/MediaDecoder.cpp +++ b/dom/media/MediaDecoder.cpp @@ -140,23 +140,26 @@ NS_IMPL_ISUPPORTS(MediaMemoryTracker, ns NS_IMPL_ISUPPORTS0(MediaDecoder) void MediaDecoder::ResourceCallback::Connect(MediaDecoder* aDecoder) { MOZ_ASSERT(NS_IsMainThread()); mDecoder = aDecoder; + mTimer = do_CreateInstance("@mozilla.org/timer;1"); } void MediaDecoder::ResourceCallback::Disconnect() { MOZ_ASSERT(NS_IsMainThread()); mDecoder = nullptr; + mTimer->Cancel(); + mTimer = nullptr; } MediaDecoderOwner* MediaDecoder::ResourceCallback::GetMediaOwner() const { MOZ_ASSERT(NS_IsMainThread()); return mDecoder ? mDecoder->GetOwner() : nullptr; } @@ -211,23 +214,40 @@ MediaDecoder::ResourceCallback::NotifyDe nsCOMPtr<nsIRunnable> r = NS_NewRunnableFunction([=] () { if (self->mDecoder) { self->mDecoder->DecodeError(); } }); AbstractThread::MainThread()->Dispatch(r.forget()); } +/* static */ void +MediaDecoder::ResourceCallback::TimerCallback(nsITimer* aTimer, void* aClosure) +{ + MOZ_ASSERT(NS_IsMainThread()); + ResourceCallback* thiz = static_cast<ResourceCallback*>(aClosure); + MOZ_ASSERT(thiz->mDecoder); + thiz->mDecoder->NotifyDataArrived(); + thiz->mTimerArmed = false; +} + void MediaDecoder::ResourceCallback::NotifyDataArrived() { MOZ_ASSERT(NS_IsMainThread()); - if (mDecoder) { - mDecoder->NotifyDataArrived(); + if (!mDecoder || mTimerArmed) { + return; } + // In situations where these notifications come from stochastic network + // activity, we can save significant computation by throttling the + // calls to MediaDecoder::NotifyDataArrived() which will update the buffer + // ranges of the reader. + mTimerArmed = true; + mTimer->InitWithFuncCallback( + TimerCallback, this, sDelay, nsITimer::TYPE_ONE_SHOT); } void MediaDecoder::ResourceCallback::NotifyBytesDownloaded() { MOZ_ASSERT(NS_IsMainThread()); if (mDecoder) { mDecoder->NotifyBytesDownloaded();
--- a/dom/media/MediaDecoder.h +++ b/dom/media/MediaDecoder.h @@ -65,16 +65,20 @@ public: : mAtEnd(aAtEnd), mEventVisibility(aEventVisibility) {} bool mAtEnd; MediaDecoderEventVisibility mEventVisibility; }; // Used to register with MediaResource to receive notifications which will // be forwarded to MediaDecoder. class ResourceCallback : public MediaResourceCallback { + // Throttle calls to MediaDecoder::NotifyDataArrived() + // to be at most once per 500ms. + static const uint32_t sDelay = 500; + public: // Start to receive notifications from ResourceCallback. void Connect(MediaDecoder* aDecoder); // Called upon shutdown to stop receiving notifications. void Disconnect(); private: /* MediaResourceCallback functions */ @@ -87,18 +91,22 @@ public: void NotifyDecodeError() override; void NotifyDataArrived() override; void NotifyBytesDownloaded() override; void NotifyDataEnded(nsresult aStatus) override; void NotifyPrincipalChanged() override; void NotifySuspendedStatusChanged() override; void NotifyBytesConsumed(int64_t aBytes, int64_t aOffset) override; + static void TimerCallback(nsITimer* aTimer, void* aClosure); + // The decoder to send notifications. Main-thread only. MediaDecoder* mDecoder = nullptr; + nsCOMPtr<nsITimer> mTimer; + bool mTimerArmed = false; }; typedef MozPromise<SeekResolveValue, bool /* aIgnored */, /* IsExclusive = */ true> SeekPromise; NS_DECL_THREADSAFE_ISUPPORTS // Enumeration for the valid play states (see mPlayState) enum PlayState {