/*
 *  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.
 */

#ifndef MODULES_RTP_RTCP_SOURCE_RTCP_SENDER_H_
#define MODULES_RTP_RTCP_SOURCE_RTCP_SENDER_H_

#include <map>
#include <memory>
#include <set>
#include <string>
#include <vector>

#include "absl/types/optional.h"
#include "api/call/transport.h"
#include "api/video/video_bitrate_allocation.h"
#include "modules/remote_bitrate_estimator/include/bwe_defines.h"
#include "modules/remote_bitrate_estimator/include/remote_bitrate_estimator.h"
#include "modules/rtp_rtcp/include/receive_statistics.h"
#include "modules/rtp_rtcp/include/rtp_rtcp_defines.h"
#include "modules/rtp_rtcp/source/rtcp_nack_stats.h"
#include "modules/rtp_rtcp/source/rtcp_packet.h"
#include "modules/rtp_rtcp/source/rtcp_packet/compound_packet.h"
#include "modules/rtp_rtcp/source/rtcp_packet/dlrr.h"
#include "modules/rtp_rtcp/source/rtcp_packet/report_block.h"
#include "modules/rtp_rtcp/source/rtcp_packet/tmmb_item.h"
#include "modules/rtp_rtcp/source/rtp_rtcp_interface.h"
#include "rtc_base/constructor_magic.h"
#include "rtc_base/critical_section.h"
#include "rtc_base/random.h"
#include "rtc_base/thread_annotations.h"

namespace webrtc {

class RTCPReceiver;
class RtcEventLog;

class RTCPSender final {
 public:
  struct FeedbackState {
    FeedbackState();
    FeedbackState(const FeedbackState&);
    FeedbackState(FeedbackState&&);

    ~FeedbackState();

    uint32_t packets_sent;
    size_t media_bytes_sent;
    uint32_t send_bitrate;

    uint32_t last_rr_ntp_secs;
    uint32_t last_rr_ntp_frac;
    uint32_t remote_sr;

    std::vector<rtcp::ReceiveTimeInfo> last_xr_rtis;

    // Used when generating TMMBR.
    RTCPReceiver* receiver;
  };

  explicit RTCPSender(const RtpRtcpInterface::Configuration& config);
  virtual ~RTCPSender();

  RtcpMode Status() const RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);
  void SetRTCPStatus(RtcpMode method)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  bool Sending() const RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);
  int32_t SetSendingStatus(const FeedbackState& feedback_state,
                           bool enabled)
      RTC_LOCKS_EXCLUDED(
          critical_section_rtcp_sender_);  // combine the functions

  int32_t SetNackStatus(bool enable)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SetTimestampOffset(uint32_t timestamp_offset)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  // TODO(bugs.webrtc.org/6458): Remove default parameter value when all the
  // depending projects are updated to correctly set payload type.
  void SetLastRtpTime(uint32_t rtp_timestamp,
                      int64_t capture_time_ms,
                      int8_t payload_type = -1)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SetRtpClockRate(int8_t payload_type, int rtp_clock_rate_hz)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  uint32_t SSRC() const { return ssrc_; }

  void SetRemoteSSRC(uint32_t ssrc)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  int32_t SetCNAME(const char* cName)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  int32_t AddMixedCNAME(uint32_t SSRC, const char* c_name)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  int32_t RemoveMixedCNAME(uint32_t SSRC)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  bool TimeToSendRTCPReport(bool sendKeyframeBeforeRTP = false) const
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  int32_t SendRTCP(const FeedbackState& feedback_state,
                   RTCPPacketType packetType,
                   int32_t nackSize = 0,
                   const uint16_t* nackList = 0)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  int32_t SendCompoundRTCP(const FeedbackState& feedback_state,
                           const std::set<RTCPPacketType>& packetTypes,
                           int32_t nackSize = 0,
                           const uint16_t* nackList = nullptr)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  int32_t SendLossNotification(const FeedbackState& feedback_state,
                               uint16_t last_decoded_seq_num,
                               uint16_t last_received_seq_num,
                               bool decodability_flag,
                               bool buffering_allowed)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SetRemb(int64_t bitrate_bps, std::vector<uint32_t> ssrcs)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void UnsetRemb() RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  bool TMMBR() const RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SetTMMBRStatus(bool enable)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SetMaxRtpPacketSize(size_t max_packet_size)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SetTmmbn(std::vector<rtcp::TmmbItem> bounding_set)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SendRtcpXrReceiverReferenceTime(bool enable)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  bool RtcpXrReceiverReferenceTime() const
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SetCsrcs(const std::vector<uint32_t>& csrcs)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

  void SetTargetBitrate(unsigned int target_bitrate)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);
  void SetVideoBitrateAllocation(const VideoBitrateAllocation& bitrate)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);
  void SendCombinedRtcpPacket(
      std::vector<std::unique_ptr<rtcp::RtcpPacket>> rtcp_packets)
      RTC_LOCKS_EXCLUDED(critical_section_rtcp_sender_);

 private:
  class RtcpContext;

  int32_t SendCompoundRTCPLocked(const FeedbackState& feedback_state,
                                 const std::set<RTCPPacketType>& packet_types,
                                 int32_t nack_size,
                                 const uint16_t* nack_list)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);

  absl::optional<int32_t> ComputeCompoundRTCPPacket(
      const FeedbackState& feedback_state,
      const std::set<RTCPPacketType>& packet_types,
      int32_t nack_size,
      const uint16_t* nack_list,
      rtcp::CompoundPacket* out_packet)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);

  // Determine which RTCP messages should be sent and setup flags.
  void PrepareReport(const FeedbackState& feedback_state)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);

  std::vector<rtcp::ReportBlock> CreateReportBlocks(
      const FeedbackState& feedback_state)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);

  std::unique_ptr<rtcp::RtcpPacket> BuildSR(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildRR(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildSDES(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildPLI(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildREMB(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildTMMBR(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildTMMBN(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildAPP(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildLossNotification(
      const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildExtendedReports(
      const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildBYE(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildFIR(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  std::unique_ptr<rtcp::RtcpPacket> BuildNACK(const RtcpContext& context)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);

 private:
  const bool audio_;
  const uint32_t ssrc_;
  Clock* const clock_;
  Random random_ RTC_GUARDED_BY(critical_section_rtcp_sender_);
  RtcpMode method_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  RtcEventLog* const event_log_;
  Transport* const transport_;

  const int report_interval_ms_;

  rtc::CriticalSection critical_section_rtcp_sender_;
  bool sending_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  int64_t next_time_to_send_rtcp_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  uint32_t timestamp_offset_ RTC_GUARDED_BY(critical_section_rtcp_sender_);
  uint32_t last_rtp_timestamp_ RTC_GUARDED_BY(critical_section_rtcp_sender_);
  int64_t last_frame_capture_time_ms_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);
  // SSRC that we receive on our RTP channel
  uint32_t remote_ssrc_ RTC_GUARDED_BY(critical_section_rtcp_sender_);
  std::string cname_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  ReceiveStatisticsProvider* receive_statistics_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);
  std::map<uint32_t, std::string> csrc_cnames_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);

  // send CSRCs
  std::vector<uint32_t> csrcs_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  // Full intra request
  uint8_t sequence_number_fir_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  // Loss Notification
  struct LossNotificationState {
    uint16_t last_decoded_seq_num;
    uint16_t last_received_seq_num;
    bool decodability_flag;
  };
  LossNotificationState loss_notification_state_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);

  // REMB
  int64_t remb_bitrate_ RTC_GUARDED_BY(critical_section_rtcp_sender_);
  std::vector<uint32_t> remb_ssrcs_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);

  std::vector<rtcp::TmmbItem> tmmbn_to_send_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);
  uint32_t tmmbr_send_bps_ RTC_GUARDED_BY(critical_section_rtcp_sender_);
  uint32_t packet_oh_send_ RTC_GUARDED_BY(critical_section_rtcp_sender_);
  size_t max_packet_size_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  // True if sending of XR Receiver reference time report is enabled.
  bool xr_send_receiver_reference_time_enabled_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);

  RtcpPacketTypeCounterObserver* const packet_type_counter_observer_;
  RtcpPacketTypeCounter packet_type_counter_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);

  RtcpNackStats nack_stats_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  VideoBitrateAllocation video_bitrate_allocation_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);
  bool send_video_bitrate_allocation_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);

  std::map<int8_t, int> rtp_clock_rates_khz_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);
  int8_t last_payload_type_ RTC_GUARDED_BY(critical_section_rtcp_sender_);

  absl::optional<VideoBitrateAllocation> CheckAndUpdateLayerStructure(
      const VideoBitrateAllocation& bitrate) const
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);

  void SetFlag(uint32_t type, bool is_volatile)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  void SetFlags(const std::set<RTCPPacketType>& types, bool is_volatile)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  bool IsFlagPresent(uint32_t type) const
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  bool ConsumeFlag(uint32_t type, bool forced = false)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  bool AllVolatileFlagsConsumed() const
      RTC_EXCLUSIVE_LOCKS_REQUIRED(critical_section_rtcp_sender_);
  struct ReportFlag {
    ReportFlag(uint32_t type, bool is_volatile)
        : type(type), is_volatile(is_volatile) {}
    bool operator<(const ReportFlag& flag) const { return type < flag.type; }
    bool operator==(const ReportFlag& flag) const { return type == flag.type; }
    const uint32_t type;
    const bool is_volatile;
  };

  std::set<ReportFlag> report_flags_
      RTC_GUARDED_BY(critical_section_rtcp_sender_);

  typedef std::unique_ptr<rtcp::RtcpPacket> (RTCPSender::*BuilderFunc)(
      const RtcpContext&);
  // Map from RTCPPacketType to builder.
  std::map<uint32_t, BuilderFunc> builders_;

  RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(RTCPSender);
};
}  // namespace webrtc

#endif  // MODULES_RTP_RTCP_SOURCE_RTCP_SENDER_H_
