/*
 *  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 "video/video_stream_decoder.h"

#include <algorithm>
#include <map>
#include <vector>

#include "common_video/include/frame_callback.h"
#include "modules/video_coding/video_coding_impl.h"
#include "rtc_base/checks.h"
#include "rtc_base/logging.h"
#include "system_wrappers/include/metrics.h"
#include "video/call_stats.h"
#include "video/payload_router.h"
#include "video/receive_statistics_proxy.h"

namespace webrtc {

VideoStreamDecoder::VideoStreamDecoder(
    vcm::VideoReceiver* video_receiver,
    VCMFrameTypeCallback* vcm_frame_type_callback,
    VCMPacketRequestCallback* vcm_packet_request_callback,
    bool enable_nack,
    bool enable_fec,
    ReceiveStatisticsProxy* receive_statistics_proxy,
    rtc::VideoSinkInterface<VideoFrame>* incoming_video_stream)
    : video_receiver_(video_receiver),
      receive_stats_callback_(receive_statistics_proxy),
      incoming_video_stream_(incoming_video_stream) {
  RTC_DCHECK(video_receiver_);

  static const int kMaxPacketAgeToNack = 450;
  static const int kMaxNackListSize = 250;
  video_receiver_->SetNackSettings(kMaxNackListSize,
                                   kMaxPacketAgeToNack, 0);
  video_receiver_->RegisterReceiveCallback(this);
  video_receiver_->RegisterFrameTypeCallback(vcm_frame_type_callback);
  video_receiver_->RegisterReceiveStatisticsCallback(this);

  VCMVideoProtection video_protection =
      enable_nack ? (enable_fec ? kProtectionNackFEC : kProtectionNack)
                  : kProtectionNone;

  VCMDecodeErrorMode decode_error_mode = enable_nack ? kNoErrors : kWithErrors;
  video_receiver_->SetVideoProtection(video_protection, true);
  video_receiver_->SetDecodeErrorMode(decode_error_mode);
  VCMPacketRequestCallback* packet_request_callback =
      enable_nack ? vcm_packet_request_callback : nullptr;
  video_receiver_->RegisterPacketRequestCallback(packet_request_callback);
}

VideoStreamDecoder::~VideoStreamDecoder() {
  // Note: There's an assumption at this point that the decoder thread is
  // *not* running. If it was, then there could be a race for each of these
  // callbacks.

  // Unset all the callback pointers that we set in the ctor.
  video_receiver_->RegisterPacketRequestCallback(nullptr);
  video_receiver_->RegisterReceiveStatisticsCallback(nullptr);
  video_receiver_->RegisterFrameTypeCallback(nullptr);
  video_receiver_->RegisterReceiveCallback(nullptr);
}

// Do not acquire the lock of |video_receiver_| in this function. Decode
// callback won't necessarily be called from the decoding thread. The decoding
// thread may have held the lock when calling VideoDecoder::Decode, Reset, or
// Release. Acquiring the same lock in the path of decode callback can deadlock.
int32_t VideoStreamDecoder::FrameToRender(VideoFrame& video_frame,
                                          rtc::Optional<uint8_t> qp,
                                          VideoContentType content_type) {
  receive_stats_callback_->OnDecodedFrame(qp, content_type);
  incoming_video_stream_->OnFrame(video_frame);
  return 0;
}

int32_t VideoStreamDecoder::ReceivedDecodedReferenceFrame(
  const uint64_t picture_id) {
  RTC_NOTREACHED();
  return 0;
}

void VideoStreamDecoder::OnIncomingPayloadType(int payload_type) {
  receive_stats_callback_->OnIncomingPayloadType(payload_type);
}

void VideoStreamDecoder::OnDecoderImplementationName(
    const char* implementation_name) {
  receive_stats_callback_->OnDecoderImplementationName(implementation_name);
}

void VideoStreamDecoder::OnReceiveRatesUpdated(uint32_t bit_rate,
                                               uint32_t frame_rate) {
  receive_stats_callback_->OnIncomingRate(frame_rate, bit_rate);
}

void VideoStreamDecoder::OnDiscardedPacketsUpdated(int discarded_packets) {
  receive_stats_callback_->OnDiscardedPacketsUpdated(discarded_packets);
}

void VideoStreamDecoder::OnFrameCountsUpdated(const FrameCounts& frame_counts) {
  receive_stats_callback_->OnFrameCountsUpdated(frame_counts);
}

void VideoStreamDecoder::OnFrameBufferTimingsUpdated(int decode_ms,
                                                     int max_decode_ms,
                                                     int current_delay_ms,
                                                     int target_delay_ms,
                                                     int jitter_buffer_ms,
                                                     int min_playout_delay_ms,
                                                     int render_delay_ms) {}

void VideoStreamDecoder::OnTimingFrameInfoUpdated(const TimingFrameInfo& info) {
}

void VideoStreamDecoder::OnCompleteFrame(bool is_keyframe,
                                         size_t size_bytes,
                                         VideoContentType content_type) {}

void VideoStreamDecoder::UpdateRtt(int64_t max_rtt_ms) {
  video_receiver_->SetReceiveChannelParameters(max_rtt_ms);
}
}  // namespace webrtc
