/*
 *  Copyright (c) 2016 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_VIDEO_CODING_NACK_REQUESTER_H_
#define MODULES_VIDEO_CODING_NACK_REQUESTER_H_

#include <stdint.h>

#include <map>
#include <set>
#include <vector>

#include "api/field_trials_view.h"
#include "api/sequence_checker.h"
#include "api/task_queue/pending_task_safety_flag.h"
#include "api/units/time_delta.h"
#include "api/units/timestamp.h"
#include "modules/include/module_common_types.h"
#include "modules/video_coding/histogram.h"
#include "rtc_base/numerics/sequence_number_util.h"
#include "rtc_base/task_queue.h"
#include "rtc_base/task_utils/repeating_task.h"
#include "rtc_base/thread_annotations.h"
#include "system_wrappers/include/clock.h"

namespace webrtc {

class NackRequesterBase {
 public:
  virtual ~NackRequesterBase() = default;
  virtual void ProcessNacks() = 0;
};

class NackPeriodicProcessor {
 public:
  static constexpr TimeDelta kUpdateInterval = TimeDelta::Millis(20);
  explicit NackPeriodicProcessor(TimeDelta update_interval = kUpdateInterval);
  ~NackPeriodicProcessor();
  void RegisterNackModule(NackRequesterBase* module);
  void UnregisterNackModule(NackRequesterBase* module);

 private:
  void ProcessNackModules() RTC_RUN_ON(sequence_);

  const TimeDelta update_interval_;
  RepeatingTaskHandle repeating_task_ RTC_GUARDED_BY(sequence_);
  std::vector<NackRequesterBase*> modules_ RTC_GUARDED_BY(sequence_);
  RTC_NO_UNIQUE_ADDRESS SequenceChecker sequence_;
};

class ScopedNackPeriodicProcessorRegistration {
 public:
  ScopedNackPeriodicProcessorRegistration(NackRequesterBase* module,
                                          NackPeriodicProcessor* processor);
  ~ScopedNackPeriodicProcessorRegistration();

 private:
  NackRequesterBase* const module_;
  NackPeriodicProcessor* const processor_;
};

class NackRequester final : public NackRequesterBase {
 public:
  NackRequester(TaskQueueBase* current_queue,
                NackPeriodicProcessor* periodic_processor,
                Clock* clock,
                NackSender* nack_sender,
                KeyFrameRequestSender* keyframe_request_sender,
                const FieldTrialsView& field_trials);
  ~NackRequester();

  void ProcessNacks() override;

  int OnReceivedPacket(uint16_t seq_num, bool is_keyframe);
  int OnReceivedPacket(uint16_t seq_num, bool is_keyframe, bool is_recovered);

  void ClearUpTo(uint16_t seq_num);
  void UpdateRtt(int64_t rtt_ms);

 private:
  // Which fields to consider when deciding which packet to nack in
  // GetNackBatch.
  enum NackFilterOptions { kSeqNumOnly, kTimeOnly, kSeqNumAndTime };

  // This class holds the sequence number of the packet that is in the nack list
  // as well as the meta data about when it should be nacked and how many times
  // we have tried to nack this packet.
  struct NackInfo {
    NackInfo();
    NackInfo(uint16_t seq_num,
             uint16_t send_at_seq_num,
             Timestamp created_at_time);

    uint16_t seq_num;
    uint16_t send_at_seq_num;
    Timestamp created_at_time;
    Timestamp sent_at_time;
    int retries;
  };

  void AddPacketsToNack(uint16_t seq_num_start, uint16_t seq_num_end)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(worker_thread_);

  // Removes packets from the nack list until the next keyframe. Returns true
  // if packets were removed.
  bool RemovePacketsUntilKeyFrame()
      RTC_EXCLUSIVE_LOCKS_REQUIRED(worker_thread_);
  std::vector<uint16_t> GetNackBatch(NackFilterOptions options)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(worker_thread_);

  // Update the reordering distribution.
  void UpdateReorderingStatistics(uint16_t seq_num)
      RTC_EXCLUSIVE_LOCKS_REQUIRED(worker_thread_);

  // Returns how many packets we have to wait in order to receive the packet
  // with probability `probabilty` or higher.
  int WaitNumberOfPackets(float probability) const
      RTC_EXCLUSIVE_LOCKS_REQUIRED(worker_thread_);

  TaskQueueBase* const worker_thread_;
  Clock* const clock_;
  NackSender* const nack_sender_;
  KeyFrameRequestSender* const keyframe_request_sender_;

  // TODO(philipel): Some of the variables below are consistently used on a
  // known thread (e.g. see `initialized_`). Those probably do not need
  // synchronized access.
  std::map<uint16_t, NackInfo, DescendingSeqNumComp<uint16_t>> nack_list_
      RTC_GUARDED_BY(worker_thread_);
  std::set<uint16_t, DescendingSeqNumComp<uint16_t>> keyframe_list_
      RTC_GUARDED_BY(worker_thread_);
  std::set<uint16_t, DescendingSeqNumComp<uint16_t>> recovered_list_
      RTC_GUARDED_BY(worker_thread_);
  video_coding::Histogram reordering_histogram_ RTC_GUARDED_BY(worker_thread_);
  bool initialized_ RTC_GUARDED_BY(worker_thread_);
  TimeDelta rtt_ RTC_GUARDED_BY(worker_thread_);
  uint16_t newest_seq_num_ RTC_GUARDED_BY(worker_thread_);

  // Adds a delay before send nack on packet received.
  const TimeDelta send_nack_delay_;

  ScopedNackPeriodicProcessorRegistration processor_registration_;

  // Used to signal destruction to potentially pending tasks.
  ScopedTaskSafety task_safety_;
};

}  // namespace webrtc

#endif  // MODULES_VIDEO_CODING_NACK_REQUESTER_H_
