media_source_player.cc revision eb525c5499e34cc9c4b825d6d9e75bb07cc06ace
1// Copyright (c) 2013 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.
4
5#include "media/base/android/media_source_player.h"
6
7#include "base/android/jni_android.h"
8#include "base/android/jni_string.h"
9#include "base/basictypes.h"
10#include "base/bind.h"
11#include "base/lazy_instance.h"
12#include "base/logging.h"
13#include "base/message_loop.h"
14#include "base/threading/thread.h"
15#include "media/base/android/media_codec_bridge.h"
16#include "media/base/android/media_drm_bridge.h"
17#include "media/base/android/media_player_manager.h"
18#include "media/base/audio_timestamp_helper.h"
19
20namespace {
21
22// Timeout value for media codec operations. Because the first
23// DequeInputBuffer() can take about 150 milliseconds, use 250 milliseconds
24// here. See b/9357571.
25const int kMediaCodecTimeoutInMicroseconds = 250000;
26
27// Use 16bit PCM for audio output. Keep this value in sync with the output
28// format we passed to AudioTrack in MediaCodecBridge.
29const int kBytesPerAudioOutputSample = 2;
30
31class DecoderThread : public base::Thread {
32 public:
33  virtual ~DecoderThread() {}
34 protected:
35  DecoderThread(const char* name) : base::Thread(name) { Start(); }
36};
37
38class AudioDecoderThread : public DecoderThread {
39 public:
40  AudioDecoderThread() : DecoderThread("MediaSource_AudioDecoderThread") {}
41};
42
43class VideoDecoderThread : public DecoderThread {
44 public:
45  VideoDecoderThread() : DecoderThread("MediaSource_VideoDecoderThread") {}
46};
47
48// TODO(qinmin): Check if it is tolerable to use worker pool to handle all the
49// decoding tasks so that we don't need the global threads here.
50// http://crbug.com/245750
51base::LazyInstance<AudioDecoderThread>::Leaky
52    g_audio_decoder_thread = LAZY_INSTANCE_INITIALIZER;
53
54base::LazyInstance<VideoDecoderThread>::Leaky
55    g_video_decoder_thread = LAZY_INSTANCE_INITIALIZER;
56
57}
58
59namespace media {
60
61MediaDecoderJob::MediaDecoderJob(
62    const scoped_refptr<base::MessageLoopProxy>& decoder_loop,
63    MediaCodecBridge* media_codec_bridge,
64    bool is_audio)
65    : ui_loop_(base::MessageLoopProxy::current()),
66      decoder_loop_(decoder_loop),
67      media_codec_bridge_(media_codec_bridge),
68      needs_flush_(false),
69      is_audio_(is_audio),
70      weak_this_(this),
71      is_decoding_(false) {
72}
73
74MediaDecoderJob::~MediaDecoderJob() {}
75
76// Class for managing audio decoding jobs.
77class AudioDecoderJob : public MediaDecoderJob {
78 public:
79  virtual ~AudioDecoderJob() {}
80
81  static AudioDecoderJob* Create(
82      const AudioCodec audio_codec, int sample_rate, int channel_count,
83      const uint8* extra_data, size_t extra_data_size, jobject media_crypto);
84
85 private:
86  AudioDecoderJob(MediaCodecBridge* media_codec_bridge);
87};
88
89// Class for managing video decoding jobs.
90class VideoDecoderJob : public MediaDecoderJob {
91 public:
92  virtual ~VideoDecoderJob() {}
93
94  static VideoDecoderJob* Create(
95      const VideoCodec video_codec, const gfx::Size& size, jobject surface,
96      jobject media_crypto);
97
98 private:
99  VideoDecoderJob(MediaCodecBridge* media_codec_bridge);
100};
101
102void MediaDecoderJob::Decode(
103    const MediaPlayerHostMsg_ReadFromDemuxerAck_Params::AccessUnit& unit,
104    const base::TimeTicks& start_time_ticks,
105    const base::TimeDelta& start_presentation_timestamp,
106    const MediaDecoderJob::DecoderCallback& callback) {
107  DCHECK(!is_decoding_);
108  DCHECK(ui_loop_->BelongsToCurrentThread());
109  is_decoding_ = true;
110  decoder_loop_->PostTask(FROM_HERE, base::Bind(
111      &MediaDecoderJob::DecodeInternal, base::Unretained(this), unit,
112      start_time_ticks, start_presentation_timestamp, needs_flush_,
113      callback));
114  needs_flush_ = false;
115}
116
117void MediaDecoderJob::DecodeInternal(
118    const MediaPlayerHostMsg_ReadFromDemuxerAck_Params::AccessUnit& unit,
119    const base::TimeTicks& start_time_ticks,
120    const base::TimeDelta& start_presentation_timestamp,
121    bool needs_flush,
122    const MediaDecoderJob::DecoderCallback& callback) {
123  if (needs_flush)
124    media_codec_bridge_->Reset();
125  base::TimeDelta timeout = base::TimeDelta::FromMicroseconds(
126      kMediaCodecTimeoutInMicroseconds);
127  int input_buf_index = media_codec_bridge_->DequeueInputBuffer(timeout);
128  if (input_buf_index == MediaCodecBridge::INFO_MEDIA_CODEC_ERROR) {
129    ui_loop_->PostTask(FROM_HERE, base::Bind(
130        callback, DECODE_FAILED, start_presentation_timestamp, 0, false));
131    return;
132  }
133  // TODO(qinmin): skip frames if video is falling far behind.
134  if (input_buf_index >= 0) {
135    if (unit.end_of_stream || unit.data.empty()) {
136      media_codec_bridge_->QueueEOS(input_buf_index);
137    } else if (unit.key_id.empty()){
138      media_codec_bridge_->QueueInputBuffer(
139          input_buf_index, &unit.data[0], unit.data.size(), unit.timestamp);
140    } else {
141      if (unit.iv.empty() || unit.subsamples.empty()) {
142        LOG(ERROR) << "The access unit doesn't have iv or subsamples while it "
143                   << "has key IDs!";
144        ui_loop_->PostTask(FROM_HERE, base::Bind(
145            callback, DECODE_FAILED, start_presentation_timestamp, 0, false));
146        return;
147      }
148      media_codec_bridge_->QueueSecureInputBuffer(
149          input_buf_index, &unit.data[0], unit.data.size(),
150          reinterpret_cast<const uint8*>(&unit.key_id[0]), unit.key_id.size(),
151          reinterpret_cast<const uint8*>(&unit.iv[0]), unit.iv.size(),
152          &unit.subsamples[0], unit.subsamples.size(), unit.timestamp);
153    }
154  }
155
156  size_t offset = 0;
157  size_t size = 0;
158  base::TimeDelta presentation_timestamp;
159  bool end_of_stream = false;
160  DecodeStatus decode_status = DECODE_SUCCEEDED;
161
162  int outputBufferIndex = media_codec_bridge_->DequeueOutputBuffer(
163      timeout, &offset, &size, &presentation_timestamp, &end_of_stream);
164  switch (outputBufferIndex) {
165    case MediaCodecBridge::INFO_OUTPUT_BUFFERS_CHANGED:
166      media_codec_bridge_->GetOutputBuffers();
167      break;
168    case MediaCodecBridge::INFO_OUTPUT_FORMAT_CHANGED:
169      // TODO(qinmin): figure out what we should do if format changes.
170      break;
171    case MediaCodecBridge::INFO_TRY_AGAIN_LATER:
172      decode_status = DECODE_TRY_AGAIN_LATER;
173      break;
174    case MediaCodecBridge::INFO_MEDIA_CODEC_ERROR:
175      decode_status = DECODE_FAILED;
176      break;
177    default:
178      DCHECK_LE(0, outputBufferIndex);
179      if (size == 0 && end_of_stream)
180        break;
181      base::TimeDelta time_to_render;
182      DCHECK(!start_time_ticks.is_null());
183      if (!is_audio_) {
184        time_to_render = presentation_timestamp - (base::TimeTicks::Now() -
185            start_time_ticks + start_presentation_timestamp);
186      }
187      if (time_to_render >= base::TimeDelta()) {
188        base::MessageLoop::current()->PostDelayedTask(
189            FROM_HERE,
190            base::Bind(&MediaDecoderJob::ReleaseOutputBuffer,
191                       weak_this_.GetWeakPtr(), outputBufferIndex, size,
192                       presentation_timestamp, end_of_stream, callback),
193            time_to_render);
194      } else {
195        // TODO(qinmin): The codec is lagging behind, need to recalculate the
196        // |start_presentation_timestamp_| and |start_time_ticks_|.
197        DVLOG(1) << (is_audio_ ? "audio " : "video ")
198            << "codec is lagging behind :" << time_to_render.InMicroseconds();
199        ReleaseOutputBuffer(outputBufferIndex, size, presentation_timestamp,
200                            end_of_stream, callback);
201      }
202      return;
203  }
204  ui_loop_->PostTask(FROM_HERE, base::Bind(
205      callback, decode_status, start_presentation_timestamp, 0, end_of_stream));
206}
207
208void MediaDecoderJob::ReleaseOutputBuffer(
209    int outputBufferIndex, size_t size,
210    const base::TimeDelta& presentation_timestamp,
211    bool end_of_stream, const MediaDecoderJob::DecoderCallback& callback) {
212  // TODO(qinmin): Refactor this function. Maybe AudioDecoderJob should provide
213  // its own ReleaseOutputBuffer().
214  if (is_audio_) {
215    static_cast<AudioCodecBridge*>(media_codec_bridge_.get())->PlayOutputBuffer(
216        outputBufferIndex, size);
217  }
218  media_codec_bridge_->ReleaseOutputBuffer(outputBufferIndex, !is_audio_);
219  ui_loop_->PostTask(FROM_HERE, base::Bind(
220      callback, DECODE_SUCCEEDED, presentation_timestamp, is_audio_ ? size : 0,
221      end_of_stream));
222}
223
224void MediaDecoderJob::OnDecodeCompleted() {
225  DCHECK(ui_loop_->BelongsToCurrentThread());
226  is_decoding_ = false;
227}
228
229void MediaDecoderJob::Flush() {
230  // Do nothing, flush when the next Decode() happens.
231  needs_flush_ = true;
232}
233
234void MediaDecoderJob::Release() {
235  // If |decoding_| is false, there is nothing running on the decoder thread.
236  // So it is safe to delete the MediaDecoderJob on the UI thread. However,
237  // if we post a task to the decoder thread to delete object, then we cannot
238  // immediately pass the surface to a new MediaDecoderJob instance because
239  // the java surface is still owned by the old object. New decoder creation
240  // will be blocked on the UI thread until the previous decoder gets deleted.
241  // This introduces extra latency during config changes, and makes the logic in
242  // MediaSourcePlayer more complicated.
243  //
244  // TODO(qinmin): Figure out the logic to passing the surface to a new
245  // MediaDecoderJob instance after the previous one gets deleted on the decoder
246  // thread.
247  if (is_decoding_ && !decoder_loop_->BelongsToCurrentThread()) {
248    DCHECK(ui_loop_->BelongsToCurrentThread());
249    decoder_loop_->DeleteSoon(FROM_HERE, this);
250  } else {
251    delete this;
252  }
253}
254
255VideoDecoderJob* VideoDecoderJob::Create(
256    const VideoCodec video_codec, const gfx::Size& size, jobject surface,
257    jobject media_crypto) {
258  scoped_ptr<VideoCodecBridge> codec(VideoCodecBridge::Create(video_codec));
259  if (codec->Start(video_codec, size, surface, media_crypto))
260    return new VideoDecoderJob(codec.release());
261  return NULL;
262}
263
264VideoDecoderJob::VideoDecoderJob(MediaCodecBridge* media_codec_bridge)
265    : MediaDecoderJob(g_video_decoder_thread.Pointer()->message_loop_proxy(),
266                      media_codec_bridge,
267                      false) {}
268
269AudioDecoderJob* AudioDecoderJob::Create(
270    const AudioCodec audio_codec,
271    int sample_rate,
272    int channel_count,
273    const uint8* extra_data,
274    size_t extra_data_size,
275    jobject media_crypto) {
276  scoped_ptr<AudioCodecBridge> codec(AudioCodecBridge::Create(audio_codec));
277  if (codec->Start(audio_codec, sample_rate, channel_count, extra_data,
278                   extra_data_size, true, media_crypto)) {
279    return new AudioDecoderJob(codec.release());
280  }
281  return NULL;
282}
283
284AudioDecoderJob::AudioDecoderJob(MediaCodecBridge* media_codec_bridge)
285    : MediaDecoderJob(g_audio_decoder_thread.Pointer()->message_loop_proxy(),
286                      media_codec_bridge,
287                      true) {}
288
289MediaSourcePlayer::MediaSourcePlayer(
290    int player_id,
291    MediaPlayerManager* manager)
292    : MediaPlayerAndroid(player_id, manager),
293      pending_event_(NO_EVENT_PENDING),
294      seek_request_id_(0),
295      width_(0),
296      height_(0),
297      audio_codec_(kUnknownAudioCodec),
298      video_codec_(kUnknownVideoCodec),
299      num_channels_(0),
300      sampling_rate_(0),
301      audio_finished_(true),
302      video_finished_(true),
303      playing_(false),
304      is_audio_encrypted_(false),
305      is_video_encrypted_(false),
306      clock_(&default_tick_clock_),
307      reconfig_audio_decoder_(false),
308      reconfig_video_decoder_(false),
309      audio_access_unit_index_(0),
310      video_access_unit_index_(0),
311      waiting_for_audio_data_(false),
312      waiting_for_video_data_(false),
313      sync_decoder_jobs_(true),
314      weak_this_(this),
315      drm_bridge_(NULL) {
316}
317
318MediaSourcePlayer::~MediaSourcePlayer() {
319  Release();
320}
321
322void MediaSourcePlayer::SetVideoSurface(gfx::ScopedJavaSurface surface) {
323  surface_ =  surface.Pass();
324  pending_event_ |= SURFACE_CHANGE_EVENT_PENDING;
325  if (pending_event_ & SEEK_EVENT_PENDING) {
326    // Waiting for the seek to finish.
327    return;
328  }
329  // Setting a new surface will require a new MediaCodec to be created.
330  // Request a seek so that the new decoder will decode an I-frame first.
331  // Or otherwise, the new MediaCodec might crash. See b/8950387.
332  pending_event_ |= SEEK_EVENT_PENDING;
333  ProcessPendingEvents();
334}
335
336bool MediaSourcePlayer::Seekable() {
337  // If the duration TimeDelta, converted to milliseconds from microseconds,
338  // is >= 2^31, then the media is assumed to be unbounded and unseekable.
339  // 2^31 is the bound due to java player using 32-bit integer for time
340  // values at millisecond resolution.
341  return duration_ <
342         base::TimeDelta::FromMilliseconds(std::numeric_limits<int32>::max());
343}
344
345void MediaSourcePlayer::Start() {
346  playing_ = true;
347
348  StartInternal();
349}
350
351void MediaSourcePlayer::Pause() {
352  // Since decoder jobs have their own thread, decoding is not fully paused
353  // until all the decoder jobs call MediaDecoderCallback(). It is possible
354  // that Start() is called while the player is waiting for
355  // MediaDecoderCallback(). In that case, decoding will continue when
356  // MediaDecoderCallback() is called.
357  playing_ = false;
358  start_time_ticks_ = base::TimeTicks();
359}
360
361bool MediaSourcePlayer::IsPlaying() {
362  return playing_;
363}
364
365int MediaSourcePlayer::GetVideoWidth() {
366  return width_;
367}
368
369int MediaSourcePlayer::GetVideoHeight() {
370  return height_;
371}
372
373void MediaSourcePlayer::SeekTo(base::TimeDelta timestamp) {
374  clock_.SetTime(timestamp, timestamp);
375  if (audio_timestamp_helper_)
376    audio_timestamp_helper_->SetBaseTimestamp(timestamp);
377  pending_event_ |= SEEK_EVENT_PENDING;
378  ProcessPendingEvents();
379}
380
381base::TimeDelta MediaSourcePlayer::GetCurrentTime() {
382  return clock_.Elapsed();
383}
384
385base::TimeDelta MediaSourcePlayer::GetDuration() {
386  return duration_;
387}
388
389void MediaSourcePlayer::Release() {
390  ClearDecodingData();
391  audio_decoder_job_.reset();
392  video_decoder_job_.reset();
393  reconfig_audio_decoder_ = false;
394  reconfig_video_decoder_ = false;
395  playing_ = false;
396  pending_event_ = NO_EVENT_PENDING;
397  surface_ = gfx::ScopedJavaSurface();
398  ReleaseMediaResourcesFromManager();
399}
400
401void MediaSourcePlayer::SetVolume(float leftVolume, float rightVolume) {
402}
403
404bool MediaSourcePlayer::CanPause() {
405  return Seekable();
406}
407
408bool MediaSourcePlayer::CanSeekForward() {
409  return Seekable();
410}
411
412bool MediaSourcePlayer::CanSeekBackward() {
413  return Seekable();
414}
415
416bool MediaSourcePlayer::IsPlayerReady() {
417  return audio_decoder_job_ || video_decoder_job_;
418}
419
420void MediaSourcePlayer::StartInternal() {
421  // If there are pending events, wait for them finish.
422  if (pending_event_ != NO_EVENT_PENDING)
423    return;
424
425  // Create decoder jobs if they are not created
426  ConfigureAudioDecoderJob();
427  ConfigureVideoDecoderJob();
428
429
430  // If one of the decoder job is not ready, do nothing.
431  if ((HasAudio() && !audio_decoder_job_) ||
432      (HasVideo() && !video_decoder_job_)) {
433    return;
434  }
435
436  audio_finished_ = false;
437  video_finished_ = false;
438  sync_decoder_jobs_ = true;
439  SyncAndStartDecoderJobs();
440}
441
442void MediaSourcePlayer::DemuxerReady(
443    const MediaPlayerHostMsg_DemuxerReady_Params& params) {
444  duration_ = base::TimeDelta::FromMilliseconds(params.duration_ms);
445  width_ = params.video_size.width();
446  height_ = params.video_size.height();
447  num_channels_ = params.audio_channels;
448  sampling_rate_ = params.audio_sampling_rate;
449  audio_codec_ = params.audio_codec;
450  video_codec_ = params.video_codec;
451  audio_extra_data_ = params.audio_extra_data;
452  is_audio_encrypted_ = params.is_audio_encrypted;
453  is_video_encrypted_ = params.is_video_encrypted;
454  clock_.SetDuration(duration_);
455  audio_timestamp_helper_.reset(new AudioTimestampHelper(
456      kBytesPerAudioOutputSample * num_channels_, sampling_rate_));
457  audio_timestamp_helper_->SetBaseTimestamp(GetCurrentTime());
458  OnMediaMetadataChanged(duration_, width_, height_, true);
459  if (pending_event_ & CONFIG_CHANGE_EVENT_PENDING) {
460    if (reconfig_audio_decoder_)
461      ConfigureAudioDecoderJob();
462
463    // If there is a pending surface change, we can merge it with the config
464    // change.
465    if (reconfig_video_decoder_) {
466      pending_event_ &= ~SURFACE_CHANGE_EVENT_PENDING;
467      ConfigureVideoDecoderJob();
468    }
469    pending_event_ &= ~CONFIG_CHANGE_EVENT_PENDING;
470    if (playing_)
471      StartInternal();
472  }
473}
474
475void MediaSourcePlayer::ReadFromDemuxerAck(
476    const MediaPlayerHostMsg_ReadFromDemuxerAck_Params& params) {
477  DCHECK_LT(0u, params.access_units.size());
478  if (params.type == DemuxerStream::AUDIO)
479    waiting_for_audio_data_ = false;
480  else
481    waiting_for_video_data_ = false;
482
483  // If there is a pending seek request, ignore the data from the chunk demuxer.
484  // The data will be requested later when OnSeekRequestAck() is called.
485  if (pending_event_ & SEEK_EVENT_PENDING)
486    return;
487
488  if (params.type == DemuxerStream::AUDIO) {
489    DCHECK_EQ(0u, audio_access_unit_index_);
490    received_audio_ = params;
491  } else {
492    DCHECK_EQ(0u, video_access_unit_index_);
493    received_video_ = params;
494  }
495
496  if (pending_event_ != NO_EVENT_PENDING || !playing_)
497    return;
498
499  if (sync_decoder_jobs_) {
500    SyncAndStartDecoderJobs();
501    return;
502  }
503
504  if (params.type == DemuxerStream::AUDIO)
505    DecodeMoreAudio();
506  else
507    DecodeMoreVideo();
508}
509
510void MediaSourcePlayer::DurationChanged(const base::TimeDelta& duration) {
511  duration_ = duration;
512  clock_.SetDuration(duration_);
513}
514
515void MediaSourcePlayer::SetDrmBridge(MediaDrmBridge* drm_bridge) {
516  if (!is_audio_encrypted_ && !is_video_encrypted_)
517    return;
518
519  // Currently we don't support DRM change during the middle of playback, even
520  // if the player is paused.
521  // TODO(qinmin): support DRM change after playback has started.
522  // http://crbug.com/253792.
523  DCHECK(!audio_decoder_job_ || !audio_decoder_job_->is_decoding());
524  DCHECK(!video_decoder_job_ || !video_decoder_job_->is_decoding());
525  DCHECK_EQ(0u, audio_access_unit_index_);
526  DCHECK_EQ(0u, video_access_unit_index_);
527
528  drm_bridge_ = drm_bridge;
529
530  if (playing_)
531    StartInternal();
532}
533
534void MediaSourcePlayer::OnSeekRequestAck(unsigned seek_request_id) {
535  // Do nothing until the most recent seek request is processed.
536  if (seek_request_id_ != seek_request_id)
537    return;
538  pending_event_ &= ~SEEK_EVENT_PENDING;
539  OnSeekComplete();
540  ProcessPendingEvents();
541}
542
543void MediaSourcePlayer::UpdateTimestamps(
544    const base::TimeDelta& presentation_timestamp, size_t audio_output_bytes) {
545  if (audio_output_bytes > 0) {
546    audio_timestamp_helper_->AddBytes(audio_output_bytes);
547    clock_.SetMaxTime(audio_timestamp_helper_->GetTimestamp());
548  } else {
549    clock_.SetMaxTime(presentation_timestamp);
550  }
551
552  OnTimeUpdated();
553}
554
555void MediaSourcePlayer::ProcessPendingEvents() {
556  // Wait for all the decoding jobs to finish before processing pending tasks.
557  if ((audio_decoder_job_ && audio_decoder_job_->is_decoding()) ||
558      (video_decoder_job_ && video_decoder_job_->is_decoding())) {
559    return;
560  }
561
562  if (pending_event_ & SEEK_EVENT_PENDING) {
563    ClearDecodingData();
564    manager()->OnMediaSeekRequest(
565        player_id(), GetCurrentTime(), ++seek_request_id_);
566    return;
567  }
568
569  start_time_ticks_ = base::TimeTicks();
570  if (pending_event_ & CONFIG_CHANGE_EVENT_PENDING) {
571    DCHECK(reconfig_audio_decoder_ || reconfig_video_decoder_);
572    manager()->OnMediaConfigRequest(player_id());
573    return;
574  }
575
576  if (pending_event_ & SURFACE_CHANGE_EVENT_PENDING) {
577    video_decoder_job_.reset();
578    ConfigureVideoDecoderJob();
579    pending_event_ &= ~SURFACE_CHANGE_EVENT_PENDING;
580  }
581
582  if (playing_)
583    StartInternal();
584}
585
586void MediaSourcePlayer::MediaDecoderCallback(
587    bool is_audio, MediaDecoderJob::DecodeStatus decode_status,
588    const base::TimeDelta& presentation_timestamp, size_t audio_output_bytes,
589    bool end_of_stream) {
590  if (is_audio && audio_decoder_job_)
591    audio_decoder_job_->OnDecodeCompleted();
592  if (!is_audio && video_decoder_job_)
593    video_decoder_job_->OnDecodeCompleted();
594
595  if (is_audio)
596    decoder_starvation_callback_.Cancel();
597
598  if (decode_status == MediaDecoderJob::DECODE_FAILED) {
599    Release();
600    OnMediaError(MEDIA_ERROR_DECODE);
601    return;
602  } else if (decode_status == MediaDecoderJob::DECODE_SUCCEEDED) {
603    if (is_audio)
604      audio_access_unit_index_++;
605    else
606      video_access_unit_index_++;
607  }
608
609  if (pending_event_ != NO_EVENT_PENDING) {
610    ProcessPendingEvents();
611    return;
612  }
613
614  if (is_audio || !HasAudio())
615    UpdateTimestamps(presentation_timestamp, audio_output_bytes);
616
617  if (end_of_stream) {
618    PlaybackCompleted(is_audio);
619    return;
620  }
621
622  if (!playing_) {
623    if (is_audio || !HasAudio())
624      clock_.Pause();
625    return;
626  }
627
628  if (sync_decoder_jobs_) {
629    SyncAndStartDecoderJobs();
630    return;
631  }
632
633  base::TimeDelta current_timestamp = GetCurrentTime();
634  if (is_audio) {
635    base::TimeDelta timeout =
636        audio_timestamp_helper_->GetTimestamp() - current_timestamp;
637    StartStarvationCallback(timeout);
638    if (!HasAudioData())
639      RequestAudioData();
640    else
641      DecodeMoreAudio();
642    return;
643  }
644
645  if (!HasAudio()) {
646    DCHECK(current_timestamp <= presentation_timestamp);
647    // For video only streams, fps can be estimated from the difference
648    // between the previous and current presentation timestamps. The
649    // previous presentation timestamp is equal to current_timestamp.
650    // TODO(qinmin): determine whether 2 is a good coefficient for estimating
651    // video frame timeout.
652    StartStarvationCallback(2 * (presentation_timestamp - current_timestamp));
653  }
654  if (!HasVideoData())
655    RequestVideoData();
656  else
657    DecodeMoreVideo();
658}
659
660void MediaSourcePlayer::DecodeMoreAudio() {
661  DCHECK(!audio_decoder_job_->is_decoding());
662  DCHECK(HasAudioData());
663
664  if (DemuxerStream::kConfigChanged ==
665      received_audio_.access_units[audio_access_unit_index_].status) {
666    // Wait for demuxer ready message.
667    reconfig_audio_decoder_ = true;
668    pending_event_ |= CONFIG_CHANGE_EVENT_PENDING;
669    received_audio_ = MediaPlayerHostMsg_ReadFromDemuxerAck_Params();
670    audio_access_unit_index_ = 0;
671    ProcessPendingEvents();
672    return;
673  }
674
675  audio_decoder_job_->Decode(
676      received_audio_.access_units[audio_access_unit_index_],
677      start_time_ticks_, start_presentation_timestamp_,
678      base::Bind(&MediaSourcePlayer::MediaDecoderCallback,
679                 weak_this_.GetWeakPtr(), true));
680}
681
682void MediaSourcePlayer::DecodeMoreVideo() {
683  DCHECK(!video_decoder_job_->is_decoding());
684  DCHECK(HasVideoData());
685
686  if (DemuxerStream::kConfigChanged ==
687      received_video_.access_units[video_access_unit_index_].status) {
688    // Wait for demuxer ready message.
689    reconfig_video_decoder_ = true;
690    pending_event_ |= CONFIG_CHANGE_EVENT_PENDING;
691    received_video_ = MediaPlayerHostMsg_ReadFromDemuxerAck_Params();
692    video_access_unit_index_ = 0;
693    ProcessPendingEvents();
694    return;
695  }
696
697  video_decoder_job_->Decode(
698      received_video_.access_units[video_access_unit_index_],
699      start_time_ticks_, start_presentation_timestamp_,
700      base::Bind(&MediaSourcePlayer::MediaDecoderCallback,
701                 weak_this_.GetWeakPtr(), false));
702}
703
704void MediaSourcePlayer::PlaybackCompleted(bool is_audio) {
705  if (is_audio)
706    audio_finished_ = true;
707  else
708    video_finished_ = true;
709
710  if ((!HasAudio() || audio_finished_) && (!HasVideo() || video_finished_)) {
711    playing_ = false;
712    clock_.Pause();
713    start_time_ticks_ = base::TimeTicks();
714    OnPlaybackComplete();
715  }
716}
717
718void MediaSourcePlayer::ClearDecodingData() {
719  if (audio_decoder_job_)
720    audio_decoder_job_->Flush();
721  if (video_decoder_job_)
722    video_decoder_job_->Flush();
723  start_time_ticks_ = base::TimeTicks();
724  received_audio_ = MediaPlayerHostMsg_ReadFromDemuxerAck_Params();
725  received_video_ = MediaPlayerHostMsg_ReadFromDemuxerAck_Params();
726  audio_access_unit_index_ = 0;
727  video_access_unit_index_ = 0;
728  waiting_for_audio_data_ = false;
729  waiting_for_video_data_ = false;
730}
731
732bool MediaSourcePlayer::HasVideo() {
733  return kUnknownVideoCodec != video_codec_;
734}
735
736bool MediaSourcePlayer::HasAudio() {
737  return kUnknownAudioCodec != audio_codec_;
738}
739
740void MediaSourcePlayer::ConfigureAudioDecoderJob() {
741  if (!HasAudio()) {
742    audio_decoder_job_.reset();
743    return;
744  }
745
746  // Create audio decoder job only if config changes.
747  if (audio_decoder_job_ && !reconfig_audio_decoder_)
748    return;
749
750  base::android::ScopedJavaLocalRef<jobject> media_codec;
751  if (is_audio_encrypted_) {
752    if (drm_bridge_) {
753      media_codec = drm_bridge_->GetMediaCrypto();
754      // TODO(qinmin): currently we assume MediaCrypto is available whenever
755      // MediaDrmBridge is constructed. This will change if we want to support
756      // more general uses cases of EME.
757      DCHECK(!media_codec.is_null());
758    } else {
759      // Don't create the decoder job if |drm_bridge_| is not set,
760      // so StartInternal() will not proceed.
761      LOG(INFO) << "MediaDrmBridge is not available when creating decoder "
762                << "for encrypted audio stream.";
763      return;
764    }
765  }
766
767  audio_decoder_job_.reset(AudioDecoderJob::Create(
768      audio_codec_, sampling_rate_, num_channels_, &audio_extra_data_[0],
769      audio_extra_data_.size(), media_codec.obj()));
770
771  if (audio_decoder_job_)
772    reconfig_audio_decoder_ =  false;
773}
774
775void MediaSourcePlayer::ConfigureVideoDecoderJob() {
776  if (!HasVideo() || surface_.IsSurfaceEmpty()) {
777    video_decoder_job_.reset();
778    return;
779  }
780
781  // Create video decoder job only if config changes.
782  if (video_decoder_job_ && !reconfig_video_decoder_)
783    return;
784
785  base::android::ScopedJavaLocalRef<jobject> media_codec;
786  if (is_video_encrypted_) {
787    if (drm_bridge_) {
788      media_codec = drm_bridge_->GetMediaCrypto();
789      DCHECK(!media_codec.is_null());
790    } else {
791      LOG(INFO) << "MediaDrmBridge is not available when creating decoder "
792                << "for encrypted video stream.";
793      return;
794    }
795  }
796
797  // Release the old VideoDecoderJob first so the surface can get released.
798  // Android does not allow 2 MediaCodec instances use the same surface.
799  video_decoder_job_.reset();
800  // Create the new VideoDecoderJob.
801  video_decoder_job_.reset(VideoDecoderJob::Create(
802      video_codec_, gfx::Size(width_, height_), surface_.j_surface().obj(),
803      media_codec.obj()));
804  if (video_decoder_job_)
805    reconfig_video_decoder_ = false;
806
807  // Inform the fullscreen view the player is ready.
808  // TODO(qinmin): refactor MediaPlayerBridge so that we have a better way
809  // to inform ContentVideoView.
810  OnMediaMetadataChanged(duration_, width_, height_, true);
811}
812
813void MediaSourcePlayer::OnDecoderStarved() {
814  sync_decoder_jobs_ = true;
815}
816
817void MediaSourcePlayer::StartStarvationCallback(
818    const base::TimeDelta& timeout) {
819  decoder_starvation_callback_.Reset(
820      base::Bind(&MediaSourcePlayer::OnDecoderStarved,
821                 weak_this_.GetWeakPtr()));
822  base::MessageLoop::current()->PostDelayedTask(
823      FROM_HERE, decoder_starvation_callback_.callback(), timeout);
824}
825
826void MediaSourcePlayer::SyncAndStartDecoderJobs() {
827  // For streams with both audio and video, send the request for video too.
828  // However, don't wait for the response so that we won't have lots of
829  // noticeable pauses in the audio. Video will sync with audio by itself.
830  if (HasVideo() && !HasVideoData()) {
831    RequestVideoData();
832    if (!HasAudio())
833      return;
834  }
835  if (HasAudio() && !HasAudioData()) {
836    RequestAudioData();
837    return;
838  }
839  start_time_ticks_ = base::TimeTicks::Now();
840  start_presentation_timestamp_ = GetCurrentTime();
841  if (!clock_.IsPlaying())
842    clock_.Play();
843  if (HasAudioData() && !audio_decoder_job_->is_decoding())
844    DecodeMoreAudio();
845  if (HasVideoData() && !video_decoder_job_->is_decoding())
846    DecodeMoreVideo();
847  sync_decoder_jobs_ = false;
848}
849
850void MediaSourcePlayer::RequestAudioData() {
851  DCHECK(HasAudio());
852
853  if (waiting_for_audio_data_)
854    return;
855
856  manager()->OnReadFromDemuxer(player_id(), DemuxerStream::AUDIO);
857  received_audio_ = MediaPlayerHostMsg_ReadFromDemuxerAck_Params();
858  audio_access_unit_index_ = 0;
859  waiting_for_audio_data_ = true;
860}
861
862void MediaSourcePlayer::RequestVideoData() {
863  DCHECK(HasVideo());
864  if (waiting_for_video_data_)
865    return;
866
867  manager()->OnReadFromDemuxer(player_id(), DemuxerStream::VIDEO);
868  received_video_ = MediaPlayerHostMsg_ReadFromDemuxerAck_Params();
869  video_access_unit_index_ = 0;
870  waiting_for_video_data_ = true;
871}
872
873bool MediaSourcePlayer::HasAudioData() const {
874  return audio_access_unit_index_ < received_audio_.access_units.size();
875}
876
877bool MediaSourcePlayer::HasVideoData() const {
878  return video_access_unit_index_ < received_video_.access_units.size();
879}
880
881}  // namespace media
882