Upstream version 5.34.104.0
[platform/framework/web/crosswalk.git] / src / media / cast / transport / rtp_sender / rtp_sender.cc
index 64ef769..7bcfbca 100644 (file)
@@ -14,43 +14,54 @@ namespace media {
 namespace cast {
 namespace transport {
 
-RtpSender::RtpSender(base::TickClock* clock,
-                     const CastTransportConfig& config,
-                     bool is_audio,
-                     PacedSender* const transport)
+// Schedule the RTP statistics callback every 33mS. As this interval affects the
+// time offset of the render and playout times, we want it in the same ball park
+// as the frame rate.
+static const int kStatsCallbackIntervalMs = 33;
+
+RtpSender::RtpSender(
+    base::TickClock* clock,
+    const CastTransportConfig& config,
+    bool is_audio,
+    const scoped_refptr<base::TaskRunner>& transport_task_runner,
+    PacedSender* const transport)
     : config_(),
-      transport_(transport) {
+      transport_(transport),
+      stats_callback_(),
+      transport_task_runner_(transport_task_runner) {
   // Store generic cast config and create packetizer config.
   if (is_audio) {
-    storage_.reset(new PacketStorage(clock, config.audio_rtp_history_ms));
+    storage_.reset(
+        new PacketStorage(clock, config.audio_rtp_config.history_ms));
     config_.audio = true;
     config_.ssrc = config.audio_ssrc;
-    config_.payload_type = config.audio_rtp_payload_type;
+    config_.payload_type = config.audio_rtp_config.payload_type;
     config_.frequency = config.audio_frequency;
     config_.audio_codec = config.audio_codec;
   } else {
-    storage_.reset(new PacketStorage(clock, config.audio_rtp_history_ms));
+    storage_.reset(
+        new PacketStorage(clock, config.audio_rtp_config.history_ms));
     config_.audio = false;
     config_.ssrc = config.video_ssrc;
-    config_.payload_type = config.video_rtp_payload_type;
+    config_.payload_type = config.video_rtp_config.payload_type;
     config_.frequency = kVideoFrequency;
     config_.video_codec = config.video_codec;
   }
   // Randomly set start values.
   config_.sequence_number = base::RandInt(0, 65535);
-  config_.rtp_timestamp = base::RandInt(0, 65535);
-  config_.rtp_timestamp += base::RandInt(0, 65535) << 16;
-  packetizer_.reset(new RtpPacketizer(transport, storage_.get(), config_));
+  packetizer_.reset(
+      new RtpPacketizer(transport, storage_.get(), config_));
 }
 
 RtpSender::~RtpSender() {}
 
 void RtpSender::IncomingEncodedVideoFrame(const EncodedVideoFrame* video_frame,
-    const base::TimeTicks& capture_time) {
+                                          const base::TimeTicks& capture_time) {
   packetizer_->IncomingEncodedVideoFrame(video_frame, capture_time);
 }
 
-void RtpSender::IncomingEncodedAudioFrame(const EncodedAudioFrame* audio_frame,
+void RtpSender::IncomingEncodedAudioFrame(
+    const EncodedAudioFrame* audio_frame,
     const base::TimeTicks& recorded_time) {
   packetizer_->IncomingEncodedAudioFrame(audio_frame, recorded_time);
 }
@@ -59,8 +70,9 @@ void RtpSender::ResendPackets(
     const MissingFramesAndPacketsMap& missing_frames_and_packets) {
   // Iterate over all frames in the list.
   for (MissingFramesAndPacketsMap::const_iterator it =
-       missing_frames_and_packets.begin();
-       it != missing_frames_and_packets.end(); ++it) {
+           missing_frames_and_packets.begin();
+       it != missing_frames_and_packets.end();
+       ++it) {
     PacketList packets_to_resend;
     uint8 frame_id = it->first;
     const PacketIdSet& packets_set = it->second;
@@ -76,8 +88,8 @@ void RtpSender::ResendPackets(
 
         // Resend packet to the network.
         if (success) {
-          VLOG(1) << "Resend " << static_cast<int>(frame_id)
-                  << ":" << packet_id;
+          VLOG(1) << "Resend " << static_cast<int>(frame_id) << ":"
+                  << packet_id;
           // Set a unique incremental sequence number for every packet.
           Packet& packet = packets_to_resend.back();
           UpdateSequenceNumber(&packet);
@@ -88,14 +100,15 @@ void RtpSender::ResendPackets(
     } else {
       // Iterate over all of the packets in the frame.
       for (PacketIdSet::const_iterator set_it = packets_set.begin();
-          set_it != packets_set.end(); ++set_it) {
+           set_it != packets_set.end();
+           ++set_it) {
         uint16 packet_id = *set_it;
         success = storage_->GetPacket(frame_id, packet_id, &packets_to_resend);
 
         // Resend packet to the network.
         if (success) {
-          VLOG(1) << "Resend " << static_cast<int>(frame_id)
-                  << ":" << packet_id;
+          VLOG(1) << "Resend " << static_cast<int>(frame_id) << ":"
+                  << packet_id;
           Packet& packet = packets_to_resend.back();
           UpdateSequenceNumber(&packet);
         }
@@ -109,32 +122,31 @@ void RtpSender::UpdateSequenceNumber(Packet* packet) {
   uint16 new_sequence_number = packetizer_->NextSequenceNumber();
   int index = 2;
   (*packet)[index] = (static_cast<uint8>(new_sequence_number));
-  (*packet)[index + 1] =(static_cast<uint8>(new_sequence_number >> 8));
+  (*packet)[index + 1] = (static_cast<uint8>(new_sequence_number >> 8));
 }
 
-void RtpSender::RtpStatistics(const base::TimeTicks& now,
-                              RtcpSenderInfo* sender_info) {
-  // The timestamp of this Rtcp packet should be estimated as the timestamp of
-  // the frame being captured at this moment. We are calculating that
-  // timestamp as the last frame's timestamp + the time since the last frame
-  // was captured.
-  uint32 ntp_seconds = 0;
-  uint32 ntp_fraction = 0;
-  ConvertTimeTicksToNtp(now, &ntp_seconds, &ntp_fraction);
-  sender_info->ntp_seconds = ntp_seconds;
-  sender_info->ntp_fraction = ntp_fraction;
+void RtpSender::SubscribeRtpStatsCallback(
+    const CastTransportRtpStatistics& callback) {
+  stats_callback_ = callback;
+  ScheduleNextStatsReport();
+}
+
+void RtpSender::ScheduleNextStatsReport() {
+  transport_task_runner_->PostDelayedTask(
+      FROM_HERE,
+      base::Bind(&RtpSender::RtpStatistics, base::AsWeakPtr(this)),
+      base::TimeDelta::FromMilliseconds(kStatsCallbackIntervalMs));
+}
 
+void RtpSender::RtpStatistics() {
+  RtcpSenderInfo sender_info;
   base::TimeTicks time_sent;
-  uint32 rtp_timestamp;
-  if (packetizer_->LastSentTimestamp(&time_sent, &rtp_timestamp)) {
-    base::TimeDelta time_since_last_send = now - time_sent;
-    sender_info->rtp_timestamp = rtp_timestamp +
-        time_since_last_send.InMilliseconds() * (config_.frequency / 1000);
-  } else {
-    sender_info->rtp_timestamp = 0;
-  }
-  sender_info->send_packet_count = packetizer_->send_packets_count();
-  sender_info->send_octet_count = packetizer_->send_octet_count();
+  uint32 rtp_timestamp = 0;
+  packetizer_->LastSentTimestamp(&time_sent, &rtp_timestamp);
+  sender_info.send_packet_count = packetizer_->send_packets_count();
+  sender_info.send_octet_count = packetizer_->send_octet_count();
+  stats_callback_.Run(sender_info, time_sent, rtp_timestamp);
+  ScheduleNextStatsReport();
 }
 
 }  // namespace transport