1 /*
2 * Copyright 2004 The WebRTC Project Authors. All rights reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10
11 #include "rtc_base/event.h"
12
13 #include "api/units/time_delta.h"
14 #include "rtc_base/platform_thread.h"
15 #include "system_wrappers/include/clock.h"
16 #include "test/gtest.h"
17
18 namespace rtc {
19
TEST(EventTest,InitiallySignaled)20 TEST(EventTest, InitiallySignaled) {
21 Event event(false, true);
22 ASSERT_TRUE(event.Wait(webrtc::TimeDelta::Zero()));
23 }
24
TEST(EventTest,ManualReset)25 TEST(EventTest, ManualReset) {
26 Event event(true, false);
27 ASSERT_FALSE(event.Wait(webrtc::TimeDelta::Zero()));
28
29 event.Set();
30 ASSERT_TRUE(event.Wait(webrtc::TimeDelta::Zero()));
31 ASSERT_TRUE(event.Wait(webrtc::TimeDelta::Zero()));
32
33 event.Reset();
34 ASSERT_FALSE(event.Wait(webrtc::TimeDelta::Zero()));
35 }
36
TEST(EventTest,AutoReset)37 TEST(EventTest, AutoReset) {
38 Event event;
39 ASSERT_FALSE(event.Wait(webrtc::TimeDelta::Zero()));
40
41 event.Set();
42 ASSERT_TRUE(event.Wait(webrtc::TimeDelta::Zero()));
43 ASSERT_FALSE(event.Wait(webrtc::TimeDelta::Zero()));
44 }
45
46 class SignalerThread {
47 public:
Start(Event * writer,Event * reader)48 void Start(Event* writer, Event* reader) {
49 writer_ = writer;
50 reader_ = reader;
51 thread_ = PlatformThread::SpawnJoinable(
52 [this] {
53 while (!stop_event_.Wait(webrtc::TimeDelta::Zero())) {
54 writer_->Set();
55 reader_->Wait(Event::kForever);
56 }
57 },
58 "EventPerf");
59 }
Stop()60 void Stop() {
61 stop_event_.Set();
62 thread_.Finalize();
63 }
64 Event stop_event_;
65 Event* writer_;
66 Event* reader_;
67 PlatformThread thread_;
68 };
69
TEST(EventTest,UnsignaledWaitDoesNotReturnBeforeTimeout)70 TEST(EventTest, UnsignaledWaitDoesNotReturnBeforeTimeout) {
71 constexpr webrtc::TimeDelta kDuration = webrtc::TimeDelta::Micros(10'499);
72 Event event;
73 auto begin = webrtc::Clock::GetRealTimeClock()->CurrentTime();
74 EXPECT_FALSE(event.Wait(kDuration));
75 EXPECT_GE(webrtc::Clock::GetRealTimeClock()->CurrentTime(),
76 begin + kDuration);
77 }
78
79 // These tests are disabled by default and only intended to be run manually.
TEST(EventTest,DISABLED_PerformanceSingleThread)80 TEST(EventTest, DISABLED_PerformanceSingleThread) {
81 static const int kNumIterations = 10000000;
82 Event event;
83 for (int i = 0; i < kNumIterations; ++i) {
84 event.Set();
85 event.Wait(webrtc::TimeDelta::Zero());
86 }
87 }
88
TEST(EventTest,DISABLED_PerformanceMultiThread)89 TEST(EventTest, DISABLED_PerformanceMultiThread) {
90 static const int kNumIterations = 10000;
91 Event read;
92 Event write;
93 SignalerThread thread;
94 thread.Start(&read, &write);
95
96 for (int i = 0; i < kNumIterations; ++i) {
97 write.Set();
98 read.Wait(Event::kForever);
99 }
100 write.Set();
101
102 thread.Stop();
103 }
104
105 #if RTC_DCHECK_IS_ON && GTEST_HAS_DEATH_TEST && !defined(WEBRTC_ANDROID)
106 // Tests that we crash if we attempt to call rtc::Event::Wait while we're
107 // not allowed to (as per `RTC_DISALLOW_WAIT()`).
TEST(EventTestDeathTest,DisallowEventWait)108 TEST(EventTestDeathTest, DisallowEventWait) {
109 Event event;
110 RTC_DISALLOW_WAIT();
111 EXPECT_DEATH(event.Wait(Event::kForever), "");
112 }
113 #endif // RTC_DCHECK_IS_ON && GTEST_HAS_DEATH_TEST && !defined(WEBRTC_ANDROID)
114
115 } // namespace rtc
116