Bug 1209864. Part 1 - make all methods run on the main thread and remove usage of the decoder monitor. r=roc.

This commit is contained in:
JW Wang 2015-09-27 21:37:48 +08:00
Родитель f961371a5e
Коммит 7435f302de
4 изменённых файлов: 57 добавлений и 15 удалений

Просмотреть файл

@ -223,6 +223,7 @@ MediaDecoderStateMachine::MediaDecoderStateMachine(MediaDecoder* aDecoder,
mSentPlaybackEndedEvent(false), mSentPlaybackEndedEvent(false),
mStreamSink(new DecodedStream(mTaskQueue, mAudioQueue, mVideoQueue)), mStreamSink(new DecodedStream(mTaskQueue, mAudioQueue, mVideoQueue)),
mResource(aDecoder->GetResource()), mResource(aDecoder->GetResource()),
mAudioOffloading(false),
mBuffered(mTaskQueue, TimeIntervals(), mBuffered(mTaskQueue, TimeIntervals(),
"MediaDecoderStateMachine::mBuffered (Mirror)"), "MediaDecoderStateMachine::mBuffered (Mirror)"),
mEstimatedDuration(mTaskQueue, NullableTimeUnit(), mEstimatedDuration(mTaskQueue, NullableTimeUnit(),
@ -1088,15 +1089,13 @@ void MediaDecoderStateMachine::MaybeStartPlayback()
} }
bool playStatePermits = mPlayState == MediaDecoder::PLAY_STATE_PLAYING; bool playStatePermits = mPlayState == MediaDecoder::PLAY_STATE_PLAYING;
if (!playStatePermits || mIsAudioPrerolling || mIsVideoPrerolling) { if (!playStatePermits || mIsAudioPrerolling ||
mIsVideoPrerolling || mAudioOffloading) {
DECODER_LOG("Not starting playback [playStatePermits: %d, " DECODER_LOG("Not starting playback [playStatePermits: %d, "
"mIsAudioPrerolling: %d, mIsVideoPrerolling: %d]", "mIsAudioPrerolling: %d, mIsVideoPrerolling: %d, "
(int) playStatePermits, (int) mIsAudioPrerolling, (int) mIsVideoPrerolling); "mAudioOffloading: %d]",
return; (int)playStatePermits, (int)mIsAudioPrerolling,
} (int)mIsVideoPrerolling, (int)mAudioOffloading);
if (mDecoder->CheckDecoderCanOffloadAudio()) {
DECODER_LOG("Offloading playback");
return; return;
} }

Просмотреть файл

@ -205,6 +205,19 @@ public:
OwnerThread()->Dispatch(r.forget()); OwnerThread()->Dispatch(r.forget());
} }
void DispatchAudioOffloading(bool aAudioOffloading)
{
nsRefPtr<MediaDecoderStateMachine> self = this;
nsCOMPtr<nsIRunnable> r = NS_NewRunnableFunction([=] () {
ReentrantMonitorAutoEnter mon(self->mDecoder->GetReentrantMonitor());
if (self->mAudioOffloading != aAudioOffloading) {
self->mAudioOffloading = aAudioOffloading;
self->ScheduleStateMachine();
}
});
OwnerThread()->Dispatch(r.forget());
}
// Drop reference to decoder. Only called during shutdown dance. // Drop reference to decoder. Only called during shutdown dance.
void BreakCycles() { void BreakCycles() {
MOZ_ASSERT(NS_IsMainThread()); MOZ_ASSERT(NS_IsMainThread());
@ -1242,6 +1255,10 @@ private:
MediaEventListener mAudioQueueListener; MediaEventListener mAudioQueueListener;
MediaEventListener mVideoQueueListener; MediaEventListener mVideoQueueListener;
// True if audio is offloading.
// Playback will not start when audio is offloading.
bool mAudioOffloading;
#ifdef MOZ_EME #ifdef MOZ_EME
void OnCDMProxyReady(nsRefPtr<CDMProxy> aProxy); void OnCDMProxyReady(nsRefPtr<CDMProxy> aProxy);
void OnCDMProxyNotReady(); void OnCDMProxyNotReady();

Просмотреть файл

@ -41,13 +41,38 @@ MediaOmxCommonDecoder::~MediaOmxCommonDecoder() {}
void void
MediaOmxCommonDecoder::SetPlatformCanOffloadAudio(bool aCanOffloadAudio) MediaOmxCommonDecoder::SetPlatformCanOffloadAudio(bool aCanOffloadAudio)
{ {
ReentrantMonitorAutoEnter mon(GetReentrantMonitor()); if (!aCanOffloadAudio) {
mCanOffloadAudio = aCanOffloadAudio; return;
}
// Stop MDSM from playing to avoid startup glitch (bug 1053186).
GetStateMachine()->DispatchAudioOffloading(true);
// Modify mCanOffloadAudio in the main thread.
nsRefPtr<MediaOmxCommonDecoder> self = this;
nsCOMPtr<nsIRunnable> r = NS_NewRunnableFunction([=] () {
self->mCanOffloadAudio = true;
});
AbstractThread::MainThread()->Dispatch(r.forget());
}
void
MediaOmxCommonDecoder::DisableStateMachineAudioOffloading()
{
MOZ_ASSERT(NS_IsMainThread());
if (mCanOffloadAudio) {
// mCanOffloadAudio is true implies we've called
// |GetStateMachine()->DispatchAudioOffloading(true)| in
// SetPlatformCanOffloadAudio(). We need to turn off audio offloading
// for MDSM so it can start playback.
GetStateMachine()->DispatchAudioOffloading(false);
}
} }
bool bool
MediaOmxCommonDecoder::CheckDecoderCanOffloadAudio() MediaOmxCommonDecoder::CheckDecoderCanOffloadAudio()
{ {
MOZ_ASSERT(NS_IsMainThread());
return (mCanOffloadAudio && !mFallbackToStateMachine && return (mCanOffloadAudio && !mFallbackToStateMachine &&
!mIsCaptured && mPlaybackRate == 1.0); !mIsCaptured && mPlaybackRate == 1.0);
} }
@ -64,10 +89,10 @@ MediaOmxCommonDecoder::FirstFrameLoaded(nsAutoPtr<MediaInfo> aInfo,
MediaDecoder::FirstFrameLoaded(aInfo, aEventVisibility); MediaDecoder::FirstFrameLoaded(aInfo, aEventVisibility);
ReentrantMonitorAutoEnter mon(GetReentrantMonitor());
if (!CheckDecoderCanOffloadAudio()) { if (!CheckDecoderCanOffloadAudio()) {
DECODER_LOG(LogLevel::Debug, ("In %s Offload Audio check failed", DECODER_LOG(LogLevel::Debug, ("In %s Offload Audio check failed",
__PRETTY_FUNCTION__)); __PRETTY_FUNCTION__));
DisableStateMachineAudioOffloading();
return; return;
} }
@ -75,6 +100,7 @@ MediaOmxCommonDecoder::FirstFrameLoaded(nsAutoPtr<MediaInfo> aInfo,
mAudioOffloadPlayer = new AudioOffloadPlayer(this); mAudioOffloadPlayer = new AudioOffloadPlayer(this);
#endif #endif
if (!mAudioOffloadPlayer) { if (!mAudioOffloadPlayer) {
DisableStateMachineAudioOffloading();
return; return;
} }
@ -85,6 +111,7 @@ MediaOmxCommonDecoder::FirstFrameLoaded(nsAutoPtr<MediaInfo> aInfo,
mFallbackToStateMachine = true; mFallbackToStateMachine = true;
DECODER_LOG(LogLevel::Debug, ("In %s Unable to start offload audio %d." DECODER_LOG(LogLevel::Debug, ("In %s Unable to start offload audio %d."
"Switching to normal mode", __PRETTY_FUNCTION__, err)); "Switching to normal mode", __PRETTY_FUNCTION__, err));
DisableStateMachineAudioOffloading();
return; return;
} }
PauseStateMachine(); PauseStateMachine();
@ -105,7 +132,6 @@ void
MediaOmxCommonDecoder::PauseStateMachine() MediaOmxCommonDecoder::PauseStateMachine()
{ {
MOZ_ASSERT(NS_IsMainThread()); MOZ_ASSERT(NS_IsMainThread());
GetReentrantMonitor().AssertCurrentThreadIn();
DECODER_LOG(LogLevel::Debug, ("%s", __PRETTY_FUNCTION__)); DECODER_LOG(LogLevel::Debug, ("%s", __PRETTY_FUNCTION__));
if (mShuttingDown) { if (mShuttingDown) {
@ -123,7 +149,6 @@ void
MediaOmxCommonDecoder::ResumeStateMachine() MediaOmxCommonDecoder::ResumeStateMachine()
{ {
MOZ_ASSERT(NS_IsMainThread()); MOZ_ASSERT(NS_IsMainThread());
ReentrantMonitorAutoEnter mon(GetReentrantMonitor());
DECODER_LOG(LogLevel::Debug, ("%s current time %f", __PRETTY_FUNCTION__, mLogicalPosition)); DECODER_LOG(LogLevel::Debug, ("%s current time %f", __PRETTY_FUNCTION__, mLogicalPosition));
if (mShuttingDown) { if (mShuttingDown) {
@ -134,6 +159,8 @@ MediaOmxCommonDecoder::ResumeStateMachine()
return; return;
} }
GetStateMachine()->DispatchAudioOffloading(false);
mFallbackToStateMachine = true; mFallbackToStateMachine = true;
mAudioOffloadPlayer = nullptr; mAudioOffloadPlayer = nullptr;
SeekTarget target = SeekTarget(mLogicalPosition, SeekTarget target = SeekTarget(mLogicalPosition,
@ -231,8 +258,6 @@ MediaOmxCommonDecoder::CurrentPosition()
if (!mAudioOffloadPlayer) { if (!mAudioOffloadPlayer) {
return MediaDecoder::CurrentPosition(); return MediaDecoder::CurrentPosition();
} }
ReentrantMonitorAutoEnter mon(GetReentrantMonitor());
return mAudioOffloadPlayer->GetMediaTimeUs(); return mAudioOffloadPlayer->GetMediaTimeUs();
} }

Просмотреть файл

@ -50,6 +50,7 @@ protected:
virtual ~MediaOmxCommonDecoder(); virtual ~MediaOmxCommonDecoder();
void PauseStateMachine(); void PauseStateMachine();
void ResumeStateMachine(); void ResumeStateMachine();
void DisableStateMachineAudioOffloading();
MediaOmxCommonReader* mReader; MediaOmxCommonReader* mReader;