| Index: chrome/renderer/media/cast_session_delegate.cc
|
| diff --git a/chrome/renderer/media/cast_session_delegate.cc b/chrome/renderer/media/cast_session_delegate.cc
|
| index 11f39185606a9f68ac51e772f9816880c56eb54f..82e3f1d182501046c32180659b7977a3381da1c9 100644
|
| --- a/chrome/renderer/media/cast_session_delegate.cc
|
| +++ b/chrome/renderer/media/cast_session_delegate.cc
|
| @@ -43,8 +43,7 @@ const int kMaxAudioEventEntries = kMaxSerializedBytes / 75;
|
| } // namespace
|
|
|
| CastSessionDelegate::CastSessionDelegate()
|
| - : transport_configured_(false),
|
| - io_message_loop_proxy_(
|
| + : io_message_loop_proxy_(
|
| content::RenderThread::Get()->GetIOMessageLoopProxy()),
|
| weak_factory_(this) {
|
| DCHECK(io_message_loop_proxy_);
|
| @@ -63,56 +62,80 @@ CastSessionDelegate::~CastSessionDelegate() {
|
| }
|
| }
|
|
|
| -void CastSessionDelegate::Initialize(
|
| - const media::cast::CastLoggingConfig& logging_config) {
|
| - if (cast_environment_)
|
| - return; // Already initialized.
|
| -
|
| - // CastSender uses the renderer's IO thread as the main thread. This reduces
|
| - // thread hopping for incoming video frames and outgoing network packets.
|
| - // There's no need to decode so no thread assigned for decoding.
|
| - cast_environment_ = new CastEnvironment(
|
| - scoped_ptr<base::TickClock>(new base::DefaultTickClock()).Pass(),
|
| - base::MessageLoopProxy::current(),
|
| - g_cast_threads.Get().GetAudioEncodeMessageLoopProxy(),
|
| - NULL,
|
| - g_cast_threads.Get().GetVideoEncodeMessageLoopProxy(),
|
| - NULL,
|
| - base::MessageLoopProxy::current(),
|
| - logging_config);
|
| -}
|
| -
|
| void CastSessionDelegate::StartAudio(
|
| const AudioSenderConfig& config,
|
| - const FrameInputAvailableCallback& callback) {
|
| + const AudioFrameInputAvailableCallback& callback) {
|
| DCHECK(io_message_loop_proxy_->BelongsToCurrentThread());
|
|
|
| - audio_config_.reset(new AudioSenderConfig(config));
|
| - video_frame_input_available_callback_ = callback;
|
| - StartSendingInternal();
|
| + audio_frame_input_available_callback_ = callback;
|
| + media::cast::transport::CastTransportAudioConfig transport_config;
|
| + transport_config.base.ssrc = config.sender_ssrc;
|
| + transport_config.codec = config.codec;
|
| + transport_config.base.rtp_config = config.rtp_config;
|
| + transport_config.frequency = config.frequency;
|
| + transport_config.channels = config.channels;
|
| + cast_transport_->InitializeAudio(transport_config);
|
| + cast_sender_->InitializeAudio(
|
| + config,
|
| + base::Bind(&CastSessionDelegate::InitializationResult,
|
| + weak_factory_.GetWeakPtr()));
|
| }
|
|
|
| void CastSessionDelegate::StartVideo(
|
| const VideoSenderConfig& config,
|
| - const FrameInputAvailableCallback& callback) {
|
| + const VideoFrameInputAvailableCallback& callback) {
|
| DCHECK(io_message_loop_proxy_->BelongsToCurrentThread());
|
| - audio_frame_input_available_callback_ = callback;
|
| + video_frame_input_available_callback_ = callback;
|
|
|
| - video_config_.reset(new VideoSenderConfig(config));
|
| - StartSendingInternal();
|
| + media::cast::transport::CastTransportVideoConfig transport_config;
|
| + transport_config.base.ssrc = config.sender_ssrc;
|
| + transport_config.codec = config.codec;
|
| + transport_config.base.rtp_config = config.rtp_config;
|
| + cast_transport_->InitializeVideo(transport_config);
|
| + // TODO(mikhal): Pass in a valid GpuVideoAcceleratorFactories to support
|
| + // hardware video encoding.
|
| + cast_sender_->InitializeVideo(
|
| + config,
|
| + base::Bind(&CastSessionDelegate::InitializationResult,
|
| + weak_factory_.GetWeakPtr()),
|
| + NULL /* GPU*/);
|
| }
|
|
|
| void CastSessionDelegate::StartUDP(const net::IPEndPoint& local_endpoint,
|
| const net::IPEndPoint& remote_endpoint) {
|
| DCHECK(io_message_loop_proxy_->BelongsToCurrentThread());
|
| - transport_configured_ = true;
|
| - local_endpoint_ = local_endpoint;
|
| - remote_endpoint_ = remote_endpoint;
|
| - StartSendingInternal();
|
| +
|
| + // CastSender uses the renderer's IO thread as the main thread. This reduces
|
| + // thread hopping for incoming video frames and outgoing network packets.
|
| + // There's no need to decode so no thread assigned for decoding.
|
| + cast_environment_ = new CastEnvironment(
|
| + scoped_ptr<base::TickClock>(new base::DefaultTickClock()).Pass(),
|
| + base::MessageLoopProxy::current(),
|
| + g_cast_threads.Get().GetAudioEncodeMessageLoopProxy(),
|
| + NULL,
|
| + g_cast_threads.Get().GetVideoEncodeMessageLoopProxy(),
|
| + NULL,
|
| + base::MessageLoopProxy::current(),
|
| + media::cast::GetLoggingConfigWithRawEventsAndStatsEnabled());
|
| +
|
| + // Logging: enable raw events and stats collection.
|
| + media::cast::CastLoggingConfig logging_config =
|
| + media::cast::GetLoggingConfigWithRawEventsAndStatsEnabled();
|
| + // Rationale for using unretained: The callback cannot be called after the
|
| + // destruction of CastTransportSenderIPC, and they both share the same thread.
|
| + cast_transport_.reset(new CastTransportSenderIPC(
|
| + local_endpoint,
|
| + remote_endpoint,
|
| + base::Bind(&CastSessionDelegate::StatusNotificationCB,
|
| + base::Unretained(this)),
|
| + logging_config,
|
| + base::Bind(&CastSessionDelegate::LogRawEvents, base::Unretained(this))));
|
| +
|
| + cast_sender_ = CastSender::Create(cast_environment_, cast_transport_.get());
|
| + cast_transport_->SetPacketReceiver(cast_sender_->packet_receiver());
|
| }
|
|
|
| -void CastSessionDelegate::ToggleLogging(bool is_audio,
|
| - bool enable) {
|
| +void CastSessionDelegate::ToggleLogging(bool is_audio, bool enable) {
|
| DCHECK(io_message_loop_proxy_->BelongsToCurrentThread());
|
| if (enable) {
|
| if (is_audio) {
|
| @@ -148,11 +171,12 @@ void CastSessionDelegate::ToggleLogging(bool is_audio,
|
| }
|
|
|
| void CastSessionDelegate::GetEventLogsAndReset(
|
| - bool is_audio, const EventLogsCallback& callback) {
|
| + bool is_audio,
|
| + const EventLogsCallback& callback) {
|
| DCHECK(io_message_loop_proxy_->BelongsToCurrentThread());
|
|
|
| - media::cast::EncodingEventSubscriber* subscriber = is_audio ?
|
| - audio_event_subscriber_.get() : video_event_subscriber_.get();
|
| + media::cast::EncodingEventSubscriber* subscriber =
|
| + is_audio ? audio_event_subscriber_.get() : video_event_subscriber_.get();
|
| if (!subscriber) {
|
| callback.Run(make_scoped_ptr(new std::string).Pass());
|
| return;
|
| @@ -202,73 +226,20 @@ void CastSessionDelegate::StatusNotificationCB(
|
| // TODO(hubbe): Call javascript UDPTransport error function.
|
| }
|
|
|
| -void CastSessionDelegate::StartSendingInternal() {
|
| - DCHECK(io_message_loop_proxy_->BelongsToCurrentThread());
|
| -
|
| - // No transport, wait.
|
| - if (!transport_configured_)
|
| - return;
|
| -
|
| - // No audio or video, wait.
|
| - if (!audio_config_ || !video_config_)
|
| - return;
|
| -
|
| - // Logging: enable raw events and stats collection.
|
| - media::cast::CastLoggingConfig logging_config =
|
| - media::cast::GetLoggingConfigWithRawEventsAndStatsEnabled();
|
| - Initialize(logging_config);
|
| -
|
| - // Rationale for using unretained: The callback cannot be called after the
|
| - // destruction of CastTransportSenderIPC, and they both share the same thread.
|
| - cast_transport_.reset(new CastTransportSenderIPC(
|
| - local_endpoint_,
|
| - remote_endpoint_,
|
| - base::Bind(&CastSessionDelegate::StatusNotificationCB,
|
| - base::Unretained(this)),
|
| - logging_config,
|
| - base::Bind(&CastSessionDelegate::LogRawEvents,
|
| - base::Unretained(this))));
|
| -
|
| - // TODO(hubbe): set config.aes_key and config.aes_iv_mask.
|
| - if (audio_config_) {
|
| - media::cast::transport::CastTransportAudioConfig config;
|
| - config.base.ssrc = audio_config_->sender_ssrc;
|
| - config.codec = audio_config_->codec;
|
| - config.base.rtp_config = audio_config_->rtp_config;
|
| - config.frequency = audio_config_->frequency;
|
| - config.channels = audio_config_->channels;
|
| - cast_transport_->InitializeAudio(config);
|
| - }
|
| - if (video_config_) {
|
| - media::cast::transport::CastTransportVideoConfig config;
|
| - config.base.ssrc = video_config_->sender_ssrc;
|
| - config.codec = video_config_->codec;
|
| - config.base.rtp_config = video_config_->rtp_config;
|
| - cast_transport_->InitializeVideo(config);
|
| - }
|
| -
|
| - cast_sender_.reset(CastSender::CreateCastSender(
|
| - cast_environment_,
|
| - audio_config_.get(),
|
| - video_config_.get(),
|
| - NULL, // GPU.
|
| - base::Bind(&CastSessionDelegate::InitializationResult,
|
| - weak_factory_.GetWeakPtr()),
|
| - cast_transport_.get()));
|
| - cast_transport_->SetPacketReceiver(cast_sender_->packet_receiver());
|
| -}
|
| -
|
| void CastSessionDelegate::InitializationResult(
|
| media::cast::CastInitializationStatus result) const {
|
| DCHECK(cast_sender_);
|
|
|
| // TODO(pwestin): handle the error codes.
|
| - if (result == media::cast::STATUS_INITIALIZED) {
|
| + if (result == media::cast::STATUS_AUDIO_INITIALIZED) {
|
| if (!audio_frame_input_available_callback_.is_null()) {
|
| - audio_frame_input_available_callback_.Run(cast_sender_->frame_input());
|
| + audio_frame_input_available_callback_.Run(
|
| + cast_sender_->audio_frame_input());
|
| }
|
| + } else if (result == media::cast::STATUS_VIDEO_INITIALIZED) {
|
| if (!video_frame_input_available_callback_.is_null()) {
|
| - video_frame_input_available_callback_.Run(cast_sender_->frame_input());
|
| + video_frame_input_available_callback_.Run(
|
| + cast_sender_->video_frame_input());
|
| }
|
| }
|
| }
|
|
|