Fix broken config change handling in the mojo demuxers.
[chromium-blink-merge.git] / media / mojo / services / mojo_demuxer_stream_adapter.cc
blobca04816b5a8e7a484cc9295545399384c8d1ed4e
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "media/mojo/services/mojo_demuxer_stream_adapter.h"
7 #include "base/bind.h"
8 #include "base/callback_helpers.h"
9 #include "media/base/decoder_buffer.h"
10 #include "media/mojo/services/media_type_converters.h"
11 #include "mojo/public/cpp/system/data_pipe.h"
13 namespace media {
15 MojoDemuxerStreamAdapter::MojoDemuxerStreamAdapter(
16 mojo::DemuxerStreamPtr demuxer_stream,
17 const base::Closure& stream_ready_cb)
18 : demuxer_stream_(demuxer_stream.Pass()),
19 stream_ready_cb_(stream_ready_cb),
20 type_(DemuxerStream::UNKNOWN),
21 weak_factory_(this) {
22 DVLOG(1) << __FUNCTION__;
23 demuxer_stream_.set_client(this);
26 MojoDemuxerStreamAdapter::~MojoDemuxerStreamAdapter() {
27 DVLOG(1) << __FUNCTION__;
30 void MojoDemuxerStreamAdapter::Read(const DemuxerStream::ReadCB& read_cb) {
31 DVLOG(3) << __FUNCTION__;
32 // We shouldn't be holding on to a previous callback if a new Read() came in.
33 DCHECK(read_cb_.is_null());
35 DCHECK(stream_pipe_.is_valid());
36 read_cb_ = read_cb;
37 demuxer_stream_->Read(base::Bind(&MojoDemuxerStreamAdapter::OnBufferReady,
38 weak_factory_.GetWeakPtr()));
41 AudioDecoderConfig MojoDemuxerStreamAdapter::audio_decoder_config() {
42 DCHECK_EQ(type_, DemuxerStream::AUDIO);
43 DCHECK(!audio_config_queue_.empty());
44 return audio_config_queue_.front();
47 VideoDecoderConfig MojoDemuxerStreamAdapter::video_decoder_config() {
48 DCHECK_EQ(type_, DemuxerStream::VIDEO);
49 DCHECK(!video_config_queue_.empty());
50 return video_config_queue_.front();
53 DemuxerStream::Type MojoDemuxerStreamAdapter::type() const {
54 return type_;
57 void MojoDemuxerStreamAdapter::EnableBitstreamConverter() {
58 NOTIMPLEMENTED();
61 bool MojoDemuxerStreamAdapter::SupportsConfigChanges() {
62 return true;
65 VideoRotation MojoDemuxerStreamAdapter::video_rotation() {
66 NOTIMPLEMENTED();
67 return VIDEO_ROTATION_0;
70 // TODO(xhwang): Pass liveness here.
71 void MojoDemuxerStreamAdapter::OnStreamReady(
72 mojo::ScopedDataPipeConsumerHandle pipe) {
73 DVLOG(1) << __FUNCTION__;
74 DCHECK(pipe.is_valid());
75 DCHECK_NE(type_, DemuxerStream::UNKNOWN);
76 stream_pipe_ = pipe.Pass();
77 stream_ready_cb_.Run();
80 void MojoDemuxerStreamAdapter::OnAudioDecoderConfigChanged(
81 mojo::AudioDecoderConfigPtr config) {
82 DCHECK(type_ == DemuxerStream::UNKNOWN || type_ == DemuxerStream::AUDIO)
83 << type_;
84 type_ = DemuxerStream::AUDIO;
86 audio_config_queue_.push(config.To<AudioDecoderConfig>());
89 void MojoDemuxerStreamAdapter::OnVideoDecoderConfigChanged(
90 mojo::VideoDecoderConfigPtr config) {
91 DCHECK(type_ == DemuxerStream::UNKNOWN || type_ == DemuxerStream::VIDEO)
92 << type_;
93 type_ = DemuxerStream::VIDEO;
95 video_config_queue_.push(config.To<VideoDecoderConfig>());
98 void MojoDemuxerStreamAdapter::OnBufferReady(
99 mojo::DemuxerStream::Status status,
100 mojo::MediaDecoderBufferPtr buffer) {
101 DVLOG(3) << __FUNCTION__;
102 DCHECK(!read_cb_.is_null());
103 DCHECK_NE(type_, DemuxerStream::UNKNOWN);
104 DCHECK(stream_pipe_.is_valid());
106 if (status == mojo::DemuxerStream::STATUS_CONFIG_CHANGED) {
107 if (type_ == DemuxerStream::AUDIO) {
108 audio_config_queue_.pop();
109 DCHECK(!audio_config_queue_.empty());
110 } else if (type_ == DemuxerStream::VIDEO) {
111 video_config_queue_.pop();
112 DCHECK(!video_config_queue_.empty());
113 } else {
114 NOTREACHED() << "Unsupported config change encountered for type: "
115 << type_;
118 base::ResetAndReturn(&read_cb_).Run(DemuxerStream::kConfigChanged, nullptr);
119 return;
122 if (status == mojo::DemuxerStream::STATUS_ABORTED) {
123 base::ResetAndReturn(&read_cb_).Run(DemuxerStream::kAborted, nullptr);
124 return;
127 DCHECK_EQ(status, mojo::DemuxerStream::STATUS_OK);
128 scoped_refptr<DecoderBuffer> media_buffer(
129 buffer.To<scoped_refptr<DecoderBuffer>>());
131 if (!media_buffer->end_of_stream()) {
132 DCHECK_GT(media_buffer->data_size(), 0);
134 // Read the inner data for the DecoderBuffer from our DataPipe.
135 uint32_t num_bytes = media_buffer->data_size();
136 CHECK_EQ(ReadDataRaw(stream_pipe_.get(), media_buffer->writable_data(),
137 &num_bytes, MOJO_READ_DATA_FLAG_ALL_OR_NONE),
138 MOJO_RESULT_OK);
139 CHECK_EQ(num_bytes, static_cast<uint32_t>(media_buffer->data_size()));
142 base::ResetAndReturn(&read_cb_).Run(DemuxerStream::kOk, media_buffer);
145 } // namespace media