Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(249)

Side by Side Diff: webkit/media/webmediaplayer_impl.cc

Issue 10905236: Move ChunkDemuxer handling from WMPProxy to WMPI and remove ChunkDemuxerClient (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Fix ffmpeg_regression_tests Created 8 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "webkit/media/webmediaplayer_impl.h" 5 #include "webkit/media/webmediaplayer_impl.h"
6 6
7 #include <limits> 7 #include <limits>
8 #include <string> 8 #include <string>
9 #include <vector> 9 #include <vector>
10 10
11 #include "base/bind.h" 11 #include "base/bind.h"
12 #include "base/callback.h" 12 #include "base/callback.h"
13 #include "base/command_line.h" 13 #include "base/command_line.h"
14 #include "base/message_loop_proxy.h" 14 #include "base/message_loop_proxy.h"
15 #include "base/metrics/histogram.h" 15 #include "base/metrics/histogram.h"
16 #include "base/string_number_conversions.h" 16 #include "base/string_number_conversions.h"
17 #include "base/synchronization/waitable_event.h" 17 #include "base/synchronization/waitable_event.h"
18 #include "media/audio/null_audio_sink.h" 18 #include "media/audio/null_audio_sink.h"
19 #include "media/base/bind_to_loop.h" 19 #include "media/base/bind_to_loop.h"
20 #include "media/base/filter_collection.h" 20 #include "media/base/filter_collection.h"
21 #include "media/base/limits.h" 21 #include "media/base/limits.h"
22 #include "media/base/media_log.h" 22 #include "media/base/media_log.h"
23 #include "media/base/media_switches.h" 23 #include "media/base/media_switches.h"
24 #include "media/base/pipeline.h" 24 #include "media/base/pipeline.h"
25 #include "media/base/video_frame.h" 25 #include "media/base/video_frame.h"
26 #include "media/filters/audio_renderer_impl.h" 26 #include "media/filters/audio_renderer_impl.h"
27 #include "media/filters/chunk_demuxer.h"
27 #include "media/filters/video_renderer_base.h" 28 #include "media/filters/video_renderer_base.h"
28 #include "third_party/WebKit/Source/WebKit/chromium/public/WebVideoFrame.h" 29 #include "third_party/WebKit/Source/WebKit/chromium/public/WebVideoFrame.h"
29 #include "third_party/WebKit/Source/WebKit/chromium/public/WebView.h" 30 #include "third_party/WebKit/Source/WebKit/chromium/public/WebView.h"
30 #include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebRect.h" 31 #include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebRect.h"
31 #include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebSize.h" 32 #include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebSize.h"
32 #include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebString.h" 33 #include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebString.h"
33 #include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebURL.h" 34 #include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebURL.h"
34 #include "v8/include/v8.h" 35 #include "v8/include/v8.h"
35 #include "webkit/media/buffered_data_source.h" 36 #include "webkit/media/buffered_data_source.h"
36 #include "webkit/media/filter_helpers.h" 37 #include "webkit/media/filter_helpers.h"
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
98 static WebKit::WebTimeRanges ConvertToWebTimeRanges( 99 static WebKit::WebTimeRanges ConvertToWebTimeRanges(
99 const media::Ranges<base::TimeDelta>& ranges) { 100 const media::Ranges<base::TimeDelta>& ranges) {
100 WebKit::WebTimeRanges result(ranges.size()); 101 WebKit::WebTimeRanges result(ranges.size());
101 for (size_t i = 0; i < ranges.size(); i++) { 102 for (size_t i = 0; i < ranges.size(); i++) {
102 result[i].start = ranges.start(i).InSecondsF(); 103 result[i].start = ranges.start(i).InSecondsF();
103 result[i].end = ranges.end(i).InSecondsF(); 104 result[i].end = ranges.end(i).InSecondsF();
104 } 105 }
105 return result; 106 return result;
106 } 107 }
107 108
109 typedef base::Callback<void(const std::string&,
110 const std::string&,
Ami GONE FROM CHROMIUM 2012/09/12 18:45:34 what's with these std::strings??
acolwell GONE FROM CHROMIUM 2012/09/12 22:03:53 These are for the key_system and session_id. I'm n
Ami GONE FROM CHROMIUM 2012/09/12 22:29:03 Feel like adding a TODO to figure out whether thes
acolwell GONE FROM CHROMIUM 2012/09/13 00:16:23 Done.
111 scoped_array<uint8>,
112 int)> OnNeedKeyCB;
113
114 static void OnDemuxerNeedKeyTrampoline(
115 const scoped_refptr<base::MessageLoopProxy>& message_loop,
116 const OnNeedKeyCB& need_key_cb,
117 scoped_array<uint8> init_data,
118 int init_data_size) {
119 message_loop->PostTask(FROM_HERE, base::Bind(
120 need_key_cb, "", "", base::Passed(&init_data), init_data_size));
121 }
122
108 WebMediaPlayerImpl::WebMediaPlayerImpl( 123 WebMediaPlayerImpl::WebMediaPlayerImpl(
109 WebKit::WebFrame* frame, 124 WebKit::WebFrame* frame,
110 WebKit::WebMediaPlayerClient* client, 125 WebKit::WebMediaPlayerClient* client,
111 base::WeakPtr<WebMediaPlayerDelegate> delegate, 126 base::WeakPtr<WebMediaPlayerDelegate> delegate,
112 media::FilterCollection* collection, 127 media::FilterCollection* collection,
113 WebKit::WebAudioSourceProvider* audio_source_provider, 128 WebKit::WebAudioSourceProvider* audio_source_provider,
114 media::AudioRendererSink* audio_renderer_sink, 129 media::AudioRendererSink* audio_renderer_sink,
115 media::MessageLoopFactory* message_loop_factory, 130 media::MessageLoopFactory* message_loop_factory,
116 MediaStreamClient* media_stream_client, 131 MediaStreamClient* media_stream_client,
117 media::MediaLog* media_log) 132 media::MediaLog* media_log)
(...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after
242 // Media streams pipelines can start immediately. 257 // Media streams pipelines can start immediately.
243 if (BuildMediaStreamCollection(url, media_stream_client_, 258 if (BuildMediaStreamCollection(url, media_stream_client_,
244 message_loop_factory_.get(), 259 message_loop_factory_.get(),
245 filter_collection_.get())) { 260 filter_collection_.get())) {
246 supports_save_ = false; 261 supports_save_ = false;
247 StartPipeline(); 262 StartPipeline();
248 return; 263 return;
249 } 264 }
250 265
251 // Media source pipelines can start immediately. 266 // Media source pipelines can start immediately.
252 if (BuildMediaSourceCollection(url, GetClient()->sourceURL(), proxy_, 267 if (!url.isEmpty() && url == GetClient()->sourceURL()) {
253 message_loop_factory_.get(), 268 chunk_demuxer_ = new media::ChunkDemuxer(
254 filter_collection_.get(), 269 BIND_TO_RENDER_LOOP(&WebMediaPlayerImpl::OnDemuxerOpened),
255 &decryptor_)) { 270 base::Bind(&OnDemuxerNeedKeyTrampoline,
Ami GONE FROM CHROMIUM 2012/09/12 18:45:34 why not BIND_TO_RENDER_LOOP for this as well?
acolwell GONE FROM CHROMIUM 2012/09/12 22:03:53 BindToLoop doesn't like the scoped_array<> in the
Ami GONE FROM CHROMIUM 2012/09/12 22:29:03 This isn't an array, it's a scoped_array. I'm surp
acolwell GONE FROM CHROMIUM 2012/09/13 00:16:23 I was too. I'll left it as is for now and will cha
271 main_loop_->message_loop_proxy(),
272 base::Bind(&WebMediaPlayerImpl::OnNeedKey, AsWeakPtr())));
273
274 BuildMediaSourceCollection(chunk_demuxer_,
275 message_loop_factory_.get(),
276 filter_collection_.get(),
277 &decryptor_);
256 supports_save_ = false; 278 supports_save_ = false;
257 StartPipeline(); 279 StartPipeline();
258 return; 280 return;
259 } 281 }
260 282
261 // Otherwise it's a regular request which requires resolving the URL first. 283 // Otherwise it's a regular request which requires resolving the URL first.
262 proxy_->set_data_source( 284 proxy_->set_data_source(
263 new BufferedDataSource(main_loop_, frame_, media_log_, 285 new BufferedDataSource(main_loop_, frame_, media_log_,
264 base::Bind(&WebMediaPlayerImpl::NotifyDownloading, 286 base::Bind(&WebMediaPlayerImpl::NotifyDownloading,
265 AsWeakPtr()))); 287 AsWeakPtr())));
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
315 DCHECK_EQ(main_loop_, MessageLoop::current()); 337 DCHECK_EQ(main_loop_, MessageLoop::current());
316 return supports_save_; 338 return supports_save_;
317 } 339 }
318 340
319 void WebMediaPlayerImpl::seek(float seconds) { 341 void WebMediaPlayerImpl::seek(float seconds) {
320 DCHECK_EQ(main_loop_, MessageLoop::current()); 342 DCHECK_EQ(main_loop_, MessageLoop::current());
321 343
322 if (starting_ || seeking_) { 344 if (starting_ || seeking_) {
323 pending_seek_ = true; 345 pending_seek_ = true;
324 pending_seek_seconds_ = seconds; 346 pending_seek_seconds_ = seconds;
325 proxy_->DemuxerCancelPendingSeek(); 347 if (chunk_demuxer_)
348 chunk_demuxer_->CancelPendingSeek();
326 return; 349 return;
327 } 350 }
328 351
329 media_log_->AddEvent(media_log_->CreateSeekEvent(seconds)); 352 media_log_->AddEvent(media_log_->CreateSeekEvent(seconds));
330 353
331 base::TimeDelta seek_time = ConvertSecondsToTimestamp(seconds); 354 base::TimeDelta seek_time = ConvertSecondsToTimestamp(seconds);
332 355
333 // Update our paused time. 356 // Update our paused time.
334 if (paused_) 357 if (paused_)
335 paused_time_ = seek_time; 358 paused_time_ = seek_time;
336 359
337 seeking_ = true; 360 seeking_ = true;
338 361
339 proxy_->DemuxerStartWaitingForSeek(); 362 if (chunk_demuxer_)
363 chunk_demuxer_->StartWaitingForSeek();
340 364
341 // Kick off the asynchronous seek! 365 // Kick off the asynchronous seek!
342 pipeline_->Seek( 366 pipeline_->Seek(
343 seek_time, 367 seek_time,
344 BIND_TO_RENDER_LOOP(&WebMediaPlayerImpl::OnPipelineSeek)); 368 BIND_TO_RENDER_LOOP(&WebMediaPlayerImpl::OnPipelineSeek));
345 } 369 }
346 370
347 void WebMediaPlayerImpl::setEndTime(float seconds) { 371 void WebMediaPlayerImpl::setEndTime(float seconds) {
348 DCHECK_EQ(main_loop_, MessageLoop::current()); 372 DCHECK_EQ(main_loop_, MessageLoop::current());
349 373
(...skipping 273 matching lines...) Expand 10 before | Expand all | Expand 10 after
623 WebKit::WebMediaPlayer::AddIdStatus WebMediaPlayerImpl::sourceAddId( 647 WebKit::WebMediaPlayer::AddIdStatus WebMediaPlayerImpl::sourceAddId(
624 const WebKit::WebString& id, 648 const WebKit::WebString& id,
625 const WebKit::WebString& type, 649 const WebKit::WebString& type,
626 const WebKit::WebVector<WebKit::WebString>& codecs) { 650 const WebKit::WebVector<WebKit::WebString>& codecs) {
627 DCHECK_EQ(main_loop_, MessageLoop::current()); 651 DCHECK_EQ(main_loop_, MessageLoop::current());
628 std::vector<std::string> new_codecs(codecs.size()); 652 std::vector<std::string> new_codecs(codecs.size());
629 for (size_t i = 0; i < codecs.size(); ++i) 653 for (size_t i = 0; i < codecs.size(); ++i)
630 new_codecs[i] = codecs[i].utf8().data(); 654 new_codecs[i] = codecs[i].utf8().data();
631 655
632 return static_cast<WebKit::WebMediaPlayer::AddIdStatus>( 656 return static_cast<WebKit::WebMediaPlayer::AddIdStatus>(
633 proxy_->DemuxerAddId(id.utf8().data(), type.utf8().data(), 657 chunk_demuxer_->AddId(id.utf8().data(), type.utf8().data(), new_codecs));
634 new_codecs));
635 } 658 }
636 659
637 bool WebMediaPlayerImpl::sourceRemoveId(const WebKit::WebString& id) { 660 bool WebMediaPlayerImpl::sourceRemoveId(const WebKit::WebString& id) {
638 DCHECK(!id.isEmpty()); 661 DCHECK(!id.isEmpty());
639 proxy_->DemuxerRemoveId(id.utf8().data()); 662 chunk_demuxer_->RemoveId(id.utf8().data());
640 return true; 663 return true;
641 } 664 }
642 665
643 WebKit::WebTimeRanges WebMediaPlayerImpl::sourceBuffered( 666 WebKit::WebTimeRanges WebMediaPlayerImpl::sourceBuffered(
644 const WebKit::WebString& id) { 667 const WebKit::WebString& id) {
645 return ConvertToWebTimeRanges(proxy_->DemuxerBufferedRange(id.utf8().data())); 668 return ConvertToWebTimeRanges(
669 chunk_demuxer_->GetBufferedRanges(id.utf8().data()));
646 } 670 }
647 671
648 bool WebMediaPlayerImpl::sourceAppend(const WebKit::WebString& id, 672 bool WebMediaPlayerImpl::sourceAppend(const WebKit::WebString& id,
649 const unsigned char* data, 673 const unsigned char* data,
650 unsigned length) { 674 unsigned length) {
651 DCHECK_EQ(main_loop_, MessageLoop::current()); 675 DCHECK_EQ(main_loop_, MessageLoop::current());
652 676
653 float old_duration = duration(); 677 float old_duration = duration();
654 if (!proxy_->DemuxerAppend(id.utf8().data(), data, length)) 678 if (!chunk_demuxer_->AppendData(id.utf8().data(), data, length))
655 return false; 679 return false;
656 680
657 if (old_duration != duration()) 681 if (old_duration != duration())
658 GetClient()->durationChanged(); 682 GetClient()->durationChanged();
659 683
660 return true; 684 return true;
661 } 685 }
662 686
663 bool WebMediaPlayerImpl::sourceAbort(const WebKit::WebString& id) { 687 bool WebMediaPlayerImpl::sourceAbort(const WebKit::WebString& id) {
664 proxy_->DemuxerAbort(id.utf8().data()); 688 chunk_demuxer_->Abort(id.utf8().data());
665 return true; 689 return true;
666 } 690 }
667 691
668 void WebMediaPlayerImpl::sourceSetDuration(double new_duration) { 692 void WebMediaPlayerImpl::sourceSetDuration(double new_duration) {
669 if (static_cast<double>(duration()) == new_duration) 693 if (static_cast<double>(duration()) == new_duration)
670 return; 694 return;
671 695
672 proxy_->DemuxerSetDuration( 696 chunk_demuxer_->SetDuration(
673 base::TimeDelta::FromMicroseconds( 697 base::TimeDelta::FromMicroseconds(
674 new_duration * base::Time::kMicrosecondsPerSecond)); 698 new_duration * base::Time::kMicrosecondsPerSecond));
675 GetClient()->durationChanged(); 699 GetClient()->durationChanged();
676 } 700 }
677 701
678 void WebMediaPlayerImpl::sourceEndOfStream( 702 void WebMediaPlayerImpl::sourceEndOfStream(
679 WebMediaPlayer::EndOfStreamStatus status) { 703 WebMediaPlayer::EndOfStreamStatus status) {
680 DCHECK_EQ(main_loop_, MessageLoop::current()); 704 DCHECK_EQ(main_loop_, MessageLoop::current());
681 media::PipelineStatus pipeline_status = media::PIPELINE_OK; 705 media::PipelineStatus pipeline_status = media::PIPELINE_OK;
682 706
683 switch (status) { 707 switch (status) {
684 case WebMediaPlayer::EndOfStreamStatusNoError: 708 case WebMediaPlayer::EndOfStreamStatusNoError:
685 break; 709 break;
686 case WebMediaPlayer::EndOfStreamStatusNetworkError: 710 case WebMediaPlayer::EndOfStreamStatusNetworkError:
687 pipeline_status = media::PIPELINE_ERROR_NETWORK; 711 pipeline_status = media::PIPELINE_ERROR_NETWORK;
688 break; 712 break;
689 case WebMediaPlayer::EndOfStreamStatusDecodeError: 713 case WebMediaPlayer::EndOfStreamStatusDecodeError:
690 pipeline_status = media::PIPELINE_ERROR_DECODE; 714 pipeline_status = media::PIPELINE_ERROR_DECODE;
691 break; 715 break;
692 default: 716 default:
693 NOTIMPLEMENTED(); 717 NOTIMPLEMENTED();
694 } 718 }
695 719
696 float old_duration = duration(); 720 float old_duration = duration();
697 proxy_->DemuxerEndOfStream(pipeline_status); 721 chunk_demuxer_->EndOfStream(pipeline_status);
698 722
699 if (old_duration != duration()) 723 if (old_duration != duration())
700 GetClient()->durationChanged(); 724 GetClient()->durationChanged();
701 } 725 }
702 726
703 bool WebMediaPlayerImpl::sourceSetTimestampOffset(const WebKit::WebString& id, 727 bool WebMediaPlayerImpl::sourceSetTimestampOffset(const WebKit::WebString& id,
704 double offset) { 728 double offset) {
705 base::TimeDelta time_offset = base::TimeDelta::FromMicroseconds( 729 base::TimeDelta time_offset = base::TimeDelta::FromMicroseconds(
706 offset * base::Time::kMicrosecondsPerSecond); 730 offset * base::Time::kMicrosecondsPerSecond);
707 return proxy_->DemuxerSetTimestampOffset(id.utf8().data(), time_offset); 731 return chunk_demuxer_->SetTimestampOffset(id.utf8().data(), time_offset);
708 } 732 }
709 733
710 WebKit::WebMediaPlayer::MediaKeyException 734 WebKit::WebMediaPlayer::MediaKeyException
711 WebMediaPlayerImpl::generateKeyRequest(const WebString& key_system, 735 WebMediaPlayerImpl::generateKeyRequest(const WebString& key_system,
712 const unsigned char* init_data, 736 const unsigned char* init_data,
713 unsigned init_data_length) { 737 unsigned init_data_length) {
714 if (!IsSupportedKeySystem(key_system)) 738 if (!IsSupportedKeySystem(key_system))
715 return WebKit::WebMediaPlayer::MediaKeyExceptionKeySystemNotSupported; 739 return WebKit::WebMediaPlayer::MediaKeyExceptionKeySystemNotSupported;
716 740
717 // We do not support run-time switching between key systems for now. 741 // We do not support run-time switching between key systems for now.
(...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after
884 SetReadyState(WebMediaPlayer::ReadyStateHaveEnoughData); 908 SetReadyState(WebMediaPlayer::ReadyStateHaveEnoughData);
885 break; 909 break;
886 } 910 }
887 911
888 // Repaint to trigger UI update. 912 // Repaint to trigger UI update.
889 Repaint(); 913 Repaint();
890 } 914 }
891 915
892 void WebMediaPlayerImpl::OnDemuxerOpened() { 916 void WebMediaPlayerImpl::OnDemuxerOpened() {
893 DCHECK_EQ(main_loop_, MessageLoop::current()); 917 DCHECK_EQ(main_loop_, MessageLoop::current());
894
895 GetClient()->sourceOpened(); 918 GetClient()->sourceOpened();
896 } 919 }
897 920
898 void WebMediaPlayerImpl::OnKeyAdded(const std::string& key_system, 921 void WebMediaPlayerImpl::OnKeyAdded(const std::string& key_system,
899 const std::string& session_id) { 922 const std::string& session_id) {
900 DCHECK_EQ(main_loop_, MessageLoop::current()); 923 DCHECK_EQ(main_loop_, MessageLoop::current());
901 924
902 GetClient()->keyAdded(WebString::fromUTF8(key_system), 925 GetClient()->keyAdded(WebString::fromUTF8(key_system),
903 WebString::fromUTF8(session_id)); 926 WebString::fromUTF8(session_id));
904 } 927 }
(...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after
1020 GetClient()->readyStateChanged(); 1043 GetClient()->readyStateChanged();
1021 } 1044 }
1022 1045
1023 void WebMediaPlayerImpl::Destroy() { 1046 void WebMediaPlayerImpl::Destroy() {
1024 DCHECK_EQ(main_loop_, MessageLoop::current()); 1047 DCHECK_EQ(main_loop_, MessageLoop::current());
1025 1048
1026 // Tell the data source to abort any pending reads so that the pipeline is 1049 // Tell the data source to abort any pending reads so that the pipeline is
1027 // not blocked when issuing stop commands to the other filters. 1050 // not blocked when issuing stop commands to the other filters.
1028 if (proxy_) { 1051 if (proxy_) {
1029 proxy_->AbortDataSource(); 1052 proxy_->AbortDataSource();
1030 proxy_->DemuxerShutdown(); 1053 if (chunk_demuxer_) {
1054 chunk_demuxer_->Shutdown();
1055 chunk_demuxer_ = NULL;
1056 }
1031 } 1057 }
1032 1058
1033 // Make sure to kill the pipeline so there's no more media threads running. 1059 // Make sure to kill the pipeline so there's no more media threads running.
1034 // Note: stopping the pipeline might block for a long time. 1060 // Note: stopping the pipeline might block for a long time.
1035 base::WaitableEvent waiter(false, false); 1061 base::WaitableEvent waiter(false, false);
1036 pipeline_->Stop(base::Bind( 1062 pipeline_->Stop(base::Bind(
1037 &base::WaitableEvent::Signal, base::Unretained(&waiter))); 1063 &base::WaitableEvent::Signal, base::Unretained(&waiter)));
1038 waiter.Wait(); 1064 waiter.Wait();
1039 1065
1040 // Let V8 know we are not using extra resources anymore. 1066 // Let V8 know we are not using extra resources anymore.
(...skipping 22 matching lines...) Expand all
1063 return audio_source_provider_; 1089 return audio_source_provider_;
1064 } 1090 }
1065 1091
1066 void WebMediaPlayerImpl::IncrementExternallyAllocatedMemory() { 1092 void WebMediaPlayerImpl::IncrementExternallyAllocatedMemory() {
1067 DCHECK_EQ(main_loop_, MessageLoop::current()); 1093 DCHECK_EQ(main_loop_, MessageLoop::current());
1068 incremented_externally_allocated_memory_ = true; 1094 incremented_externally_allocated_memory_ = true;
1069 v8::V8::AdjustAmountOfExternalAllocatedMemory(kPlayerExtraMemory); 1095 v8::V8::AdjustAmountOfExternalAllocatedMemory(kPlayerExtraMemory);
1070 } 1096 }
1071 1097
1072 } // namespace webkit_media 1098 } // namespace webkit_media
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698