Always enter yield policy scope using simulated TimeControllers.
This makes the class easier to use at a minor cost of making it slightly more magic. Bug: webrtc:9883 Change-Id: If807cfbf046615333c3bcd3b58a001813102a9f9 Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/161231 Reviewed-by: Erik Språng <sprang@webrtc.org> Reviewed-by: Per Kjellander <perkj@webrtc.org> Reviewed-by: Markus Handell <handellm@webrtc.org> Commit-Queue: Per Kjellander <perkj@webrtc.org> Cr-Commit-Position: refs/heads/master@{#30008}
This commit is contained in:
parent
242a9e0ffe
commit
340af975e9
@ -40,12 +40,6 @@ class TimeController {
|
||||
// Allow task queues and process threads created by this instance to execute
|
||||
// for the given |duration|.
|
||||
virtual void AdvanceTime(TimeDelta duration) = 0;
|
||||
// Execute closure in an implementation defined scope where rtc::Event::Wait
|
||||
// might yield to execute other tasks. This allows doing blocking waits on
|
||||
// tasks on other task queues froma a task queue without deadlocking.
|
||||
virtual void InvokeWithControlledYield(std::function<void()> closure) = 0;
|
||||
// Returns a YieldInterface which can be installed as a ScopedYieldPolicy.
|
||||
virtual rtc::YieldInterface* YieldInterface() = 0;
|
||||
};
|
||||
|
||||
// Interface for telling time, scheduling an event to fire at a particular time,
|
||||
|
||||
@ -321,8 +321,7 @@ void CallClient::AddExtensions(std::vector<RtpExtension> extensions) {
|
||||
}
|
||||
|
||||
void CallClient::SendTask(std::function<void()> task) {
|
||||
time_controller_->InvokeWithControlledYield(
|
||||
[&] { task_queue_.SendTask(std::move(task), RTC_FROM_HERE); });
|
||||
task_queue_.SendTask(std::move(task), RTC_FROM_HERE);
|
||||
}
|
||||
|
||||
CallClientPair::~CallClientPair() = default;
|
||||
|
||||
@ -159,7 +159,9 @@ class ExternalTimeController::TaskQueueWrapper : public TaskQueueBase {
|
||||
};
|
||||
|
||||
ExternalTimeController::ExternalTimeController(ControlledAlarmClock* alarm)
|
||||
: alarm_(alarm), impl_(alarm_->GetClock()->CurrentTime()) {
|
||||
: alarm_(alarm),
|
||||
impl_(alarm_->GetClock()->CurrentTime()),
|
||||
yield_policy_(&impl_) {
|
||||
global_clock_.SetTime(alarm_->GetClock()->CurrentTime());
|
||||
alarm_->SetCallback([this] { Run(); });
|
||||
}
|
||||
@ -182,16 +184,6 @@ void ExternalTimeController::AdvanceTime(TimeDelta duration) {
|
||||
alarm_->Sleep(duration);
|
||||
}
|
||||
|
||||
void ExternalTimeController::InvokeWithControlledYield(
|
||||
std::function<void()> closure) {
|
||||
rtc::ScopedYieldPolicy policy(YieldInterface());
|
||||
closure();
|
||||
}
|
||||
|
||||
rtc::YieldInterface* ExternalTimeController::YieldInterface() {
|
||||
return &impl_;
|
||||
}
|
||||
|
||||
std::unique_ptr<TaskQueueBase, TaskQueueDeleter>
|
||||
ExternalTimeController::CreateTaskQueue(
|
||||
absl::string_view name,
|
||||
|
||||
@ -38,8 +38,6 @@ class ExternalTimeController : public TimeController, public TaskQueueFactory {
|
||||
std::unique_ptr<ProcessThread> CreateProcessThread(
|
||||
const char* thread_name) override;
|
||||
void AdvanceTime(TimeDelta duration) override;
|
||||
void InvokeWithControlledYield(std::function<void()> closure) override;
|
||||
rtc::YieldInterface* YieldInterface() override;
|
||||
|
||||
// Implementation of TaskQueueFactory.
|
||||
std::unique_ptr<TaskQueueBase, TaskQueueDeleter> CreateTaskQueue(
|
||||
@ -59,6 +57,7 @@ class ExternalTimeController : public TimeController, public TaskQueueFactory {
|
||||
|
||||
ControlledAlarmClock* alarm_;
|
||||
sim_time_impl::SimulatedTimeControllerImpl impl_;
|
||||
rtc::ScopedYieldPolicy yield_policy_;
|
||||
|
||||
// Overrides the global rtc::Clock to ensure that it reports the same times as
|
||||
// the time controller.
|
||||
|
||||
@ -138,11 +138,9 @@ TEST(ExternalTimeControllerTest, YieldForTask) {
|
||||
time_simulation.GetTaskQueueFactory()->CreateTaskQueue(
|
||||
"TestQueue", TaskQueueFactory::Priority::NORMAL));
|
||||
|
||||
time_simulation.InvokeWithControlledYield([&] {
|
||||
rtc::Event event;
|
||||
task_queue.PostTask([&] { event.Set(); });
|
||||
EXPECT_TRUE(event.Wait(200));
|
||||
});
|
||||
rtc::Event event;
|
||||
task_queue.PostTask([&] { event.Set(); });
|
||||
EXPECT_TRUE(event.Wait(200));
|
||||
}
|
||||
|
||||
TEST(ExternalTimeControllerTest, TasksYieldToEachOther) {
|
||||
|
||||
@ -34,15 +34,6 @@ void RealTimeController::AdvanceTime(TimeDelta duration) {
|
||||
SleepMs(duration.ms());
|
||||
}
|
||||
|
||||
void RealTimeController::InvokeWithControlledYield(
|
||||
std::function<void()> closure) {
|
||||
closure();
|
||||
}
|
||||
|
||||
rtc::YieldInterface* RealTimeController::YieldInterface() {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
RealTimeController* GlobalRealTimeController() {
|
||||
static RealTimeController* time_controller = new RealTimeController();
|
||||
return time_controller;
|
||||
|
||||
@ -29,8 +29,6 @@ class RealTimeController : public TimeController {
|
||||
std::unique_ptr<ProcessThread> CreateProcessThread(
|
||||
const char* thread_name) override;
|
||||
void AdvanceTime(TimeDelta duration) override;
|
||||
void InvokeWithControlledYield(std::function<void()> closure) override;
|
||||
rtc::YieldInterface* YieldInterface() override;
|
||||
|
||||
private:
|
||||
std::unique_ptr<TaskQueueFactory> task_queue_factory_;
|
||||
|
||||
@ -399,7 +399,7 @@ void SimulatedTimeControllerImpl::Unregister(SimulatedSequenceRunner* runner) {
|
||||
|
||||
GlobalSimulatedTimeController::GlobalSimulatedTimeController(
|
||||
Timestamp start_time)
|
||||
: sim_clock_(start_time.us()), impl_(start_time) {
|
||||
: sim_clock_(start_time.us()), impl_(start_time), yield_policy_(&impl_) {
|
||||
global_clock_.SetTime(start_time);
|
||||
}
|
||||
|
||||
@ -434,16 +434,4 @@ void GlobalSimulatedTimeController::AdvanceTime(TimeDelta duration) {
|
||||
}
|
||||
}
|
||||
|
||||
void GlobalSimulatedTimeController::InvokeWithControlledYield(
|
||||
std::function<void()> closure) {
|
||||
rtc::ScopedYieldPolicy yield_policy(&impl_);
|
||||
closure();
|
||||
}
|
||||
|
||||
rtc::YieldInterface* GlobalSimulatedTimeController::YieldInterface() {
|
||||
return &impl_;
|
||||
}
|
||||
|
||||
// namespace sim_time_impl
|
||||
|
||||
} // namespace webrtc
|
||||
|
||||
@ -91,14 +91,13 @@ class GlobalSimulatedTimeController : public TimeController {
|
||||
std::unique_ptr<ProcessThread> CreateProcessThread(
|
||||
const char* thread_name) override;
|
||||
void AdvanceTime(TimeDelta duration) override;
|
||||
void InvokeWithControlledYield(std::function<void()> closure) override;
|
||||
rtc::YieldInterface* YieldInterface() override;
|
||||
|
||||
private:
|
||||
rtc::ScopedBaseFakeClock global_clock_;
|
||||
// Provides simulated CurrentNtpInMilliseconds()
|
||||
SimulatedClock sim_clock_;
|
||||
sim_time_impl::SimulatedTimeControllerImpl impl_;
|
||||
rtc::ScopedYieldPolicy yield_policy_;
|
||||
};
|
||||
} // namespace webrtc
|
||||
|
||||
|
||||
@ -493,26 +493,18 @@ class VideoReceiveStreamTestWithSimulatedClock : public ::testing::Test {
|
||||
&call_stats_,
|
||||
time_controller_.GetClock(),
|
||||
new VCMTiming(time_controller_.GetClock())) {
|
||||
time_controller_.InvokeWithControlledYield(
|
||||
[this] { video_receive_stream_.Start(); });
|
||||
}
|
||||
|
||||
~VideoReceiveStreamTestWithSimulatedClock() {
|
||||
time_controller_.InvokeWithControlledYield(
|
||||
[this] { video_receive_stream_.Stop(); });
|
||||
video_receive_stream_.Start();
|
||||
}
|
||||
|
||||
void OnFrameDecoded() { event_->Set(); }
|
||||
|
||||
void PassEncodedFrameAndWait(
|
||||
std::unique_ptr<video_coding::EncodedFrame> frame) {
|
||||
time_controller_.InvokeWithControlledYield([this, &frame] {
|
||||
event_ = std::make_unique<rtc::Event>();
|
||||
// This call will eventually end up in the Decoded method where the
|
||||
// event is set.
|
||||
video_receive_stream_.OnCompleteFrame(std::move(frame));
|
||||
event_->Wait(rtc::Event::kForever);
|
||||
});
|
||||
}
|
||||
|
||||
protected:
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user