/*
 *  Copyright (c) 2019 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/source_tracker.h"

#include <algorithm>
#include <utility>

namespace webrtc {

constexpr int64_t SourceTracker::kTimeoutMs;

SourceTracker::SourceTracker(Clock* clock) : clock_(clock) {}

void SourceTracker::OnFrameDelivered(const RtpPacketInfos& packet_infos) {
  if (packet_infos.empty()) {
    return;
  }

  int64_t now_ms = clock_->TimeInMilliseconds();
  rtc::CritScope lock_scope(&lock_);

  for (const auto& packet_info : packet_infos) {
    for (uint32_t csrc : packet_info.csrcs()) {
      SourceKey key(RtpSourceType::CSRC, csrc);
      SourceEntry& entry = UpdateEntry(key);

      entry.timestamp_ms = now_ms;
      entry.audio_level = packet_info.audio_level();
      entry.rtp_timestamp = packet_info.rtp_timestamp();
    }

    SourceKey key(RtpSourceType::SSRC, packet_info.ssrc());
    SourceEntry& entry = UpdateEntry(key);

    entry.timestamp_ms = now_ms;
    entry.audio_level = packet_info.audio_level();
    entry.rtp_timestamp = packet_info.rtp_timestamp();
  }

  PruneEntries(now_ms);
}

std::vector<RtpSource> SourceTracker::GetSources() const {
  std::vector<RtpSource> sources;

  int64_t now_ms = clock_->TimeInMilliseconds();
  rtc::CritScope lock_scope(&lock_);

  PruneEntries(now_ms);

  for (const auto& pair : list_) {
    const SourceKey& key = pair.first;
    const SourceEntry& entry = pair.second;

    sources.emplace_back(entry.timestamp_ms, key.source, key.source_type,
                         entry.audio_level, entry.rtp_timestamp);
  }

  return sources;
}

SourceTracker::SourceEntry& SourceTracker::UpdateEntry(const SourceKey& key) {
  // We intentionally do |find() + emplace()|, instead of checking the return
  // value of |emplace()|, for performance reasons. It's much more likely for
  // the key to already exist than for it not to.
  auto map_it = map_.find(key);
  if (map_it == map_.end()) {
    // Insert a new entry at the front of the list.
    list_.emplace_front(key, SourceEntry());
    map_.emplace(key, list_.begin());
  } else if (map_it->second != list_.begin()) {
    // Move the old entry to the front of the list.
    list_.splice(list_.begin(), list_, map_it->second);
  }

  return list_.front().second;
}

void SourceTracker::PruneEntries(int64_t now_ms) const {
  int64_t prune_ms = now_ms - kTimeoutMs;

  while (!list_.empty() && list_.back().second.timestamp_ms < prune_ms) {
    map_.erase(list_.back().first);
    list_.pop_back();
  }
}

}  // namespace webrtc
