| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 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 | 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 // Simulate end to end streaming. | 5 // Simulate end to end streaming. |
| 6 // | 6 // |
| 7 // Input: | 7 // Input: |
| 8 // --source= | 8 // --source= |
| 9 // WebM used as the source of video and audio frames. | 9 // WebM used as the source of video and audio frames. |
| 10 // --output= | 10 // --output= |
| (...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 107 const std::string as_str = | 107 const std::string as_str = |
| 108 base::CommandLine::ForCurrentProcess()->GetSwitchValueASCII(switch_name); | 108 base::CommandLine::ForCurrentProcess()->GetSwitchValueASCII(switch_name); |
| 109 if (as_str.empty()) | 109 if (as_str.empty()) |
| 110 return default_value; | 110 return default_value; |
| 111 int as_int; | 111 int as_int; |
| 112 CHECK(base::StringToInt(as_str, &as_int)); | 112 CHECK(base::StringToInt(as_str, &as_int)); |
| 113 CHECK_GT(as_int, 0); | 113 CHECK_GT(as_int, 0); |
| 114 return as_int; | 114 return as_int; |
| 115 } | 115 } |
| 116 | 116 |
| 117 void UpdateCastTransportStatus(CastTransportStatus status) { | |
| 118 LOG(INFO) << "Cast transport status: " << status; | |
| 119 } | |
| 120 | |
| 121 void LogAudioOperationalStatus(OperationalStatus status) { | 117 void LogAudioOperationalStatus(OperationalStatus status) { |
| 122 LOG(INFO) << "Audio status: " << status; | 118 LOG(INFO) << "Audio status: " << status; |
| 123 } | 119 } |
| 124 | 120 |
| 125 void LogVideoOperationalStatus(OperationalStatus status) { | 121 void LogVideoOperationalStatus(OperationalStatus status) { |
| 126 LOG(INFO) << "Video status: " << status; | 122 LOG(INFO) << "Video status: " << status; |
| 127 } | 123 } |
| 128 | 124 |
| 125 struct PacketProxy { |
| 126 PacketProxy() : receiver(NULL) {} |
| 127 void ReceivePacket(scoped_ptr<Packet> packet) { |
| 128 if (receiver) |
| 129 receiver->ReceivePacket(std::move(packet)); |
| 130 } |
| 131 CastReceiver* receiver; |
| 132 }; |
| 133 |
| 134 class TransportClient : public CastTransportSender::Client { |
| 135 public: |
| 136 TransportClient(LogEventDispatcher* log_event_dispatcher, |
| 137 PacketProxy* packet_proxy) |
| 138 : log_event_dispatcher_(log_event_dispatcher), |
| 139 packet_proxy_(packet_proxy) {} |
| 140 |
| 141 void OnStatusChanged(CastTransportStatus status) final { |
| 142 LOG(INFO) << "Cast transport status: " << status; |
| 143 }; |
| 144 void OnLoggingEventsReceived( |
| 145 scoped_ptr<std::vector<FrameEvent>> frame_events, |
| 146 scoped_ptr<std::vector<PacketEvent>> packet_events) final { |
| 147 DCHECK(log_event_dispatcher_); |
| 148 log_event_dispatcher_->DispatchBatchOfEvents(std::move(frame_events), |
| 149 std::move(packet_events)); |
| 150 }; |
| 151 void ProcessRtpPacket(scoped_ptr<Packet> packet) final { |
| 152 if (packet_proxy_) |
| 153 packet_proxy_->ReceivePacket(std::move(packet)); |
| 154 }; |
| 155 |
| 156 private: |
| 157 LogEventDispatcher* const log_event_dispatcher_; // Not owned by this class. |
| 158 PacketProxy* const packet_proxy_; // Not owned by this class. |
| 159 |
| 160 DISALLOW_COPY_AND_ASSIGN(TransportClient); |
| 161 }; |
| 162 |
| 129 // Maintains a queue of encoded video frames. | 163 // Maintains a queue of encoded video frames. |
| 130 // This works by tracking FRAME_CAPTURE_END and FRAME_ENCODED events. | 164 // This works by tracking FRAME_CAPTURE_END and FRAME_ENCODED events. |
| 131 // If a video frame is detected to be encoded it transfers a frame | 165 // If a video frame is detected to be encoded it transfers a frame |
| 132 // from FakeMediaSource to its internal queue. Otherwise it drops a | 166 // from FakeMediaSource to its internal queue. Otherwise it drops a |
| 133 // frame from FakeMediaSource. | 167 // frame from FakeMediaSource. |
| 134 class EncodedVideoFrameTracker : public RawEventSubscriber { | 168 class EncodedVideoFrameTracker : public RawEventSubscriber { |
| 135 public: | 169 public: |
| 136 EncodedVideoFrameTracker(FakeMediaSource* media_source) | 170 EncodedVideoFrameTracker(FakeMediaSource* media_source) |
| 137 : media_source_(media_source), | 171 : media_source_(media_source), |
| 138 last_frame_event_type_(UNKNOWN) {} | 172 last_frame_event_type_(UNKNOWN) {} |
| (...skipping 199 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 338 video_sender_config.max_playout_delay = | 372 video_sender_config.max_playout_delay = |
| 339 audio_sender_config.max_playout_delay; | 373 audio_sender_config.max_playout_delay; |
| 340 video_sender_config.max_frame_rate = GetIntegerSwitchValue(kMaxFrameRate, 30); | 374 video_sender_config.max_frame_rate = GetIntegerSwitchValue(kMaxFrameRate, 30); |
| 341 | 375 |
| 342 // Video receiver config. | 376 // Video receiver config. |
| 343 FrameReceiverConfig video_receiver_config = | 377 FrameReceiverConfig video_receiver_config = |
| 344 GetDefaultVideoReceiverConfig(); | 378 GetDefaultVideoReceiverConfig(); |
| 345 video_receiver_config.rtp_max_delay_ms = | 379 video_receiver_config.rtp_max_delay_ms = |
| 346 video_sender_config.max_playout_delay.InMilliseconds(); | 380 video_sender_config.max_playout_delay.InMilliseconds(); |
| 347 | 381 |
| 348 // Loopback transport. | 382 // Loopback transport. Owned by CastTransportSender. |
| 349 LoopBackTransport receiver_to_sender(receiver_env); | 383 LoopBackTransport* receiver_to_sender = new LoopBackTransport(receiver_env); |
| 350 LoopBackTransport sender_to_receiver(sender_env); | 384 LoopBackTransport* sender_to_receiver = new LoopBackTransport(sender_env); |
| 351 | |
| 352 struct PacketProxy { | |
| 353 PacketProxy() : receiver(NULL) {} | |
| 354 void ReceivePacket(scoped_ptr<Packet> packet) { | |
| 355 if (receiver) | |
| 356 receiver->ReceivePacket(std::move(packet)); | |
| 357 } | |
| 358 CastReceiver* receiver; | |
| 359 }; | |
| 360 | 385 |
| 361 PacketProxy packet_proxy; | 386 PacketProxy packet_proxy; |
| 362 | 387 |
| 363 // Cast receiver. | 388 // Cast receiver. |
| 364 scoped_ptr<CastTransportSender> transport_receiver( | 389 scoped_ptr<CastTransportSender> transport_receiver( |
| 365 new CastTransportSenderImpl( | 390 new CastTransportSenderImpl( |
| 366 nullptr, &testing_clock, net::IPEndPoint(), net::IPEndPoint(), | 391 &testing_clock, base::TimeDelta::FromSeconds(1), |
| 367 make_scoped_ptr(new base::DictionaryValue), | 392 make_scoped_ptr( |
| 368 base::Bind(&UpdateCastTransportStatus), | 393 new TransportClient(receiver_env->logger(), &packet_proxy)), |
| 369 base::Bind(&LogEventDispatcher::DispatchBatchOfEvents, | 394 make_scoped_ptr(receiver_to_sender), task_runner)); |
| 370 base::Unretained(receiver_env->logger())), | |
| 371 base::TimeDelta::FromSeconds(1), task_runner, | |
| 372 base::Bind(&PacketProxy::ReceivePacket, | |
| 373 base::Unretained(&packet_proxy)), | |
| 374 &receiver_to_sender)); | |
| 375 scoped_ptr<CastReceiver> cast_receiver( | 395 scoped_ptr<CastReceiver> cast_receiver( |
| 376 CastReceiver::Create(receiver_env, | 396 CastReceiver::Create(receiver_env, |
| 377 audio_receiver_config, | 397 audio_receiver_config, |
| 378 video_receiver_config, | 398 video_receiver_config, |
| 379 transport_receiver.get())); | 399 transport_receiver.get())); |
| 380 | 400 |
| 381 packet_proxy.receiver = cast_receiver.get(); | 401 packet_proxy.receiver = cast_receiver.get(); |
| 382 | 402 |
| 383 // Cast sender and transport sender. | 403 // Cast sender and transport sender. |
| 384 scoped_ptr<CastTransportSender> transport_sender(new CastTransportSenderImpl( | 404 scoped_ptr<CastTransportSender> transport_sender(new CastTransportSenderImpl( |
| 385 nullptr, &testing_clock, net::IPEndPoint(), net::IPEndPoint(), | 405 &testing_clock, base::TimeDelta::FromSeconds(1), |
| 386 make_scoped_ptr(new base::DictionaryValue), | 406 make_scoped_ptr(new TransportClient(sender_env->logger(), nullptr)), |
| 387 base::Bind(&UpdateCastTransportStatus), | 407 make_scoped_ptr(sender_to_receiver), task_runner)); |
| 388 base::Bind(&LogEventDispatcher::DispatchBatchOfEvents, | |
| 389 base::Unretained(sender_env->logger())), | |
| 390 base::TimeDelta::FromSeconds(1), task_runner, PacketReceiverCallback(), | |
| 391 &sender_to_receiver)); | |
| 392 scoped_ptr<CastSender> cast_sender( | 408 scoped_ptr<CastSender> cast_sender( |
| 393 CastSender::Create(sender_env, transport_sender.get())); | 409 CastSender::Create(sender_env, transport_sender.get())); |
| 394 | 410 |
| 395 // Initialize network simulation model. | 411 // Initialize network simulation model. |
| 396 const bool use_network_simulation = | 412 const bool use_network_simulation = |
| 397 model.type() == media::cast::proto::INTERRUPTED_POISSON_PROCESS; | 413 model.type() == media::cast::proto::INTERRUPTED_POISSON_PROCESS; |
| 398 scoped_ptr<test::InterruptedPoissonProcess> ipp; | 414 scoped_ptr<test::InterruptedPoissonProcess> ipp; |
| 399 if (use_network_simulation) { | 415 if (use_network_simulation) { |
| 400 LOG(INFO) << "Running Poisson based network simulation."; | 416 LOG(INFO) << "Running Poisson based network simulation."; |
| 401 const IPPModel& ipp_model = model.ipp(); | 417 const IPPModel& ipp_model = model.ipp(); |
| 402 std::vector<double> average_rates(ipp_model.average_rate_size()); | 418 std::vector<double> average_rates(ipp_model.average_rate_size()); |
| 403 std::copy(ipp_model.average_rate().begin(), | 419 std::copy(ipp_model.average_rate().begin(), |
| 404 ipp_model.average_rate().end(), | 420 ipp_model.average_rate().end(), |
| 405 average_rates.begin()); | 421 average_rates.begin()); |
| 406 ipp.reset(new test::InterruptedPoissonProcess( | 422 ipp.reset(new test::InterruptedPoissonProcess( |
| 407 average_rates, | 423 average_rates, |
| 408 ipp_model.coef_burstiness(), ipp_model.coef_variance(), 0)); | 424 ipp_model.coef_burstiness(), ipp_model.coef_variance(), 0)); |
| 409 receiver_to_sender.Initialize(ipp->NewBuffer(128 * 1024), | 425 receiver_to_sender->Initialize(ipp->NewBuffer(128 * 1024), |
| 410 transport_sender->PacketReceiverForTesting(), | 426 transport_sender->PacketReceiverForTesting(), |
| 411 task_runner, &testing_clock); | 427 task_runner, &testing_clock); |
| 412 sender_to_receiver.Initialize( | 428 sender_to_receiver->Initialize( |
| 413 ipp->NewBuffer(128 * 1024), | 429 ipp->NewBuffer(128 * 1024), |
| 414 transport_receiver->PacketReceiverForTesting(), task_runner, | 430 transport_receiver->PacketReceiverForTesting(), task_runner, |
| 415 &testing_clock); | 431 &testing_clock); |
| 416 } else { | 432 } else { |
| 417 LOG(INFO) << "No network simulation."; | 433 LOG(INFO) << "No network simulation."; |
| 418 receiver_to_sender.Initialize( | 434 receiver_to_sender->Initialize(scoped_ptr<test::PacketPipe>(), |
| 419 scoped_ptr<test::PacketPipe>(), | 435 transport_sender->PacketReceiverForTesting(), |
| 420 transport_sender->PacketReceiverForTesting(), | 436 task_runner, &testing_clock); |
| 421 task_runner, &testing_clock); | 437 sender_to_receiver->Initialize( |
| 422 sender_to_receiver.Initialize( | |
| 423 scoped_ptr<test::PacketPipe>(), | 438 scoped_ptr<test::PacketPipe>(), |
| 424 transport_receiver->PacketReceiverForTesting(), task_runner, | 439 transport_receiver->PacketReceiverForTesting(), task_runner, |
| 425 &testing_clock); | 440 &testing_clock); |
| 426 } | 441 } |
| 427 | 442 |
| 428 // Initialize a fake media source and a tracker to encoded video frames. | 443 // Initialize a fake media source and a tracker to encoded video frames. |
| 429 const bool quality_test = !metrics_output_path.empty(); | 444 const bool quality_test = !metrics_output_path.empty(); |
| 430 FakeMediaSource media_source(task_runner, | 445 FakeMediaSource media_source(task_runner, |
| 431 &testing_clock, | 446 &testing_clock, |
| 432 audio_sender_config, | 447 audio_sender_config, |
| (...skipping 285 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 718 values.SetString("sim-id", sim_id); | 733 values.SetString("sim-id", sim_id); |
| 719 | 734 |
| 720 std::string extra_data; | 735 std::string extra_data; |
| 721 base::JSONWriter::Write(values, &extra_data); | 736 base::JSONWriter::Write(values, &extra_data); |
| 722 | 737 |
| 723 // Run. | 738 // Run. |
| 724 media::cast::RunSimulation(source_path, log_output_path, metrics_output_path, | 739 media::cast::RunSimulation(source_path, log_output_path, metrics_output_path, |
| 725 yuv_output_path, extra_data, model); | 740 yuv_output_path, extra_data, model); |
| 726 return 0; | 741 return 0; |
| 727 } | 742 } |
| OLD | NEW |