blob: 5316fac2ae61c7f927ebd4f84889eb473cad41d8 [file] [log] [blame]
// Copyright 2021 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "third_party/webrtc_overrides/metronome_source.h"
#include <memory>
#include <utility>
#include "base/containers/flat_set.h"
#include "base/functional/bind.h"
#include "base/memory/ptr_util.h"
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_refptr.h"
#include "base/sequence_checker.h"
#include "base/task/sequenced_task_runner.h"
#include "base/task/thread_pool.h"
#include "base/thread_annotations.h"
#include "base/time/time.h"
#include "base/trace_event/typed_macros.h"
#include "third_party/webrtc/api/metronome/metronome.h"
#include "third_party/webrtc_overrides/timer_based_tick_provider.h"
namespace blink {
class WebRtcMetronomeAdapter : public webrtc::Metronome {
public:
explicit WebRtcMetronomeAdapter(base::WeakPtr<MetronomeSource> source)
: source_(std::move(source)) {}
// webrtc::Metronome implementation.
webrtc::TimeDelta TickPeriod() const override {
const base::TimeDelta period = source_
? source_->TickPeriod()
: TimerBasedTickProvider::kDefaultPeriod;
return webrtc::TimeDelta::Micros(period.InMicroseconds());
}
void RequestCallOnNextTick(absl::AnyInvocable<void() &&> callback) override {
if (source_)
source_->RequestCallOnNextTick(std::move(callback));
}
private:
const base::WeakPtr<MetronomeSource> source_;
};
MetronomeSource::MetronomeSource(scoped_refptr<TickProvider> tick_provider)
: tick_provider_(std::move(tick_provider)) {
DETACH_FROM_SEQUENCE(metronome_sequence_checker_);
}
MetronomeSource::~MetronomeSource() {
DCHECK_CALLED_ON_VALID_SEQUENCE(metronome_sequence_checker_);
}
void MetronomeSource::RequestCallOnNextTick(
absl::AnyInvocable<void() &&> callback) {
DCHECK_CALLED_ON_VALID_SEQUENCE(metronome_sequence_checker_);
callbacks_.push_back(std::move(callback));
if (callbacks_.size() == 1)
Reschedule();
}
void MetronomeSource::OnMetronomeTick() {
TRACE_EVENT_INSTANT0("webrtc", "MetronomeSource::OnMetronomeTick",
TRACE_EVENT_SCOPE_PROCESS);
TRACE_EVENT0("webrtc", "MetronomeSource::OnMetronomeTick");
DCHECK_CALLED_ON_VALID_SEQUENCE(metronome_sequence_checker_);
std::vector<absl::AnyInvocable<void() &&>> callbacks;
callbacks.swap(callbacks_);
for (auto& callback : callbacks) {
std::move(callback)();
}
}
void MetronomeSource::Reschedule() {
DCHECK_CALLED_ON_VALID_SEQUENCE(metronome_sequence_checker_);
tick_provider_->RequestCallOnNextTick(base::BindOnce(
&MetronomeSource::OnMetronomeTick, weak_factory_.GetWeakPtr()));
}
base::TimeDelta MetronomeSource::TickPeriod() {
DCHECK_CALLED_ON_VALID_SEQUENCE(metronome_sequence_checker_);
return tick_provider_->TickPeriod();
}
std::unique_ptr<webrtc::Metronome> MetronomeSource::CreateWebRtcMetronome() {
return std::make_unique<WebRtcMetronomeAdapter>(weak_factory_.GetWeakPtr());
}
} // namespace blink