/*
 *  Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include "modules/rtp_rtcp/source/rtp_sender.h"

#include <memory>
#include <vector>

#include "absl/strings/string_view.h"
#include "api/rtc_event_log/rtc_event.h"
#include "api/transport/field_trial_based_config.h"
#include "api/video/video_codec_constants.h"
#include "api/video/video_timing.h"
#include "logging/rtc_event_log/mock/mock_rtc_event_log.h"
#include "modules/rtp_rtcp/include/rtp_cvo.h"
#include "modules/rtp_rtcp/include/rtp_header_extension_map.h"
#include "modules/rtp_rtcp/include/rtp_packet_sender.h"
#include "modules/rtp_rtcp/include/rtp_rtcp_defines.h"
#include "modules/rtp_rtcp/source/packet_sequencer.h"
#include "modules/rtp_rtcp/source/rtp_format_video_generic.h"
#include "modules/rtp_rtcp/source/rtp_generic_frame_descriptor.h"
#include "modules/rtp_rtcp/source/rtp_generic_frame_descriptor_extension.h"
#include "modules/rtp_rtcp/source/rtp_header_extensions.h"
#include "modules/rtp_rtcp/source/rtp_packet_received.h"
#include "modules/rtp_rtcp/source/rtp_packet_to_send.h"
#include "modules/rtp_rtcp/source/rtp_sender_video.h"
#include "modules/rtp_rtcp/source/video_fec_generator.h"
#include "rtc_base/arraysize.h"
#include "rtc_base/logging.h"
#include "rtc_base/rate_limiter.h"
#include "rtc_base/strings/string_builder.h"
#include "test/field_trial.h"
#include "test/gmock.h"
#include "test/gtest.h"
#include "test/mock_transport.h"
#include "test/scoped_key_value_config.h"
#include "test/time_controller/simulated_time_controller.h"

namespace webrtc {

namespace {
enum : int {  // The first valid value is 1.
  kAbsoluteSendTimeExtensionId = 1,
  kAudioLevelExtensionId,
  kGenericDescriptorId,
  kMidExtensionId,
  kRepairedRidExtensionId,
  kRidExtensionId,
  kTransmissionTimeOffsetExtensionId,
  kTransportSequenceNumberExtensionId,
  kVideoRotationExtensionId,
  kVideoTimingExtensionId,
};

const int kPayload = 100;
const int kRtxPayload = 98;
const uint32_t kTimestamp = 10;
const uint16_t kSeqNum = 33;
const uint32_t kSsrc = 725242;
const uint32_t kRtxSsrc = 12345;
const uint32_t kFlexFecSsrc = 45678;
const uint64_t kStartTime = 123456789;
const size_t kMaxPaddingSize = 224u;
const uint8_t kPayloadData[] = {47, 11, 32, 93, 89};
const int64_t kDefaultExpectedRetransmissionTimeMs = 125;
const size_t kMaxPaddingLength = 224;      // Value taken from rtp_sender.cc.
const uint32_t kTimestampTicksPerMs = 90;  // 90kHz clock.
constexpr absl::string_view kMid = "mid";
constexpr absl::string_view kRid = "f";
constexpr bool kMarkerBit = true;

using ::testing::_;
using ::testing::AllOf;
using ::testing::AtLeast;
using ::testing::Contains;
using ::testing::Each;
using ::testing::ElementsAre;
using ::testing::Eq;
using ::testing::Field;
using ::testing::Gt;
using ::testing::IsEmpty;
using ::testing::NiceMock;
using ::testing::Not;
using ::testing::Pointee;
using ::testing::Property;
using ::testing::Return;
using ::testing::SizeIs;

class MockRtpPacketPacer : public RtpPacketSender {
 public:
  MockRtpPacketPacer() {}
  virtual ~MockRtpPacketPacer() {}

  MOCK_METHOD(void,
              EnqueuePackets,
              (std::vector<std::unique_ptr<RtpPacketToSend>>),
              (override));
};

}  // namespace

class RtpSenderTest : public ::testing::Test {
 protected:
  RtpSenderTest()
      : time_controller_(Timestamp::Millis(kStartTime)),
        clock_(time_controller_.GetClock()),
        retransmission_rate_limiter_(clock_, 1000),
        flexfec_sender_(0,
                        kFlexFecSsrc,
                        kSsrc,
                        "",
                        std::vector<RtpExtension>(),
                        std::vector<RtpExtensionSize>(),
                        nullptr,
                        clock_) {}

  void SetUp() override { SetUpRtpSender(true, false, nullptr); }

  void SetUpRtpSender(bool populate_network2,
                      bool always_send_mid_and_rid,
                      VideoFecGenerator* fec_generator) {
    RtpRtcpInterface::Configuration config = GetDefaultConfig();
    config.fec_generator = fec_generator;
    config.populate_network2_timestamp = populate_network2;
    config.always_send_mid_and_rid = always_send_mid_and_rid;
    CreateSender(config);
  }

  RtpRtcpInterface::Configuration GetDefaultConfig() {
    RtpRtcpInterface::Configuration config;
    config.clock = clock_;
    config.local_media_ssrc = kSsrc;
    config.rtx_send_ssrc = kRtxSsrc;
    config.event_log = &mock_rtc_event_log_;
    config.retransmission_rate_limiter = &retransmission_rate_limiter_;
    config.paced_sender = &mock_paced_sender_;
    config.field_trials = &field_trials_;
    // Configure rid unconditionally, it has effect only if
    // corresponding header extension is enabled.
    config.rid = std::string(kRid);
    return config;
  }

  void CreateSender(const RtpRtcpInterface::Configuration& config) {
    packet_history_ = std::make_unique<RtpPacketHistory>(
        config.clock, config.enable_rtx_padding_prioritization);
    sequencer_.emplace(kSsrc, kRtxSsrc,
                       /*require_marker_before_media_padding=*/!config.audio,
                       clock_);
    rtp_sender_ = std::make_unique<RTPSender>(config, packet_history_.get(),
                                              config.paced_sender);
    sequencer_->set_media_sequence_number(kSeqNum);
    rtp_sender_->SetTimestampOffset(0);
  }

  GlobalSimulatedTimeController time_controller_;
  Clock* const clock_;
  NiceMock<MockRtcEventLog> mock_rtc_event_log_;
  MockRtpPacketPacer mock_paced_sender_;
  RateLimiter retransmission_rate_limiter_;
  FlexfecSender flexfec_sender_;

  absl::optional<PacketSequencer> sequencer_;
  std::unique_ptr<RtpPacketHistory> packet_history_;
  std::unique_ptr<RTPSender> rtp_sender_;

  const test::ScopedKeyValueConfig field_trials_;

  std::unique_ptr<RtpPacketToSend> BuildRtpPacket(int payload_type,
                                                  bool marker_bit,
                                                  uint32_t timestamp,
                                                  int64_t capture_time_ms) {
    auto packet = rtp_sender_->AllocatePacket();
    packet->SetPayloadType(payload_type);
    packet->set_packet_type(RtpPacketMediaType::kVideo);
    packet->SetMarker(marker_bit);
    packet->SetTimestamp(timestamp);
    packet->set_capture_time(Timestamp::Millis(capture_time_ms));
    return packet;
  }

  std::unique_ptr<RtpPacketToSend> SendPacket(int64_t capture_time_ms,
                                              int payload_length) {
    uint32_t timestamp = capture_time_ms * 90;
    auto packet =
        BuildRtpPacket(kPayload, kMarkerBit, timestamp, capture_time_ms);
    packet->AllocatePayload(payload_length);
    packet->set_allow_retransmission(true);

    // Packet should be stored in a send bucket.
    EXPECT_TRUE(
        rtp_sender_->SendToNetwork(std::make_unique<RtpPacketToSend>(*packet)));
    return packet;
  }

  std::unique_ptr<RtpPacketToSend> SendGenericPacket() {
    const int64_t kCaptureTimeMs = clock_->TimeInMilliseconds();
    // Use maximum allowed size to catch corner cases when packet is dropped
    // because of lack of capacity for the media packet, or for an rtx packet
    // containing the media packet.
    return SendPacket(kCaptureTimeMs,
                      /*payload_length=*/rtp_sender_->MaxRtpPacketSize() -
                          rtp_sender_->ExpectedPerPacketOverhead());
  }

  std::vector<std::unique_ptr<RtpPacketToSend>> GeneratePadding(
      size_t target_size_bytes) {
    return rtp_sender_->GeneratePadding(
        target_size_bytes, /*media_has_been_sent=*/true,
        sequencer_->CanSendPaddingOnMediaSsrc());
  }

  std::vector<std::unique_ptr<RtpPacketToSend>> Sequence(
      std::vector<std::unique_ptr<RtpPacketToSend>> packets) {
    for (auto& packet : packets) {
      sequencer_->Sequence(*packet);
    }
    return packets;
  }

  size_t GenerateAndSendPadding(size_t target_size_bytes) {
    size_t generated_bytes = 0;
    for (auto& packet : GeneratePadding(target_size_bytes)) {
      generated_bytes += packet->payload_size() + packet->padding_size();
      rtp_sender_->SendToNetwork(std::move(packet));
    }
    return generated_bytes;
  }

  // The following are helpers for configuring the RTPSender. They must be
  // called before sending any packets.

  // Enable the retransmission stream with sizable packet storage.
  void EnableRtx() {
    // RTX needs to be able to read the source packets from the packet store.
    // Pick a number of packets to store big enough for any unit test.
    constexpr uint16_t kNumberOfPacketsToStore = 100;
    packet_history_->SetStorePacketsStatus(
        RtpPacketHistory::StorageMode::kStoreAndCull, kNumberOfPacketsToStore);
    rtp_sender_->SetRtxPayloadType(kRtxPayload, kPayload);
    rtp_sender_->SetRtxStatus(kRtxRetransmitted | kRtxRedundantPayloads);
  }

  // Enable sending of the MID header extension for both the primary SSRC and
  // the RTX SSRC.
  void EnableMidSending(absl::string_view mid) {
    rtp_sender_->RegisterRtpHeaderExtension(RtpMid::Uri(), kMidExtensionId);
    rtp_sender_->SetMid(mid);
  }

  // Enable sending of the RSID header extension for the primary SSRC and the
  // RRSID header extension for the RTX SSRC.
  void EnableRidSending() {
    rtp_sender_->RegisterRtpHeaderExtension(RtpStreamId::Uri(),
                                            kRidExtensionId);
    rtp_sender_->RegisterRtpHeaderExtension(RepairedRtpStreamId::Uri(),
                                            kRepairedRidExtensionId);
  }
};

TEST_F(RtpSenderTest, AllocatePacketSetCsrc) {
  // Configure rtp_sender with csrc.
  std::vector<uint32_t> csrcs;
  csrcs.push_back(0x23456789);
  rtp_sender_->SetCsrcs(csrcs);

  auto packet = rtp_sender_->AllocatePacket();

  ASSERT_TRUE(packet);
  EXPECT_EQ(rtp_sender_->SSRC(), packet->Ssrc());
  EXPECT_EQ(csrcs, packet->Csrcs());
}

TEST_F(RtpSenderTest, AllocatePacketReserveExtensions) {
  // Configure rtp_sender with extensions.
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransmissionOffset::Uri(), kTransmissionTimeOffsetExtensionId));
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      AbsoluteSendTime::Uri(), kAbsoluteSendTimeExtensionId));
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(AudioLevel::Uri(),
                                                      kAudioLevelExtensionId));
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransportSequenceNumber::Uri(), kTransportSequenceNumberExtensionId));
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      VideoOrientation::Uri(), kVideoRotationExtensionId));

  auto packet = rtp_sender_->AllocatePacket();

  ASSERT_TRUE(packet);
  // Preallocate BWE extensions RtpSender set itself.
  EXPECT_TRUE(packet->HasExtension<TransmissionOffset>());
  EXPECT_TRUE(packet->HasExtension<AbsoluteSendTime>());
  EXPECT_TRUE(packet->HasExtension<TransportSequenceNumber>());
  // Do not allocate media specific extensions.
  EXPECT_FALSE(packet->HasExtension<AudioLevel>());
  EXPECT_FALSE(packet->HasExtension<VideoOrientation>());
}

TEST_F(RtpSenderTest, PaddingAlwaysAllowedOnAudio) {
  RtpRtcpInterface::Configuration config = GetDefaultConfig();
  config.audio = true;
  CreateSender(config);

  std::unique_ptr<RtpPacketToSend> audio_packet = rtp_sender_->AllocatePacket();
  // Padding on audio stream allowed regardless of marker in the last packet.
  audio_packet->SetMarker(false);
  audio_packet->SetPayloadType(kPayload);
  sequencer_->Sequence(*audio_packet);

  const size_t kPaddingSize = 59;

  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(AllOf(
          Pointee(Property(&RtpPacketToSend::packet_type,
                           RtpPacketMediaType::kPadding)),
          Pointee(Property(&RtpPacketToSend::padding_size, kPaddingSize))))));
  EXPECT_EQ(kPaddingSize, GenerateAndSendPadding(kPaddingSize));

  // Requested padding size is too small, will send a larger one.
  const size_t kMinPaddingSize = 50;
  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(
                  AllOf(Pointee(Property(&RtpPacketToSend::packet_type,
                                         RtpPacketMediaType::kPadding)),
                        Pointee(Property(&RtpPacketToSend::padding_size,
                                         kMinPaddingSize))))));
  EXPECT_EQ(kMinPaddingSize, GenerateAndSendPadding(kMinPaddingSize - 5));
}

TEST_F(RtpSenderTest, SendToNetworkForwardsPacketsToPacer) {
  auto packet = BuildRtpPacket(kPayload, kMarkerBit, kTimestamp, 0);
  Timestamp now = clock_->CurrentTime();

  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(AllOf(
                  Pointee(Property(&RtpPacketToSend::Ssrc, kSsrc)),
                  Pointee(Property(&RtpPacketToSend::capture_time, now))))));
  EXPECT_TRUE(
      rtp_sender_->SendToNetwork(std::make_unique<RtpPacketToSend>(*packet)));
}

TEST_F(RtpSenderTest, ReSendPacketForwardsPacketsToPacer) {
  packet_history_->SetStorePacketsStatus(
      RtpPacketHistory::StorageMode::kStoreAndCull, 10);
  int64_t now_ms = clock_->TimeInMilliseconds();
  auto packet = BuildRtpPacket(kPayload, kMarkerBit, kTimestamp, now_ms);
  packet->SetSequenceNumber(kSeqNum);
  packet->set_allow_retransmission(true);
  packet_history_->PutRtpPacket(std::move(packet), Timestamp::Millis(now_ms));

  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(AllOf(
                  Pointee(Property(&RtpPacketToSend::Ssrc, kSsrc)),
                  Pointee(Property(&RtpPacketToSend::SequenceNumber, kSeqNum)),
                  Pointee(Property(&RtpPacketToSend::capture_time,
                                   Timestamp::Millis(now_ms))),
                  Pointee(Property(&RtpPacketToSend::packet_type,
                                   RtpPacketMediaType::kRetransmission))))));
  EXPECT_TRUE(rtp_sender_->ReSendPacket(kSeqNum));
}

// This test sends 1 regular video packet, then 4 padding packets, and then
// 1 more regular packet.
TEST_F(RtpSenderTest, SendPadding) {
  constexpr int kNumPaddingPackets = 4;
  EXPECT_CALL(mock_paced_sender_, EnqueuePackets);
  std::unique_ptr<RtpPacketToSend> media_packet =
      SendPacket(/*capture_time_ms=*/clock_->TimeInMilliseconds(),
                 /*payload_size=*/100);
  sequencer_->Sequence(*media_packet);

  // Wait 50 ms before generating each padding packet.
  for (int i = 0; i < kNumPaddingPackets; ++i) {
    time_controller_.AdvanceTime(TimeDelta::Millis(50));
    const size_t kPaddingTargetBytes = 100;  // Request 100 bytes of padding.

    // Padding should be sent on the media ssrc, with a continous sequence
    // number range. Size will be forced to full pack size and the timestamp
    // shall be that of the last media packet.
    EXPECT_CALL(mock_paced_sender_,
                EnqueuePackets(ElementsAre(Pointee(AllOf(
                    Property(&RtpPacketToSend::Ssrc, kSsrc),
                    Property(&RtpPacketToSend::padding_size, kMaxPaddingLength),
                    Property(&RtpPacketToSend::SequenceNumber,
                             media_packet->SequenceNumber() + i + 1),
                    Property(&RtpPacketToSend::Timestamp,
                             media_packet->Timestamp()))))));
    std::vector<std::unique_ptr<RtpPacketToSend>> padding_packets =
        Sequence(GeneratePadding(kPaddingTargetBytes));
    ASSERT_THAT(padding_packets, SizeIs(1));
    rtp_sender_->SendToNetwork(std::move(padding_packets[0]));
  }

  // Send a regular video packet again.
  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(Property(
          &RtpPacketToSend::Timestamp, Gt(media_packet->Timestamp()))))));

  std::unique_ptr<RtpPacketToSend> next_media_packet =
      SendPacket(/*capture_time_ms=*/clock_->TimeInMilliseconds(),
                 /*payload_size=*/100);
}

TEST_F(RtpSenderTest, NoPaddingAsFirstPacketWithoutBweExtensions) {
  EXPECT_THAT(rtp_sender_->GeneratePadding(
                  /*target_size_bytes=*/100,
                  /*media_has_been_sent=*/false,
                  /*can_send_padding_on_media_ssrc=*/false),
              IsEmpty());

  // Don't send padding before media even with RTX.
  EnableRtx();
  EXPECT_THAT(rtp_sender_->GeneratePadding(
                  /*target_size_bytes=*/100,
                  /*media_has_been_sent=*/false,
                  /*can_send_padding_on_media_ssrc=*/false),
              IsEmpty());
}

TEST_F(RtpSenderTest, RequiresRtxSsrcToEnableRtx) {
  RtpRtcpInterface::Configuration config = GetDefaultConfig();
  config.rtx_send_ssrc = absl::nullopt;
  RTPSender rtp_sender(config, packet_history_.get(), config.paced_sender);
  rtp_sender.SetRtxPayloadType(kRtxPayload, kPayload);

  rtp_sender.SetRtxStatus(kRtxRetransmitted);

  EXPECT_EQ(rtp_sender.RtxStatus(), kRtxOff);
}

TEST_F(RtpSenderTest, RequiresRtxPayloadTypesToEnableRtx) {
  RtpRtcpInterface::Configuration config = GetDefaultConfig();
  config.rtx_send_ssrc = kRtxSsrc;
  RTPSender rtp_sender(config, packet_history_.get(), config.paced_sender);

  rtp_sender.SetRtxStatus(kRtxRetransmitted);

  EXPECT_EQ(rtp_sender.RtxStatus(), kRtxOff);
}

TEST_F(RtpSenderTest, CanEnableRtxWhenRtxSsrcAndPayloadTypeAreConfigured) {
  RtpRtcpInterface::Configuration config = GetDefaultConfig();
  config.rtx_send_ssrc = kRtxSsrc;
  RTPSender rtp_sender(config, packet_history_.get(), config.paced_sender);
  rtp_sender.SetRtxPayloadType(kRtxPayload, kPayload);

  ASSERT_EQ(rtp_sender.RtxStatus(), kRtxOff);
  rtp_sender.SetRtxStatus(kRtxRetransmitted);

  EXPECT_EQ(rtp_sender.RtxStatus(), kRtxRetransmitted);
}

TEST_F(RtpSenderTest, AllowPaddingAsFirstPacketOnRtxWithTransportCc) {
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransportSequenceNumber::Uri(), kTransportSequenceNumberExtensionId));

  // Padding can't be sent as first packet on media SSRC since we don't know
  // what payload type to assign.
  EXPECT_THAT(rtp_sender_->GeneratePadding(
                  /*target_size_bytes=*/100,
                  /*media_has_been_sent=*/false,
                  /*can_send_padding_on_media_ssrc=*/false),
              IsEmpty());

  // With transportcc padding can be sent as first packet on the RTX SSRC.
  EnableRtx();
  EXPECT_THAT(rtp_sender_->GeneratePadding(
                  /*target_size_bytes=*/100,
                  /*media_has_been_sent=*/false,
                  /*can_send_padding_on_media_ssrc=*/false),
              Not(IsEmpty()));
}

TEST_F(RtpSenderTest, AllowPaddingAsFirstPacketOnRtxWithAbsSendTime) {
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      AbsoluteSendTime::Uri(), kAbsoluteSendTimeExtensionId));

  // Padding can't be sent as first packet on media SSRC since we don't know
  // what payload type to assign.
  EXPECT_THAT(rtp_sender_->GeneratePadding(
                  /*target_size_bytes=*/100,
                  /*media_has_been_sent=*/false,
                  /*can_send_padding_on_media_ssrc=*/false),
              IsEmpty());

  // With abs send time, padding can be sent as first packet on the RTX SSRC.
  EnableRtx();
  EXPECT_THAT(rtp_sender_->GeneratePadding(
                  /*target_size_bytes=*/100,
                  /*media_has_been_sent=*/false,
                  /*can_send_padding_on_media_ssrc=*/false),
              Not(IsEmpty()));
}

TEST_F(RtpSenderTest, UpdatesTimestampsOnPlainRtxPadding) {
  EnableRtx();
  // Timestamps as set based on capture time in RtpSenderTest.
  const int64_t start_time = clock_->TimeInMilliseconds();
  const uint32_t start_timestamp = start_time * kTimestampTicksPerMs;

  // Start by sending one media packet.
  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(
          AllOf(Pointee(Property(&RtpPacketToSend::padding_size, 0u)),
                Pointee(Property(&RtpPacketToSend::Timestamp, start_timestamp)),
                Pointee(Property(&RtpPacketToSend::capture_time,
                                 Timestamp::Millis(start_time)))))));
  std::unique_ptr<RtpPacketToSend> media_packet =
      SendPacket(start_time, /*payload_size=*/600);
  sequencer_->Sequence(*media_packet);

  // Advance time before sending padding.
  const TimeDelta kTimeDiff = TimeDelta::Millis(17);
  time_controller_.AdvanceTime(kTimeDiff);

  // Timestamps on padding should be offset from the sent media.
  EXPECT_THAT(
      Sequence(GeneratePadding(/*target_size_bytes=*/100)),
      Each(Pointee(AllOf(
          Property(&RtpPacketToSend::padding_size, kMaxPaddingLength),
          Property(&RtpPacketToSend::Timestamp,
                   start_timestamp + (kTimestampTicksPerMs * kTimeDiff.ms())),
          Property(&RtpPacketToSend::capture_time,
                   Timestamp::Millis(start_time) + kTimeDiff)))));
}

TEST_F(RtpSenderTest, KeepsTimestampsOnPayloadPadding) {
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransportSequenceNumber::Uri(), kTransportSequenceNumberExtensionId));
  EnableRtx();
  // Timestamps as set based on capture time in RtpSenderTest.
  const int64_t start_time = clock_->TimeInMilliseconds();
  const uint32_t start_timestamp = start_time * kTimestampTicksPerMs;
  const size_t kPayloadSize = 200;
  const size_t kRtxHeaderSize = 2;

  // Start by sending one media packet and putting in the packet history.
  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(
          AllOf(Pointee(Property(&RtpPacketToSend::padding_size, 0u)),
                Pointee(Property(&RtpPacketToSend::Timestamp, start_timestamp)),
                Pointee(Property(&RtpPacketToSend::capture_time,
                                 Timestamp::Millis(start_time)))))));
  std::unique_ptr<RtpPacketToSend> media_packet =
      SendPacket(start_time, kPayloadSize);
  packet_history_->PutRtpPacket(std::move(media_packet),
                                Timestamp::Millis(start_time));

  // Advance time before sending padding.
  const TimeDelta kTimeDiff = TimeDelta::Millis(17);
  time_controller_.AdvanceTime(kTimeDiff);

  // Timestamps on payload padding should be set to original.
  EXPECT_THAT(GeneratePadding(/*target_size_bytes=*/100),
              Each(AllOf(Pointee(Property(&RtpPacketToSend::padding_size, 0u)),
                         Pointee(Property(&RtpPacketToSend::payload_size,
                                          kPayloadSize + kRtxHeaderSize)),
                         Pointee(Property(&RtpPacketToSend::Timestamp,
                                          start_timestamp)),
                         Pointee(Property(&RtpPacketToSend::capture_time,
                                          Timestamp::Millis(start_time))))));
}

// Test that the MID header extension is included on sent packets when
// configured.
TEST_F(RtpSenderTest, MidIncludedOnSentPackets) {
  EnableMidSending(kMid);

  // Send a couple packets, expect both packets to have the MID set.
  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(Pointee(
                  Property(&RtpPacketToSend::GetExtension<RtpMid>, kMid)))))
      .Times(2);
  SendGenericPacket();
  SendGenericPacket();
}

TEST_F(RtpSenderTest, RidIncludedOnSentPackets) {
  EnableRidSending();

  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(Pointee(Property(
                  &RtpPacketToSend::GetExtension<RtpStreamId>, kRid)))));
  SendGenericPacket();
}

TEST_F(RtpSenderTest, RidIncludedOnRtxSentPackets) {
  EnableRtx();
  EnableRidSending();

  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(Pointee(AllOf(
                  Property(&RtpPacketToSend::GetExtension<RtpStreamId>, kRid),
                  Property(&RtpPacketToSend::HasExtension<RepairedRtpStreamId>,
                           false))))))
      .WillOnce([&](std::vector<std::unique_ptr<RtpPacketToSend>> packets) {
        sequencer_->Sequence(*packets[0]);
        packet_history_->PutRtpPacket(std::move(packets[0]),
                                      clock_->CurrentTime());
      });
  SendGenericPacket();

  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(AllOf(
          Property(&RtpPacketToSend::GetExtension<RepairedRtpStreamId>, kRid),
          Property(&RtpPacketToSend::HasExtension<RtpStreamId>, false))))));
  rtp_sender_->ReSendPacket(kSeqNum);
}

TEST_F(RtpSenderTest, MidAndRidNotIncludedOnSentPacketsAfterAck) {
  EnableMidSending(kMid);
  EnableRidSending();

  // This first packet should include both MID and RID.
  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(AllOf(
          Property(&RtpPacketToSend::GetExtension<RtpMid>, kMid),
          Property(&RtpPacketToSend::GetExtension<RtpStreamId>, kRid))))));
  auto first_built_packet = SendGenericPacket();
  rtp_sender_->OnReceivedAckOnSsrc(first_built_packet->SequenceNumber());

  // The second packet should include neither since an ack was received.
  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(AllOf(
          Property(&RtpPacketToSend::HasExtension<RtpMid>, false),
          Property(&RtpPacketToSend::HasExtension<RtpStreamId>, false))))));
  SendGenericPacket();
}

TEST_F(RtpSenderTest, MidAndRidAlwaysIncludedOnSentPacketsWhenConfigured) {
  SetUpRtpSender(false, /*always_send_mid_and_rid=*/true, nullptr);
  EnableMidSending(kMid);
  EnableRidSending();

  // Send two media packets: one before and one after the ack.
  // Due to the configuration, both sent packets should contain MID and RID.
  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(
          AllOf(Property(&RtpPacketToSend::GetExtension<RtpMid>, kMid),
                Property(&RtpPacketToSend::GetExtension<RtpStreamId>, kRid))))))
      .Times(2);
  auto first_built_packet = SendGenericPacket();
  rtp_sender_->OnReceivedAckOnSsrc(first_built_packet->SequenceNumber());
  SendGenericPacket();
}

// Test that the first RTX packet includes both MID and RRID even if the packet
// being retransmitted did not have MID or RID. The MID and RID are needed on
// the first packets for a given SSRC, and RTX packets are sent on a separate
// SSRC.
TEST_F(RtpSenderTest, MidAndRidIncludedOnFirstRtxPacket) {
  EnableRtx();
  EnableMidSending(kMid);
  EnableRidSending();

  // This first packet will include both MID and RID.
  EXPECT_CALL(mock_paced_sender_, EnqueuePackets);
  auto first_built_packet = SendGenericPacket();
  rtp_sender_->OnReceivedAckOnSsrc(first_built_packet->SequenceNumber());

  // The second packet will include neither since an ack was received, put
  // it in the packet history for retransmission.
  EXPECT_CALL(mock_paced_sender_, EnqueuePackets(SizeIs(1)))
      .WillOnce([&](std::vector<std::unique_ptr<RtpPacketToSend>> packets) {
        packet_history_->PutRtpPacket(std::move(packets[0]),
                                      clock_->CurrentTime());
      });
  auto second_built_packet = SendGenericPacket();

  // The first RTX packet should include MID and RRID.
  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(Pointee(AllOf(
                  Property(&RtpPacketToSend::GetExtension<RtpMid>, kMid),
                  Property(&RtpPacketToSend::GetExtension<RepairedRtpStreamId>,
                           kRid))))));
  rtp_sender_->ReSendPacket(second_built_packet->SequenceNumber());
}

// Test that the RTX packets sent after receving an ACK on the RTX SSRC does
// not include either MID or RRID even if the packet being retransmitted did
// had a MID or RID.
TEST_F(RtpSenderTest, MidAndRidNotIncludedOnRtxPacketsAfterAck) {
  EnableRtx();
  EnableMidSending(kMid);
  EnableRidSending();

  // This first packet will include both MID and RID.
  auto first_built_packet = SendGenericPacket();
  sequencer_->Sequence(*first_built_packet);
  packet_history_->PutRtpPacket(
      std::make_unique<RtpPacketToSend>(*first_built_packet),
      /*send_time=*/clock_->CurrentTime());
  rtp_sender_->OnReceivedAckOnSsrc(first_built_packet->SequenceNumber());

  // The second packet will include neither since an ack was received.
  auto second_built_packet = SendGenericPacket();
  sequencer_->Sequence(*second_built_packet);
  packet_history_->PutRtpPacket(
      std::make_unique<RtpPacketToSend>(*second_built_packet),
      /*send_time=*/clock_->CurrentTime());

  // The first RTX packet will include MID and RRID.
  EXPECT_CALL(mock_paced_sender_, EnqueuePackets(SizeIs(1)))
      .WillOnce([&](std::vector<std::unique_ptr<RtpPacketToSend>> packets) {
        rtp_sender_->OnReceivedAckOnRtxSsrc(packets[0]->SequenceNumber());
        packet_history_->MarkPacketAsSent(
            *packets[0]->retransmitted_sequence_number());
      });
  rtp_sender_->ReSendPacket(second_built_packet->SequenceNumber());

  // The second and third RTX packets should not include MID nor RRID.
  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(Pointee(AllOf(
                  Property(&RtpPacketToSend::HasExtension<RtpMid>, false),
                  Property(&RtpPacketToSend::HasExtension<RepairedRtpStreamId>,
                           false))))))
      .Times(2);
  rtp_sender_->ReSendPacket(first_built_packet->SequenceNumber());
  rtp_sender_->ReSendPacket(second_built_packet->SequenceNumber());
}

TEST_F(RtpSenderTest, MidAndRidAlwaysIncludedOnRtxPacketsWhenConfigured) {
  SetUpRtpSender(false, /*always_send_mid_and_rid=*/true, nullptr);
  EnableRtx();
  EnableMidSending(kMid);
  EnableRidSending();

  // Send two media packets: one before and one after the ack.
  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(
          AllOf(Property(&RtpPacketToSend::GetExtension<RtpMid>, kMid),
                Property(&RtpPacketToSend::GetExtension<RtpStreamId>, kRid))))))
      .Times(2)
      .WillRepeatedly(
          [&](std::vector<std::unique_ptr<RtpPacketToSend>> packets) {
            packet_history_->PutRtpPacket(std::move(packets[0]),
                                          clock_->CurrentTime());
          });
  auto media_packet1 = SendGenericPacket();
  rtp_sender_->OnReceivedAckOnSsrc(media_packet1->SequenceNumber());
  auto media_packet2 = SendGenericPacket();

  // Send three RTX packets with different combinations of orders w.r.t. the
  // media and RTX acks.
  // Due to the configuration, all sent packets should contain MID
  // and either RID (media) or RRID (RTX).
  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(Pointee(AllOf(
                  Property(&RtpPacketToSend::GetExtension<RtpMid>, kMid),
                  Property(&RtpPacketToSend::GetExtension<RepairedRtpStreamId>,
                           kRid))))))
      .Times(3)
      .WillRepeatedly(
          [&](std::vector<std::unique_ptr<RtpPacketToSend>> packets) {
            rtp_sender_->OnReceivedAckOnRtxSsrc(packets[0]->SequenceNumber());
            packet_history_->MarkPacketAsSent(
                *packets[0]->retransmitted_sequence_number());
          });
  rtp_sender_->ReSendPacket(media_packet2->SequenceNumber());
  rtp_sender_->ReSendPacket(media_packet1->SequenceNumber());
  rtp_sender_->ReSendPacket(media_packet2->SequenceNumber());
}

// Test that if the RtpState indicates an ACK has been received on that SSRC
// then neither the MID nor RID header extensions will be sent.
TEST_F(RtpSenderTest, MidAndRidNotIncludedOnSentPacketsAfterRtpStateRestored) {
  EnableMidSending(kMid);
  EnableRidSending();

  RtpState state = rtp_sender_->GetRtpState();
  EXPECT_FALSE(state.ssrc_has_acked);
  state.ssrc_has_acked = true;
  rtp_sender_->SetRtpState(state);

  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(AllOf(
          Property(&RtpPacketToSend::HasExtension<RtpMid>, false),
          Property(&RtpPacketToSend::HasExtension<RtpStreamId>, false))))));
  SendGenericPacket();
}

// Test that if the RTX RtpState indicates an ACK has been received on that
// RTX SSRC then neither the MID nor RRID header extensions will be sent on
// RTX packets.
TEST_F(RtpSenderTest, MidAndRridNotIncludedOnRtxPacketsAfterRtpStateRestored) {
  EnableRtx();
  EnableMidSending(kMid);
  EnableRidSending();

  RtpState rtx_state = rtp_sender_->GetRtxRtpState();
  EXPECT_FALSE(rtx_state.ssrc_has_acked);
  rtx_state.ssrc_has_acked = true;
  rtp_sender_->SetRtxRtpState(rtx_state);

  EXPECT_CALL(mock_paced_sender_, EnqueuePackets(SizeIs(1)))
      .WillOnce([&](std::vector<std::unique_ptr<RtpPacketToSend>> packets) {
        packet_history_->PutRtpPacket(std::move(packets[0]),
                                      clock_->CurrentTime());
      });
  auto built_packet = SendGenericPacket();

  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(AllOf(
          Property(&RtpPacketToSend::HasExtension<RtpMid>, false),
          Property(&RtpPacketToSend::HasExtension<RtpStreamId>, false))))));
  ASSERT_LT(0, rtp_sender_->ReSendPacket(built_packet->SequenceNumber()));
}

TEST_F(RtpSenderTest, RespectsNackBitrateLimit) {
  const int32_t kPacketSize = 1400;
  const int32_t kNumPackets = 30;
  retransmission_rate_limiter_.SetMaxRate(kPacketSize * kNumPackets * 8);
  EnableRtx();

  std::vector<uint16_t> sequence_numbers;
  for (int32_t i = 0; i < kNumPackets; ++i) {
    std::unique_ptr<RtpPacketToSend> packet =
        BuildRtpPacket(kPayload, /*marker_bit=*/true, /*timestamp=*/0,
                       /*capture_time_ms=*/clock_->TimeInMilliseconds());
    packet->set_allow_retransmission(true);
    sequencer_->Sequence(*packet);
    sequence_numbers.push_back(packet->SequenceNumber());
    packet_history_->PutRtpPacket(std::move(packet),
                                  /*send_time=*/clock_->CurrentTime());
    time_controller_.AdvanceTime(TimeDelta::Millis(1));
  }

  time_controller_.AdvanceTime(TimeDelta::Millis(1000 - kNumPackets));

  // Resending should work - brings the bandwidth up to the limit.
  // NACK bitrate is capped to the same bitrate as the encoder, since the max
  // protection overhead is 50% (see MediaOptimization::SetTargetRates).
  EXPECT_CALL(mock_paced_sender_, EnqueuePackets(ElementsAre(Pointee(Property(
                                      &RtpPacketToSend::packet_type,
                                      RtpPacketMediaType::kRetransmission)))))
      .Times(kNumPackets)
      .WillRepeatedly(
          [&](std::vector<std::unique_ptr<RtpPacketToSend>> packets) {
            for (const auto& packet : packets) {
              packet_history_->MarkPacketAsSent(
                  *packet->retransmitted_sequence_number());
            }
          });
  rtp_sender_->OnReceivedNack(sequence_numbers, 0);

  // Must be at least 5ms in between retransmission attempts.
  time_controller_.AdvanceTime(TimeDelta::Millis(5));

  // Resending should not work, bandwidth exceeded.
  EXPECT_CALL(mock_paced_sender_, EnqueuePackets).Times(0);
  rtp_sender_->OnReceivedNack(sequence_numbers, 0);
}

TEST_F(RtpSenderTest, UpdatingCsrcsUpdatedOverhead) {
  RtpRtcpInterface::Configuration config = GetDefaultConfig();
  config.rtx_send_ssrc = {};
  CreateSender(config);

  // Base RTP overhead is 12B.
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 12u);

  // Adding two csrcs adds 2*4 bytes to the header.
  rtp_sender_->SetCsrcs({1, 2});
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 20u);
}

TEST_F(RtpSenderTest, OnOverheadChanged) {
  RtpRtcpInterface::Configuration config = GetDefaultConfig();
  config.rtx_send_ssrc = {};
  CreateSender(config);

  // Base RTP overhead is 12B.
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 12u);

  rtp_sender_->RegisterRtpHeaderExtension(TransmissionOffset::Uri(),
                                          kTransmissionTimeOffsetExtensionId);

  // TransmissionTimeOffset extension has a size of 3B, but with the addition
  // of header index and rounding to 4 byte boundary we end up with 20B total.
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 20u);
}

TEST_F(RtpSenderTest, CountMidOnlyUntilAcked) {
  RtpRtcpInterface::Configuration config = GetDefaultConfig();
  config.rtx_send_ssrc = {};
  CreateSender(config);

  // Base RTP overhead is 12B.
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 12u);

  rtp_sender_->RegisterRtpHeaderExtension(RtpMid::Uri(), kMidExtensionId);

  // Counted only if set.
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 12u);
  rtp_sender_->SetMid("foo");
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 36u);
  rtp_sender_->RegisterRtpHeaderExtension(RtpStreamId::Uri(), kRidExtensionId);
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 52u);

  // Ack received, mid/rid no longer sent.
  rtp_sender_->OnReceivedAckOnSsrc(0);
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 12u);
}

TEST_F(RtpSenderTest, DontCountVolatileExtensionsIntoOverhead) {
  RtpRtcpInterface::Configuration config = GetDefaultConfig();
  config.rtx_send_ssrc = {};
  CreateSender(config);

  // Base RTP overhead is 12B.
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 12u);

  rtp_sender_->RegisterRtpHeaderExtension(InbandComfortNoiseExtension::Uri(),
                                          1);
  rtp_sender_->RegisterRtpHeaderExtension(AbsoluteCaptureTimeExtension::Uri(),
                                          2);
  rtp_sender_->RegisterRtpHeaderExtension(VideoOrientation::Uri(), 3);
  rtp_sender_->RegisterRtpHeaderExtension(PlayoutDelayLimits::Uri(), 4);
  rtp_sender_->RegisterRtpHeaderExtension(VideoContentTypeExtension::Uri(), 5);
  rtp_sender_->RegisterRtpHeaderExtension(VideoTimingExtension::Uri(), 6);
  rtp_sender_->RegisterRtpHeaderExtension(RepairedRtpStreamId::Uri(), 7);
  rtp_sender_->RegisterRtpHeaderExtension(ColorSpaceExtension::Uri(), 8);

  // Still only 12B counted since can't count on above being sent.
  EXPECT_EQ(rtp_sender_->ExpectedPerPacketOverhead(), 12u);
}

TEST_F(RtpSenderTest, SendPacketHandlesRetransmissionHistory) {
  packet_history_->SetStorePacketsStatus(
      RtpPacketHistory::StorageMode::kStoreAndCull, 10);

  // Ignore calls to EnqueuePackets() for this test.
  EXPECT_CALL(mock_paced_sender_, EnqueuePackets).WillRepeatedly(Return());

  // Build a media packet and put in the packet history.
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, true, 0, clock_->TimeInMilliseconds());
  const uint16_t media_sequence_number = packet->SequenceNumber();
  packet->set_allow_retransmission(true);
  packet_history_->PutRtpPacket(std::move(packet), clock_->CurrentTime());

  // Simulate successful retransmission request.
  time_controller_.AdvanceTime(TimeDelta::Millis(30));
  EXPECT_THAT(rtp_sender_->ReSendPacket(media_sequence_number), Gt(0));

  // Packet already pending, retransmission not allowed.
  time_controller_.AdvanceTime(TimeDelta::Millis(30));
  EXPECT_THAT(rtp_sender_->ReSendPacket(media_sequence_number), Eq(0));

  // Simulate packet exiting pacer, mark as not longer pending.
  packet_history_->MarkPacketAsSent(media_sequence_number);

  // Retransmissions allowed again.
  time_controller_.AdvanceTime(TimeDelta::Millis(30));
  EXPECT_THAT(rtp_sender_->ReSendPacket(media_sequence_number), Gt(0));
}

TEST_F(RtpSenderTest, MarksRetransmittedPackets) {
  packet_history_->SetStorePacketsStatus(
      RtpPacketHistory::StorageMode::kStoreAndCull, 10);

  // Build a media packet and put in the packet history.
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, true, 0, clock_->TimeInMilliseconds());
  const uint16_t media_sequence_number = packet->SequenceNumber();
  packet->set_allow_retransmission(true);
  packet_history_->PutRtpPacket(std::move(packet), clock_->CurrentTime());

  // Expect a retransmission packet marked with which packet it is a
  // retransmit of.
  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(AllOf(
          Pointee(Property(&RtpPacketToSend::packet_type,
                           RtpPacketMediaType::kRetransmission)),
          Pointee(Property(&RtpPacketToSend::retransmitted_sequence_number,
                           Eq(media_sequence_number)))))));
  EXPECT_THAT(rtp_sender_->ReSendPacket(media_sequence_number), Gt(0));
}

TEST_F(RtpSenderTest, GeneratedPaddingHasBweExtensions) {
  // Min requested size in order to use RTX payload.
  const size_t kMinPaddingSize = 50;
  EnableRtx();

  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransmissionOffset::Uri(), kTransmissionTimeOffsetExtensionId));
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      AbsoluteSendTime::Uri(), kAbsoluteSendTimeExtensionId));
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransportSequenceNumber::Uri(), kTransportSequenceNumberExtensionId));

  // Put a packet in the history, in order to facilitate payload padding.
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, true, 0, clock_->TimeInMilliseconds());
  packet->set_allow_retransmission(true);
  packet->SetPayloadSize(kMinPaddingSize);
  packet->set_packet_type(RtpPacketMediaType::kVideo);
  packet_history_->PutRtpPacket(std::move(packet), clock_->CurrentTime());

  // Generate a plain padding packet, check that extensions are registered.
  std::vector<std::unique_ptr<RtpPacketToSend>> generated_packets =
      GeneratePadding(/*target_size_bytes=*/1);
  ASSERT_THAT(generated_packets, SizeIs(1));
  auto& plain_padding = generated_packets.front();
  EXPECT_GT(plain_padding->padding_size(), 0u);
  EXPECT_TRUE(plain_padding->HasExtension<TransportSequenceNumber>());
  EXPECT_TRUE(plain_padding->HasExtension<AbsoluteSendTime>());
  EXPECT_TRUE(plain_padding->HasExtension<TransmissionOffset>());
  EXPECT_GT(plain_padding->padding_size(), 0u);

  // Generate a payload padding packets, check that extensions are registered.
  generated_packets = GeneratePadding(kMinPaddingSize);
  ASSERT_EQ(generated_packets.size(), 1u);
  auto& payload_padding = generated_packets.front();
  EXPECT_EQ(payload_padding->padding_size(), 0u);
  EXPECT_TRUE(payload_padding->HasExtension<TransportSequenceNumber>());
  EXPECT_TRUE(payload_padding->HasExtension<AbsoluteSendTime>());
  EXPECT_TRUE(payload_padding->HasExtension<TransmissionOffset>());
  EXPECT_GT(payload_padding->payload_size(), 0u);
}

TEST_F(RtpSenderTest, GeneratePaddingResendsOldPacketsWithRtx) {
  // Min requested size in order to use RTX payload.
  const size_t kMinPaddingSize = 50;

  rtp_sender_->SetRtxPayloadType(kRtxPayload, kPayload);
  rtp_sender_->SetRtxStatus(kRtxRetransmitted | kRtxRedundantPayloads);
  packet_history_->SetStorePacketsStatus(
      RtpPacketHistory::StorageMode::kStoreAndCull, 1);

  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransportSequenceNumber::Uri(), kTransportSequenceNumberExtensionId));

  const size_t kPayloadPacketSize = kMinPaddingSize;
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, true, 0, clock_->TimeInMilliseconds());
  packet->set_allow_retransmission(true);
  packet->SetPayloadSize(kPayloadPacketSize);
  packet->set_packet_type(RtpPacketMediaType::kVideo);
  packet_history_->PutRtpPacket(std::move(packet), clock_->CurrentTime());

  // Generated padding has large enough budget that the video packet should be
  // retransmitted as padding.
  std::vector<std::unique_ptr<RtpPacketToSend>> generated_packets =
      GeneratePadding(kMinPaddingSize);
  ASSERT_EQ(generated_packets.size(), 1u);
  auto& padding_packet = generated_packets.front();
  EXPECT_EQ(padding_packet->packet_type(), RtpPacketMediaType::kPadding);
  EXPECT_EQ(padding_packet->Ssrc(), kRtxSsrc);
  EXPECT_EQ(padding_packet->payload_size(),
            kPayloadPacketSize + kRtxHeaderSize);

  // Not enough budged for payload padding, use plain padding instead.
  const size_t kPaddingBytesRequested = kMinPaddingSize - 1;

  size_t padding_bytes_generated = 0;
  generated_packets = GeneratePadding(kPaddingBytesRequested);
  EXPECT_EQ(generated_packets.size(), 1u);
  for (auto& packet : generated_packets) {
    EXPECT_EQ(packet->packet_type(), RtpPacketMediaType::kPadding);
    EXPECT_EQ(packet->Ssrc(), kRtxSsrc);
    EXPECT_EQ(packet->payload_size(), 0u);
    EXPECT_GT(packet->padding_size(), 0u);
    padding_bytes_generated += packet->padding_size();
  }

  EXPECT_EQ(padding_bytes_generated, kMaxPaddingSize);
}

TEST_F(RtpSenderTest, LimitsPayloadPaddingSize) {
  // RTX payload padding is limited to 3x target size.
  const double kFactor = 3.0;
  SetUpRtpSender(false, false, nullptr);
  rtp_sender_->SetRtxPayloadType(kRtxPayload, kPayload);
  rtp_sender_->SetRtxStatus(kRtxRetransmitted | kRtxRedundantPayloads);
  packet_history_->SetStorePacketsStatus(
      RtpPacketHistory::StorageMode::kStoreAndCull, 1);

  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransportSequenceNumber::Uri(), kTransportSequenceNumberExtensionId));

  // Send a dummy video packet so it ends up in the packet history.
  const size_t kPayloadPacketSize = 1234u;
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, true, 0, clock_->TimeInMilliseconds());
  packet->set_allow_retransmission(true);
  packet->SetPayloadSize(kPayloadPacketSize);
  packet->set_packet_type(RtpPacketMediaType::kVideo);
  packet_history_->PutRtpPacket(std::move(packet), clock_->CurrentTime());

  // Smallest target size that will result in the sent packet being returned as
  // padding.
  const size_t kMinTargerSizeForPayload =
      (kPayloadPacketSize + kRtxHeaderSize) / kFactor;

  // Generated padding has large enough budget that the video packet should be
  // retransmitted as padding.
  EXPECT_THAT(
      GeneratePadding(kMinTargerSizeForPayload),
      AllOf(Not(IsEmpty()),
            Each(Pointee(Property(&RtpPacketToSend::padding_size, Eq(0u))))));

  // If payload padding is > 2x requested size, plain padding is returned
  // instead.
  EXPECT_THAT(
      GeneratePadding(kMinTargerSizeForPayload - 1),
      AllOf(Not(IsEmpty()),
            Each(Pointee(Property(&RtpPacketToSend::padding_size, Gt(0u))))));
}

TEST_F(RtpSenderTest, GeneratePaddingCreatesPurePaddingWithoutRtx) {
  packet_history_->SetStorePacketsStatus(
      RtpPacketHistory::StorageMode::kStoreAndCull, 1);
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransmissionOffset::Uri(), kTransmissionTimeOffsetExtensionId));
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      AbsoluteSendTime::Uri(), kAbsoluteSendTimeExtensionId));
  ASSERT_TRUE(rtp_sender_->RegisterRtpHeaderExtension(
      TransportSequenceNumber::Uri(), kTransportSequenceNumberExtensionId));

  const size_t kPayloadPacketSize = 1234;
  // Send a dummy video packet so it ends up in the packet history. Since we
  // are not using RTX, it should never be used as padding.
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, true, 0, clock_->TimeInMilliseconds());
  packet->set_allow_retransmission(true);
  packet->SetPayloadSize(kPayloadPacketSize);
  packet->set_packet_type(RtpPacketMediaType::kVideo);
  sequencer_->Sequence(*packet);
  packet_history_->PutRtpPacket(std::move(packet), clock_->CurrentTime());

  // Payload padding not available without RTX, only generate plain padding on
  // the media SSRC.
  // Number of padding packets is the requested padding size divided by max
  // padding packet size, rounded up. Pure padding packets are always of the
  // maximum size.
  const size_t kPaddingBytesRequested = kPayloadPacketSize + kRtxHeaderSize;
  const size_t kExpectedNumPaddingPackets =
      (kPaddingBytesRequested + kMaxPaddingSize - 1) / kMaxPaddingSize;
  size_t padding_bytes_generated = 0;
  std::vector<std::unique_ptr<RtpPacketToSend>> padding_packets =
      GeneratePadding(kPaddingBytesRequested);
  EXPECT_EQ(padding_packets.size(), kExpectedNumPaddingPackets);
  for (auto& packet : padding_packets) {
    EXPECT_EQ(packet->packet_type(), RtpPacketMediaType::kPadding);
    EXPECT_EQ(packet->Ssrc(), kSsrc);
    EXPECT_EQ(packet->payload_size(), 0u);
    EXPECT_GT(packet->padding_size(), 0u);
    padding_bytes_generated += packet->padding_size();
    EXPECT_TRUE(packet->HasExtension<TransportSequenceNumber>());
    EXPECT_TRUE(packet->HasExtension<AbsoluteSendTime>());
    EXPECT_TRUE(packet->HasExtension<TransmissionOffset>());
  }

  EXPECT_EQ(padding_bytes_generated,
            kExpectedNumPaddingPackets * kMaxPaddingSize);
}

TEST_F(RtpSenderTest, SupportsPadding) {
  bool kSendingMediaStats[] = {true, false};
  bool kEnableRedundantPayloads[] = {true, false};
  absl::string_view kBweExtensionUris[] = {
      TransportSequenceNumber::Uri(), TransportSequenceNumberV2::Uri(),
      AbsoluteSendTime::Uri(), TransmissionOffset::Uri()};
  const int kExtensionsId = 7;

  for (bool sending_media : kSendingMediaStats) {
    rtp_sender_->SetSendingMediaStatus(sending_media);
    for (bool redundant_payloads : kEnableRedundantPayloads) {
      int rtx_mode = kRtxRetransmitted;
      if (redundant_payloads) {
        rtx_mode |= kRtxRedundantPayloads;
      }
      rtp_sender_->SetRtxPayloadType(kRtxPayload, kPayload);
      rtp_sender_->SetRtxStatus(rtx_mode);

      for (auto extension_uri : kBweExtensionUris) {
        EXPECT_FALSE(rtp_sender_->SupportsPadding());
        rtp_sender_->RegisterRtpHeaderExtension(extension_uri, kExtensionsId);
        if (!sending_media) {
          EXPECT_FALSE(rtp_sender_->SupportsPadding());
        } else {
          EXPECT_TRUE(rtp_sender_->SupportsPadding());
          if (redundant_payloads) {
            EXPECT_TRUE(rtp_sender_->SupportsRtxPayloadPadding());
          } else {
            EXPECT_FALSE(rtp_sender_->SupportsRtxPayloadPadding());
          }
        }
        rtp_sender_->DeregisterRtpHeaderExtension(extension_uri);
        EXPECT_FALSE(rtp_sender_->SupportsPadding());
      }
    }
  }
}

TEST_F(RtpSenderTest, SetsCaptureTimeOnRtxRetransmissions) {
  EnableRtx();

  // Put a packet in the packet history, with current time as capture time.
  const int64_t start_time_ms = clock_->TimeInMilliseconds();
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, kMarkerBit, start_time_ms,
                     /*capture_time_ms=*/start_time_ms);
  packet->set_allow_retransmission(true);
  sequencer_->Sequence(*packet);
  packet_history_->PutRtpPacket(std::move(packet),
                                Timestamp::Millis(start_time_ms));

  // Advance time, request an RTX retransmission. Capture timestamp should be
  // preserved.
  time_controller_.AdvanceTime(TimeDelta::Millis(10));

  EXPECT_CALL(
      mock_paced_sender_,
      EnqueuePackets(ElementsAre(Pointee(Property(
          &RtpPacketToSend::capture_time, Timestamp::Millis(start_time_ms))))));
  EXPECT_GT(rtp_sender_->ReSendPacket(kSeqNum), 0);
}

TEST_F(RtpSenderTest, IgnoresNackAfterDisablingMedia) {
  const TimeDelta kRtt = TimeDelta::Millis(10);

  EnableRtx();
  packet_history_->SetRtt(kRtt);

  // Put a packet in the history.
  const int64_t start_time_ms = clock_->TimeInMilliseconds();
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, kMarkerBit, start_time_ms,
                     /*capture_time_ms=*/start_time_ms);
  packet->set_allow_retransmission(true);
  sequencer_->Sequence(*packet);
  packet_history_->PutRtpPacket(std::move(packet),
                                Timestamp::Millis(start_time_ms));

  // Disable media sending and try to retransmit the packet, it should fail.
  rtp_sender_->SetSendingMediaStatus(false);
  time_controller_.AdvanceTime(kRtt);
  EXPECT_LT(rtp_sender_->ReSendPacket(kSeqNum), 0);
}

TEST_F(RtpSenderTest, DoesntFecProtectRetransmissions) {
  // Set up retranmission without RTX, so that a plain copy of the old packet is
  // re-sent instead.
  const TimeDelta kRtt = TimeDelta::Millis(10);
  rtp_sender_->SetSendingMediaStatus(true);
  rtp_sender_->SetRtxStatus(kRtxOff);
  packet_history_->SetStorePacketsStatus(
      RtpPacketHistory::StorageMode::kStoreAndCull, 10);
  packet_history_->SetRtt(kRtt);

  // Put a fec protected packet in the history.
  const int64_t start_time_ms = clock_->TimeInMilliseconds();
  std::unique_ptr<RtpPacketToSend> packet =
      BuildRtpPacket(kPayload, kMarkerBit, start_time_ms,
                     /*capture_time_ms=*/start_time_ms);
  packet->set_allow_retransmission(true);
  packet->set_fec_protect_packet(true);
  sequencer_->Sequence(*packet);
  packet_history_->PutRtpPacket(std::move(packet),
                                Timestamp::Millis(start_time_ms));

  // Re-send packet, the retransmitted packet should not have the FEC protection
  // flag set.
  EXPECT_CALL(mock_paced_sender_,
              EnqueuePackets(ElementsAre(Pointee(
                  Property(&RtpPacketToSend::fec_protect_packet, false)))));

  time_controller_.AdvanceTime(kRtt);
  EXPECT_GT(rtp_sender_->ReSendPacket(kSeqNum), 0);
}

TEST_F(RtpSenderTest, MarksPacketsWithKeyframeStatus) {
  RTPSenderVideo::Config video_config;
  video_config.clock = clock_;
  video_config.rtp_sender = rtp_sender_.get();
  video_config.field_trials = &field_trials_;
  RTPSenderVideo rtp_sender_video(video_config);

  const uint8_t kPayloadType = 127;
  const absl::optional<VideoCodecType> kCodecType =
      VideoCodecType::kVideoCodecGeneric;

  const uint32_t kCaptureTimeMsToRtpTimestamp = 90;  // 90 kHz clock

  {
    EXPECT_CALL(mock_paced_sender_,
                EnqueuePackets(Each(
                    Pointee(Property(&RtpPacketToSend::is_key_frame, true)))))
        .Times(AtLeast(1));
    RTPVideoHeader video_header;
    video_header.frame_type = VideoFrameType::kVideoFrameKey;
    int64_t capture_time_ms = clock_->TimeInMilliseconds();
    EXPECT_TRUE(rtp_sender_video.SendVideo(
        kPayloadType, kCodecType,
        capture_time_ms * kCaptureTimeMsToRtpTimestamp, capture_time_ms,
        kPayloadData, video_header, kDefaultExpectedRetransmissionTimeMs));

    time_controller_.AdvanceTime(TimeDelta::Millis(33));
  }

  {
    EXPECT_CALL(mock_paced_sender_,
                EnqueuePackets(Each(
                    Pointee(Property(&RtpPacketToSend::is_key_frame, false)))))
        .Times(AtLeast(1));
    RTPVideoHeader video_header;
    video_header.frame_type = VideoFrameType::kVideoFrameDelta;
    int64_t capture_time_ms = clock_->TimeInMilliseconds();
    EXPECT_TRUE(rtp_sender_video.SendVideo(
        kPayloadType, kCodecType,
        capture_time_ms * kCaptureTimeMsToRtpTimestamp, capture_time_ms,
        kPayloadData, video_header, kDefaultExpectedRetransmissionTimeMs));

    time_controller_.AdvanceTime(TimeDelta::Millis(33));
  }
}

}  // namespace webrtc
