Chromium Code Reviews| Index: content/renderer/media/android/media_source_delegate.cc |
| =================================================================== |
| --- content/renderer/media/android/media_source_delegate.cc (revision 220850) |
| +++ content/renderer/media/android/media_source_delegate.cc (working copy) |
| @@ -37,35 +37,44 @@ |
| namespace content { |
| -// TODO(xhwang): BIND_TO_RENDER_LOOP* force posts callback! Since everything |
| -// works on the same thread in this class, not all force posts are necessary. |
| - |
| #define BIND_TO_RENDER_LOOP(function) \ |
| - media::BindToLoop(base::MessageLoopProxy::current(), \ |
| - base::Bind(function, weak_this_.GetWeakPtr())) |
| + media::BindToLoop(main_loop_, \ |
| + base::Bind(function, main_weak_this_.GetWeakPtr())) |
| #define BIND_TO_RENDER_LOOP_1(function, arg1) \ |
| - media::BindToLoop(base::MessageLoopProxy::current(), \ |
| - base::Bind(function, weak_this_.GetWeakPtr(), arg1)) |
| + media::BindToLoop(main_loop_, \ |
| + base::Bind(function, main_weak_this_.GetWeakPtr(), arg1)) |
| -#define BIND_TO_RENDER_LOOP_2(function, arg1, arg2) \ |
| - media::BindToLoop(base::MessageLoopProxy::current(), \ |
| - base::Bind(function, weak_this_.GetWeakPtr(), arg1, arg2)) |
| +#if defined(GOOGLE_TV) |
| +#define DCHECK_BELONG_TO_MEDIA_LOOP() \ |
| + DCHECK(media_loop_->BelongsToCurrentThread()) |
| +#else |
| +#define DCHECK_BELONG_TO_MEDIA_LOOP() \ |
| + DCHECK(main_loop_->BelongsToCurrentThread()) |
| +#endif |
| -#define BIND_TO_RENDER_LOOP_3(function, arg1, arg2, arg3) \ |
| - media::BindToLoop(base::MessageLoopProxy::current(), \ |
| - base::Bind(function, \ |
| - weak_this_.GetWeakPtr(), arg1, arg2, arg3)) |
| - |
| static void LogMediaSourceError(const scoped_refptr<media::MediaLog>& media_log, |
| const std::string& error) { |
| media_log->AddEvent(media_log->CreateMediaSourceErrorEvent(error)); |
| } |
| -MediaSourceDelegate::MediaSourceDelegate(WebMediaPlayerProxyAndroid* proxy, |
| - int player_id, |
| - media::MediaLog* media_log) |
| - : weak_this_(this), |
| +MediaSourceDelegate::MediaSourceDelegate( |
| + WebMediaPlayerProxyAndroid* proxy, |
| + int player_id, |
| + const scoped_refptr<base::MessageLoopProxy>& media_loop, |
| + media::MediaLog* media_log) |
| + : main_weak_this_(this), |
| + media_weak_this_(this), |
| + main_loop_(base::MessageLoopProxy::current()), |
| +#if defined(GOOGLE_TV) |
| + media_loop_(media_loop), |
| + send_read_from_demuxer_ack_cb_( |
| + BIND_TO_RENDER_LOOP(&MediaSourceDelegate::SendReadFromDemuxerAck)), |
| + send_seek_request_ack_cb_( |
| + BIND_TO_RENDER_LOOP(&MediaSourceDelegate::SendSeekRequestAck)), |
| + send_demuxer_ready_cb_( |
| + BIND_TO_RENDER_LOOP(&MediaSourceDelegate::SendDemuxerReady)), |
| +#endif |
| proxy_(proxy), |
| player_id_(player_id), |
| media_log_(media_log), |
| @@ -80,6 +89,7 @@ |
| } |
| MediaSourceDelegate::~MediaSourceDelegate() { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| DVLOG(1) << "~MediaSourceDelegate() : " << player_id_; |
| DCHECK(!chunk_demuxer_); |
| DCHECK(!demuxer_); |
| @@ -90,6 +100,7 @@ |
| } |
| void MediaSourceDelegate::Destroy() { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| DVLOG(1) << "Destroy() : " << player_id_; |
| if (!demuxer_) { |
| delete this; |
| @@ -101,7 +112,27 @@ |
| media_source_.reset(); |
| proxy_ = NULL; |
| - demuxer_ = NULL; |
| + main_weak_this_.InvalidateWeakPtrs(); |
| + DCHECK(!main_weak_this_.HasWeakPtrs()); |
| + |
| + if (chunk_demuxer_) |
| + chunk_demuxer_->Shutdown(); |
| +#if defined(GOOGLE_TV) |
| + // |this| will be transfered to the callback StopDemuxer() and |
| + // OnDemuxerStopDone(). they own |this| and OnDemuxerStopDone() will delete |
| + // it when called. Hence using base::Unretained(this) is safe here. |
| + media_loop_->PostTask(FROM_HERE, |
| + base::Bind(&MediaSourceDelegate::StopDemuxer, |
| + base::Unretained(this))); |
| +#else |
| + StopDemuxer(); |
| +#endif |
| +} |
| + |
| +void MediaSourceDelegate::StopDemuxer() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| + DCHECK(demuxer_); |
| + |
| audio_stream_ = NULL; |
| video_stream_ = NULL; |
| // TODO(xhwang): Figure out if we need to Reset the DDSs after Seeking or |
| @@ -109,15 +140,14 @@ |
| audio_decrypting_demuxer_stream_.reset(); |
| video_decrypting_demuxer_stream_.reset(); |
| - weak_this_.InvalidateWeakPtrs(); |
| - DCHECK(!weak_this_.HasWeakPtrs()); |
| + media_weak_this_.InvalidateWeakPtrs(); |
| + DCHECK(!media_weak_this_.HasWeakPtrs()); |
| - if (chunk_demuxer_) { |
| - // The callback OnDemuxerStopDone() owns |this| and will delete it when |
| - // called. Hence using base::Unretained(this) is safe here. |
| - chunk_demuxer_->Stop(base::Bind(&MediaSourceDelegate::OnDemuxerStopDone, |
| - base::Unretained(this))); |
| - } |
| + // The callback OnDemuxerStopDone() owns |this| and will delete it when |
| + // called. Hence using base::Unretained(this) is safe here. |
| + demuxer_->Stop(media::BindToLoop(main_loop_, |
| + base::Bind(&MediaSourceDelegate::OnDemuxerStopDone, |
| + base::Unretained(this)))); |
| } |
| void MediaSourceDelegate::InitializeMediaSource( |
| @@ -126,12 +156,13 @@ |
| const media::SetDecryptorReadyCB& set_decryptor_ready_cb, |
| const UpdateNetworkStateCB& update_network_state_cb, |
| const DurationChangeCB& duration_change_cb) { |
| - DCHECK(media_source); |
| - media_source_.reset(media_source); |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| + DCHECK(!media_source_opened_cb.is_null()); |
|
ycheo (away)
2013/09/03 03:46:25
This line should be reverted to OLD-L129.
|
| + media_source_opened_cb_ = media_source_opened_cb; |
|
ycheo (away)
2013/09/03 03:46:25
This line should be reverted to OLD-L130.
|
| need_key_cb_ = need_key_cb; |
| set_decryptor_ready_cb_ = set_decryptor_ready_cb; |
| - update_network_state_cb_ = update_network_state_cb; |
| - duration_change_cb_ = duration_change_cb; |
| + update_network_state_cb_ = media::BindToCurrentLoop(update_network_state_cb); |
| + duration_change_cb_ = media::BindToCurrentLoop(duration_change_cb); |
| access_unit_size_ = kAccessUnitSizeForMediaSource; |
| chunk_demuxer_.reset(new media::ChunkDemuxer( |
| @@ -142,23 +173,40 @@ |
| base::Bind(&LogMediaSourceError, media_log_))); |
| demuxer_ = chunk_demuxer_.get(); |
| - chunk_demuxer_->Initialize(this, |
| - BIND_TO_RENDER_LOOP(&MediaSourceDelegate::OnDemuxerInitDone)); |
| +#if defined(GOOGLE_TV) |
| + // |this| will be retained until StopDemuxer() is posted, so Unretained() is |
| + // safe here. |
| + media_loop_->PostTask(FROM_HERE, |
| + base::Bind(&MediaSourceDelegate::InitializeDemuxer, |
| + base::Unretained(this))); |
| +#else |
| + InitializeDemuxer(); |
| +#endif |
| } |
| +void MediaSourceDelegate::InitializeDemuxer() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| + demuxer_->Initialize(this, base::Bind(&MediaSourceDelegate::OnDemuxerInitDone, |
| + media_weak_this_.GetWeakPtr())); |
| +} |
| + |
| #if defined(GOOGLE_TV) |
| void MediaSourceDelegate::InitializeMediaStream( |
| media::Demuxer* demuxer, |
| const UpdateNetworkStateCB& update_network_state_cb) { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| DCHECK(demuxer); |
| demuxer_ = demuxer; |
| - update_network_state_cb_ = update_network_state_cb; |
| + update_network_state_cb_ = media::BindToCurrentLoop(update_network_state_cb); |
| // When playing Media Stream, don't wait to accumulate multiple packets per |
| // IPC communication. |
| access_unit_size_ = 1; |
| - demuxer_->Initialize(this, |
| - BIND_TO_RENDER_LOOP(&MediaSourceDelegate::OnDemuxerInitDone)); |
| + // |this| will be retained until StopDemuxer() is posted, so Unretained() is |
| + // safe here. |
| + media_loop_->PostTask(FROM_HERE, |
| + base::Bind(&MediaSourceDelegate::InitializeDemuxer, |
| + base::Unretained(this))); |
| } |
| #endif |
| @@ -185,13 +233,14 @@ |
| } |
| void MediaSourceDelegate::Seek(base::TimeDelta time, unsigned seek_request_id) { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| DVLOG(1) << "Seek(" << time.InSecondsF() << ") : " << player_id_; |
| last_seek_time_ = time; |
| last_seek_request_id_ = seek_request_id; |
| if (chunk_demuxer_) { |
| - if (seeking_) { |
| + if (IsSeeking()) { |
| chunk_demuxer_->CancelPendingSeek(time); |
| return; |
| } |
| @@ -199,12 +248,24 @@ |
| chunk_demuxer_->StartWaitingForSeek(time); |
| } |
| - seeking_ = true; |
| - demuxer_->Seek(time, |
| - BIND_TO_RENDER_LOOP_1(&MediaSourceDelegate::OnDemuxerSeekDone, |
| - seek_request_id)); |
| + SetSeeking(true); |
| +#if defined(GOOGLE_TV) |
| + media_loop_->PostTask(FROM_HERE, |
| + base::Bind(&MediaSourceDelegate::SeekInternal, |
| + base::Unretained(this), |
| + time, seek_request_id)); |
| +#else |
| + SeekInternal(time, seek_request_id); |
| +#endif |
| } |
| +void MediaSourceDelegate::SeekInternal(base::TimeDelta time, |
| + unsigned request_id) { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| + demuxer_->Seek(time, base::Bind(&MediaSourceDelegate::OnDemuxerSeekDone, |
| + media_weak_this_.GetWeakPtr(), request_id)); |
| +} |
| + |
| void MediaSourceDelegate::SetTotalBytes(int64 total_bytes) { |
| NOTIMPLEMENTED(); |
| } |
| @@ -220,45 +281,61 @@ |
| void MediaSourceDelegate::SetDuration(base::TimeDelta duration) { |
| DVLOG(1) << "SetDuration(" << duration.InSecondsF() << ") : " << player_id_; |
| - // Notify our owner (e.g. WebMediaPlayerAndroid) that |
| - // duration has changed. |
| + // Notify our owner (e.g. WebMediaPlayerAndroid) that duration has changed. |
| + // |duration_change_cb_| is bound to the main thread. |
| if (!duration_change_cb_.is_null()) |
| duration_change_cb_.Run(duration); |
| } |
| void MediaSourceDelegate::OnReadFromDemuxer(media::DemuxerStream::Type type) { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| +#if defined(GOOGLE_TV) |
| + media_loop_->PostTask( |
| + FROM_HERE, |
| + base::Bind(&MediaSourceDelegate::OnReadFromDemuxerInternal, |
| + base::Unretained(this), type)); |
| +#else |
| + OnReadFromDemuxerInternal(type); |
| +#endif |
| +} |
| + |
| +void MediaSourceDelegate::OnReadFromDemuxerInternal( |
| + media::DemuxerStream::Type type) { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "OnReadFromDemuxer(" << type << ") : " << player_id_; |
| - if (seeking_) |
| + if (IsSeeking()) |
| return; // Drop the request during seeking. |
| DCHECK(type == DemuxerStream::AUDIO || type == DemuxerStream::VIDEO); |
| // The access unit size should have been initialized properly at this stage. |
| DCHECK_GT(access_unit_size_, 0u); |
| - MediaPlayerHostMsg_ReadFromDemuxerAck_Params* params = |
| - type == DemuxerStream::AUDIO ? &audio_params_ : &video_params_; |
| + scoped_ptr<MediaPlayerHostMsg_ReadFromDemuxerAck_Params> params( |
| + new MediaPlayerHostMsg_ReadFromDemuxerAck_Params()); |
| params->type = type; |
| params->access_units.resize(access_unit_size_); |
| - ReadFromDemuxerStream(type, params, 0); |
| + ReadFromDemuxerStream(type, params.Pass(), 0); |
| } |
| void MediaSourceDelegate::ReadFromDemuxerStream( |
| media::DemuxerStream::Type type, |
| - MediaPlayerHostMsg_ReadFromDemuxerAck_Params* params, |
| + scoped_ptr<MediaPlayerHostMsg_ReadFromDemuxerAck_Params> params, |
| size_t index) { |
| - DCHECK(!seeking_); |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| // DemuxerStream::Read() always returns the read callback asynchronously. |
| DemuxerStream* stream = |
| (type == DemuxerStream::AUDIO) ? audio_stream_ : video_stream_; |
| - stream->Read(base::Bind(&MediaSourceDelegate::OnBufferReady, |
| - weak_this_.GetWeakPtr(), type, params, index)); |
| + stream->Read(base::Bind( |
| + &MediaSourceDelegate::OnBufferReady, |
| + media_weak_this_.GetWeakPtr(), type, base::Passed(¶ms), index)); |
| } |
| void MediaSourceDelegate::OnBufferReady( |
| media::DemuxerStream::Type type, |
| - MediaPlayerHostMsg_ReadFromDemuxerAck_Params* params, |
| + scoped_ptr<MediaPlayerHostMsg_ReadFromDemuxerAck_Params> params, |
| size_t index, |
| DemuxerStream::Status status, |
| const scoped_refptr<media::DecoderBuffer>& buffer) { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "OnBufferReady(" << index << ", " << status << ", " |
| << ((!buffer || buffer->end_of_stream()) ? |
| -1 : buffer->timestamp().InMilliseconds()) |
| @@ -267,9 +344,8 @@ |
| // No new OnReadFromDemuxer() will be called during seeking. So this callback |
| // must be from previous OnReadFromDemuxer() call and should be ignored. |
| - if (seeking_) { |
| + if (IsSeeking()) { |
| DVLOG(1) << "OnBufferReady(): Ignore previous read during seeking."; |
| - params->access_units.clear(); |
| return; |
| } |
| @@ -288,7 +364,6 @@ |
| case DemuxerStream::kAborted: |
| // Because the abort was caused by the seek, don't respond ack. |
| DVLOG(1) << "OnBufferReady() : Aborted"; |
| - params->access_units.clear(); |
| return; |
| case DemuxerStream::kConfigChanged: |
| @@ -348,7 +423,7 @@ |
| buffer->decrypt_config()->subsamples(); |
| } |
| if (++index < params->access_units.size()) { |
| - ReadFromDemuxerStream(type, params, index); |
| + ReadFromDemuxerStream(type, params.Pass(), index); |
| return; |
| } |
| break; |
| @@ -357,19 +432,29 @@ |
| NOTREACHED(); |
| } |
| - if (proxy_) |
| +#if defined(GOOGLE_TV) |
| + send_read_from_demuxer_ack_cb_.Run(params.Pass()); |
| +#else |
| + SendReadFromDemuxerAck(params.Pass()); |
| +#endif |
| +} |
| + |
| +void MediaSourceDelegate::SendReadFromDemuxerAck( |
| + scoped_ptr<MediaPlayerHostMsg_ReadFromDemuxerAck_Params> params) { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| + if (!IsSeeking() && proxy_) |
| proxy_->ReadFromDemuxerAck(player_id_, *params); |
| - |
| - params->access_units.clear(); |
| } |
| void MediaSourceDelegate::OnDemuxerError(media::PipelineStatus status) { |
| DVLOG(1) << "OnDemuxerError(" << status << ") : " << player_id_; |
| + // |update_network_state_cb_| is bound to the main thread. |
| if (status != media::PIPELINE_OK && !update_network_state_cb_.is_null()) |
| update_network_state_cb_.Run(PipelineErrorToNetworkState(status)); |
| } |
| void MediaSourceDelegate::OnDemuxerInitDone(media::PipelineStatus status) { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "OnDemuxerInitDone(" << status << ") : " << player_id_; |
| DCHECK(demuxer_); |
| @@ -402,6 +487,7 @@ |
| } |
| void MediaSourceDelegate::InitAudioDecryptingDemuxerStream() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "InitAudioDecryptingDemuxerStream() : " << player_id_; |
| DCHECK(!set_decryptor_ready_cb_.is_null()); |
| @@ -409,11 +495,12 @@ |
| base::MessageLoopProxy::current(), set_decryptor_ready_cb_)); |
| audio_decrypting_demuxer_stream_->Initialize( |
| audio_stream_, |
| - BIND_TO_RENDER_LOOP( |
| - &MediaSourceDelegate::OnAudioDecryptingDemuxerStreamInitDone)); |
| + base::Bind(&MediaSourceDelegate::OnAudioDecryptingDemuxerStreamInitDone, |
| + media_weak_this_.GetWeakPtr())); |
| } |
| void MediaSourceDelegate::InitVideoDecryptingDemuxerStream() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "InitVideoDecryptingDemuxerStream() : " << player_id_; |
| DCHECK(!set_decryptor_ready_cb_.is_null()); |
| @@ -421,12 +508,13 @@ |
| base::MessageLoopProxy::current(), set_decryptor_ready_cb_)); |
| video_decrypting_demuxer_stream_->Initialize( |
| video_stream_, |
| - BIND_TO_RENDER_LOOP( |
| - &MediaSourceDelegate::OnVideoDecryptingDemuxerStreamInitDone)); |
| + base::Bind(&MediaSourceDelegate::OnVideoDecryptingDemuxerStreamInitDone, |
| + media_weak_this_.GetWeakPtr())); |
| } |
| void MediaSourceDelegate::OnAudioDecryptingDemuxerStreamInitDone( |
| media::PipelineStatus status) { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "OnAudioDecryptingDemuxerStreamInitDone(" << status |
| << ") : " << player_id_; |
| DCHECK(demuxer_); |
| @@ -450,6 +538,7 @@ |
| void MediaSourceDelegate::OnVideoDecryptingDemuxerStreamInitDone( |
| media::PipelineStatus status) { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "OnVideoDecryptingDemuxerStreamInitDone(" << status |
| << ") : " << player_id_; |
| DCHECK(demuxer_); |
| @@ -467,8 +556,9 @@ |
| void MediaSourceDelegate::OnDemuxerSeekDone(unsigned seek_request_id, |
| media::PipelineStatus status) { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "OnDemuxerSeekDone(" << status << ") : " << player_id_; |
| - DCHECK(seeking_); |
| + DCHECK(IsSeeking()); |
| if (status != media::PIPELINE_OK) { |
| OnDemuxerError(status); |
| @@ -479,10 +569,7 @@ |
| if (seek_request_id != last_seek_request_id_) { |
| if (chunk_demuxer_) |
| chunk_demuxer_->StartWaitingForSeek(last_seek_time_); |
| - demuxer_->Seek( |
| - last_seek_time_, |
| - BIND_TO_RENDER_LOOP_1(&MediaSourceDelegate::OnDemuxerSeekDone, |
| - last_seek_request_id_)); |
| + SeekInternal(last_seek_time_, last_seek_request_id_); |
| return; |
| } |
| @@ -490,46 +577,73 @@ |
| } |
| void MediaSourceDelegate::ResetAudioDecryptingDemuxerStream() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "ResetAudioDecryptingDemuxerStream() : " << player_id_; |
| if (audio_decrypting_demuxer_stream_) { |
| audio_decrypting_demuxer_stream_->Reset( |
| base::Bind(&MediaSourceDelegate::ResetVideoDecryptingDemuxerStream, |
| - weak_this_.GetWeakPtr())); |
| + media_weak_this_.GetWeakPtr())); |
| } else { |
| ResetVideoDecryptingDemuxerStream(); |
| } |
| } |
| void MediaSourceDelegate::ResetVideoDecryptingDemuxerStream() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "ResetVideoDecryptingDemuxerStream()"; |
| +#if defined(GOOGLE_TV) |
| + if (video_decrypting_demuxer_stream_) |
| + video_decrypting_demuxer_stream_->Reset(send_seek_request_ack_cb_); |
| + else |
| + send_seek_request_ack_cb_.Run(); |
| +#else |
| if (video_decrypting_demuxer_stream_) { |
| video_decrypting_demuxer_stream_->Reset( |
| base::Bind(&MediaSourceDelegate::SendSeekRequestAck, |
| - weak_this_.GetWeakPtr())); |
| + main_weak_this_.GetWeakPtr())); |
| } else { |
| SendSeekRequestAck(); |
| } |
| +#endif |
| } |
| void MediaSourceDelegate::SendSeekRequestAck() { |
| DVLOG(1) << "SendSeekRequestAck() : " << player_id_; |
| - seeking_ = false; |
| + SetSeeking(false); |
| proxy_->SeekRequestAck(player_id_, last_seek_request_id_); |
| last_seek_request_id_ = 0; |
| } |
| void MediaSourceDelegate::OnDemuxerStopDone() { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| DVLOG(1) << "OnDemuxerStopDone() : " << player_id_; |
| chunk_demuxer_.reset(); |
| + demuxer_ = NULL; |
| delete this; |
| } |
| void MediaSourceDelegate::OnMediaConfigRequest() { |
| +#if defined(GOOGLE_TV) |
| + if (!media_loop_->BelongsToCurrentThread()) { |
| + media_loop_->PostTask(FROM_HERE, |
| + base::Bind(&MediaSourceDelegate::OnMediaConfigRequest, |
| + base::Unretained(this))); |
| + return; |
| + } |
| +#endif |
| if (CanNotifyDemuxerReady()) |
| NotifyDemuxerReady(); |
| } |
| void MediaSourceDelegate::NotifyKeyAdded(const std::string& key_system) { |
| +#if defined(GOOGLE_TV) |
| + if (!media_loop_->BelongsToCurrentThread()) { |
| + media_loop_->PostTask(FROM_HERE, |
| + base::Bind(&MediaSourceDelegate::NotifyKeyAdded, |
| + base::Unretained(this), key_system)); |
| + return; |
| + } |
| +#endif |
| DVLOG(1) << "NotifyKeyAdded() : " << player_id_; |
| // TODO(kjyoun): Enhance logic to detect when to call NotifyDemuxerReady() |
| // For now, we calls it when the first key is added. See |
| @@ -545,6 +659,7 @@ |
| } |
| bool MediaSourceDelegate::CanNotifyDemuxerReady() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| // This can happen when a key is added before the demuxer is initialized. |
| // See NotifyKeyAdded(). |
| // TODO(kjyoun): Remove NotifyDemxuerReady() call from NotifyKeyAdded() so |
| @@ -558,36 +673,49 @@ |
| } |
| void MediaSourceDelegate::NotifyDemuxerReady() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| DVLOG(1) << "NotifyDemuxerReady() : " << player_id_; |
| DCHECK(CanNotifyDemuxerReady()); |
| - MediaPlayerHostMsg_DemuxerReady_Params params; |
| + scoped_ptr<MediaPlayerHostMsg_DemuxerReady_Params> params( |
| + new MediaPlayerHostMsg_DemuxerReady_Params()); |
| if (audio_stream_) { |
| media::AudioDecoderConfig config = audio_stream_->audio_decoder_config(); |
| - params.audio_codec = config.codec(); |
| - params.audio_channels = |
| + params->audio_codec = config.codec(); |
| + params->audio_channels = |
| media::ChannelLayoutToChannelCount(config.channel_layout()); |
| - params.audio_sampling_rate = config.samples_per_second(); |
| - params.is_audio_encrypted = config.is_encrypted(); |
| - params.audio_extra_data = std::vector<uint8>( |
| + params->audio_sampling_rate = config.samples_per_second(); |
| + params->is_audio_encrypted = config.is_encrypted(); |
| + params->audio_extra_data = std::vector<uint8>( |
| config.extra_data(), config.extra_data() + config.extra_data_size()); |
| } |
| if (video_stream_) { |
| media::VideoDecoderConfig config = video_stream_->video_decoder_config(); |
| - params.video_codec = config.codec(); |
| - params.video_size = config.natural_size(); |
| - params.is_video_encrypted = config.is_encrypted(); |
| - params.video_extra_data = std::vector<uint8>( |
| + params->video_codec = config.codec(); |
| + params->video_size = config.natural_size(); |
| + params->is_video_encrypted = config.is_encrypted(); |
| + params->video_extra_data = std::vector<uint8>( |
| config.extra_data(), config.extra_data() + config.extra_data_size()); |
| } |
| - params.duration_ms = GetDurationMs(); |
| - params.key_system = HasEncryptedStream() ? key_system_ : ""; |
| + params->duration_ms = GetDurationMs(); |
| + params->key_system = HasEncryptedStream() ? key_system_ : ""; |
| +#if defined(GOOGLE_TV) |
| + send_demuxer_ready_cb_.Run(params.Pass()); |
| +#else |
| + SendDemuxerReady(params.Pass()); |
| +#endif |
| +} |
| + |
| +void MediaSourceDelegate::SendDemuxerReady( |
| + scoped_ptr<MediaPlayerHostMsg_DemuxerReady_Params> params) { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| if (proxy_) |
| - proxy_->DemuxerReady(player_id_, params); |
| + proxy_->DemuxerReady(player_id_, *params); |
| } |
| int MediaSourceDelegate::GetDurationMs() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| if (!chunk_demuxer_) |
| return -1; |
| @@ -601,7 +729,8 @@ |
| } |
| void MediaSourceDelegate::OnDemuxerOpened() { |
| - if (!media_source_) |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| + if (media_source_opened_cb_.is_null()) |
|
ycheo (away)
2013/09/03 03:46:25
This line should be reverted to OLD-L604.
|
| return; |
| media_source_->open(new WebMediaSourceClientImpl( |
| @@ -612,6 +741,7 @@ |
| const std::string& type, |
| scoped_ptr<uint8[]> init_data, |
| int init_data_size) { |
| + DCHECK(main_loop_->BelongsToCurrentThread()); |
| if (need_key_cb_.is_null()) |
| return; |
| @@ -626,10 +756,21 @@ |
| } |
| bool MediaSourceDelegate::HasEncryptedStream() { |
| + DCHECK_BELONG_TO_MEDIA_LOOP(); |
| return (audio_stream_ && |
| audio_stream_->audio_decoder_config().is_encrypted()) || |
| (video_stream_ && |
| video_stream_->video_decoder_config().is_encrypted()); |
| } |
| +void MediaSourceDelegate::SetSeeking(bool seeking) { |
| + base::AutoLock auto_lock(seeking_lock_); |
| + seeking_ = seeking; |
| +} |
| + |
| +bool MediaSourceDelegate::IsSeeking() const { |
| + base::AutoLock auto_lock(seeking_lock_); |
| + return seeking_; |
| +} |
| + |
| } // namespace content |