1 // Copyright 2019 The Pigweed Authors
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not
4 // use this file except in compliance with the License. You may obtain a copy of
5 // the License at
6 //
7 // https://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
12 // License for the specific language governing permissions and limitations under
13 // the License.
14
15 #include "pw_unit_test/framework.h"
16
17 #include <cstring>
18
19 #include "pw_assert/check.h"
20 #include "pw_result/result.h"
21 #include "pw_status/status.h"
22 #include "pw_status/status_with_size.h"
23
24 namespace pw {
25 namespace {
26
TEST(PigweedTest,ExpectBool)27 TEST(PigweedTest, ExpectBool) {
28 EXPECT_TRUE(true);
29 EXPECT_FALSE(false);
30
31 EXPECT_TRUE(1);
32 EXPECT_TRUE(1203492);
33 EXPECT_TRUE(-1);
34 EXPECT_TRUE(0.1f);
35
36 EXPECT_FALSE(0);
37 EXPECT_FALSE(0.0f);
38 EXPECT_FALSE(-0.0f);
39 }
40
TEST(PigweedTest,ExpectBasicComparisons)41 TEST(PigweedTest, ExpectBasicComparisons) {
42 EXPECT_EQ(1, 1 + 0);
43 ASSERT_EQ(1, 1 + 0);
44
45 EXPECT_EQ(0.0f, -0.0f);
46 ASSERT_EQ(0.0f, -0.0f);
47
48 EXPECT_NE(-1, 0);
49 ASSERT_NE(-1, 0);
50
51 EXPECT_GT(2, 1);
52 ASSERT_GT(3, 0);
53
54 EXPECT_GE(1, 1);
55 ASSERT_GE(3, 0);
56
57 EXPECT_LT(0, 1);
58 ASSERT_LT(-2, 1209);
59
60 EXPECT_LE(-1, 0);
61 ASSERT_LE(-2, -2);
62 }
63
TEST(PigweedTest,ExpectNearComparisons)64 TEST(PigweedTest, ExpectNearComparisons) {
65 EXPECT_NEAR(1, 2, 1);
66 ASSERT_NEAR(1, 2, 1);
67
68 EXPECT_NEAR(-5, 5, 10);
69 ASSERT_NEAR(-5, 5, 10);
70
71 int x = 17;
72 int epsilon = 5;
73
74 EXPECT_NEAR(x, 15, epsilon);
75 ASSERT_NEAR(x, 15, epsilon);
76 }
77
TEST(PigweedTest,ExpectFloatComparisons)78 TEST(PigweedTest, ExpectFloatComparisons) {
79 EXPECT_FLOAT_EQ(5.0f, 10.0f / 2);
80 ASSERT_FLOAT_EQ(5.0f, 10.0f / 2);
81
82 EXPECT_FLOAT_EQ(-0.5f, -5.0f / 10);
83 ASSERT_FLOAT_EQ(-0.5f, -5.0f / 10);
84
85 float x = 17.0f / 20.0f;
86
87 EXPECT_FLOAT_EQ(x, 17.0f / 20.0f);
88 ASSERT_FLOAT_EQ(x, 17.0f / 20.0f);
89 }
90
TEST(PigweedTest,ExpectDoubleComparisons)91 TEST(PigweedTest, ExpectDoubleComparisons) {
92 EXPECT_DOUBLE_EQ(5.0, 10.0 / 2);
93 ASSERT_DOUBLE_EQ(5.0, 10.0 / 2);
94
95 EXPECT_DOUBLE_EQ(-0.5, -5.0 / 10);
96 ASSERT_DOUBLE_EQ(-0.5, -5.0 / 10);
97
98 double x = 17.0 / 20.0;
99
100 EXPECT_DOUBLE_EQ(x, 17.0 / 20.0);
101 ASSERT_DOUBLE_EQ(x, 17.0 / 20.0);
102 }
103
TEST(PigweedTest,ExpectStringEquality)104 TEST(PigweedTest, ExpectStringEquality) {
105 EXPECT_STREQ("", "");
106 EXPECT_STREQ("Yes", "Yes");
107
108 char no[] = {'N', 'o', '\0'};
109 ASSERT_STREQ("No", no);
110
111 EXPECT_STRNE("NO", "no");
112 ASSERT_STRNE("yes", no);
113
114 const char* invalid_string = nullptr;
115 EXPECT_STREQ(invalid_string, nullptr);
116 EXPECT_STRNE("abc", nullptr);
117 }
118
TEST(PigweedTest,SucceedAndFailMacros)119 TEST(PigweedTest, SucceedAndFailMacros) {
120 SUCCEED();
121
122 // The ADD_FAILURE() and FAIL() macros cause a test to fail if they are
123 // reached. Use them, but don't let them run so that this test still passes.
124 if (false) {
125 ADD_FAILURE();
126 FAIL();
127 }
128
129 // Without braces, clang-tidy complains if these are multiple statements.
130 if (false)
131 ADD_FAILURE();
132
133 if (false)
134 FAIL();
135 }
136
TEST(PigweedTest,SkipMacro)137 TEST(PigweedTest, SkipMacro) {
138 // Without a brace, clang-tidy complains if GTEST_SKIP is multiple statements.
139 if (false)
140 GTEST_SKIP();
141
142 GTEST_SKIP();
143 // This code should not run.
144 EXPECT_TRUE(false);
145 }
146
TEST(PigweedTest,Logs)147 TEST(PigweedTest, Logs) {
148 EXPECT_TRUE(true) << "This message is ignored";
149 EXPECT_FALSE(false) << "This message is ignored";
150 EXPECT_EQ(0, 0) << "This message is ignored";
151 EXPECT_NE(0, 1) << "This message is ignored";
152 EXPECT_GT(1, 0) << "This message is ignored";
153 EXPECT_GE(0, 0) << "This message is ignored";
154 EXPECT_LT(0, 1) << "This message is ignored";
155 EXPECT_LE(0, 0) << "This message is ignored";
156 EXPECT_STREQ("", "") << "This message is ignored";
157 EXPECT_STRNE("", "?") << "This message is ignored";
158
159 ASSERT_TRUE(true) << "This message is ignored";
160 ASSERT_FALSE(false) << "This message is ignored";
161 ASSERT_EQ(0, 0) << "This message is ignored";
162 ASSERT_NE(0, 1) << "This message is ignored";
163 ASSERT_GT(1, 0) << "This message is ignored";
164 ASSERT_GE(0, 0) << "This message is ignored";
165 ASSERT_LT(0, 1) << "This message is ignored";
166 ASSERT_LE(0, 0) << "This message is ignored";
167 ASSERT_STREQ("", "") << "This message is ignored";
168 ASSERT_STRNE("", "?") << "This message is ignored";
169
170 if (false) {
171 ADD_FAILURE() << "This failed!" << 123;
172 GTEST_FAIL() << "This failed!" << 123 << '?';
173 GTEST_SKIP() << 1.0f << " skips!";
174 }
175 GTEST_SUCCEED() << "This message is ignored";
176 }
177
TEST(PigweedTest,PwOkMatchers)178 TEST(PigweedTest, PwOkMatchers) {
179 PW_TEST_ASSERT_OK(OkStatus());
180 PW_TEST_ASSERT_OK(StatusWithSize(123));
181 PW_TEST_ASSERT_OK(Result<int>(123));
182
183 PW_TEST_EXPECT_OK(OkStatus());
184 PW_TEST_EXPECT_OK(StatusWithSize(123));
185 PW_TEST_EXPECT_OK(Result<int>(123));
186
187 PW_TEST_ASSERT_OK_AND_ASSIGN(auto val, Result<int>(123));
188 EXPECT_EQ(val, 123);
189 PW_TEST_ASSERT_OK_AND_ASSIGN(auto size, StatusWithSize(123U));
190 EXPECT_EQ(size, 123U);
191 }
192
TEST(AssertOkAndAssign,AssignsOkValueToNewLvalue)193 TEST(AssertOkAndAssign, AssignsOkValueToNewLvalue) {
194 const auto value = Result<int>(5);
195 PW_TEST_ASSERT_OK_AND_ASSIGN(int declare_and_assign, value);
196 EXPECT_EQ(5, declare_and_assign);
197 }
198
TEST(AssertOkAndAssign,AssignsOkValueToExistingLvalue)199 TEST(AssertOkAndAssign, AssignsOkValueToExistingLvalue) {
200 const auto value = Result<int>(5);
201 int existing_value = 0;
202 PW_TEST_ASSERT_OK_AND_ASSIGN(existing_value, value);
203 EXPECT_EQ(5, existing_value);
204 }
205
TEST(AssertOkAndAssign,AssignsExistingLvalueToConstReference)206 TEST(AssertOkAndAssign, AssignsExistingLvalueToConstReference) {
207 const auto value = Result<int>(5);
208 PW_TEST_ASSERT_OK_AND_ASSIGN(const auto& ref, value);
209 EXPECT_EQ(5, ref);
210 }
211
212 class CopyMoveCounter {
213 public:
214 CopyMoveCounter() = delete;
CopyMoveCounter(int & copies,int & moves)215 CopyMoveCounter(int& copies, int& moves) : copies_(&copies), moves_(&moves) {}
CopyMoveCounter(const CopyMoveCounter & other)216 CopyMoveCounter(const CopyMoveCounter& other)
217 : copies_(other.copies_), moves_(other.moves_) {
218 ++(*copies_);
219 }
CopyMoveCounter(CopyMoveCounter && other)220 CopyMoveCounter(CopyMoveCounter&& other)
221 : copies_(other.copies_), moves_(other.moves_) {
222 ++(*moves_);
223 }
operator =(const CopyMoveCounter & other)224 CopyMoveCounter& operator=(const CopyMoveCounter& other) {
225 copies_ = other.copies_;
226 moves_ = other.moves_;
227 ++(*copies_);
228 return *this;
229 }
operator =(CopyMoveCounter && other)230 CopyMoveCounter& operator=(CopyMoveCounter&& other) {
231 copies_ = other.copies_;
232 moves_ = other.moves_;
233 ++(*moves_);
234 return *this;
235 }
236
237 private:
238 int* copies_;
239 int* moves_;
240 };
241
TEST(AssertOkAndAssign,OkRvalueDoesNotCopy)242 TEST(AssertOkAndAssign, OkRvalueDoesNotCopy) {
243 int copies = 0;
244 int moves = 0;
245 PW_TEST_ASSERT_OK_AND_ASSIGN([[maybe_unused]] CopyMoveCounter cm,
246 Result(CopyMoveCounter(copies, moves)));
247 EXPECT_EQ(copies, 0);
248 EXPECT_EQ(moves, 2);
249 }
250
TEST(AssertOkAndAssign,OkLvalueMovedDoesNotCopy)251 TEST(AssertOkAndAssign, OkLvalueMovedDoesNotCopy) {
252 int copies = 0;
253 int moves = 0;
254 Result result(CopyMoveCounter(copies, moves));
255 PW_TEST_ASSERT_OK_AND_ASSIGN([[maybe_unused]] CopyMoveCounter cm,
256 std::move(result));
257 EXPECT_EQ(copies, 0);
258 EXPECT_EQ(moves, 3);
259 }
260
TEST(AssertOkAndAssign,OkLvalueCopiesOnce)261 TEST(AssertOkAndAssign, OkLvalueCopiesOnce) {
262 int copies = 0;
263 int moves = 0;
264 Result result(CopyMoveCounter(copies, moves));
265 PW_TEST_ASSERT_OK_AND_ASSIGN([[maybe_unused]] CopyMoveCounter cm, result);
266 EXPECT_EQ(copies, 1);
267 EXPECT_EQ(moves, 2);
268 }
269
270 // The following test contents are disabled and is only for checking what
271 // failure cases would look like. For example, when enabling the test,
272 // the output is:
273 // clang-format off
274 // ERR pw_unit_test/framework_test.cc:294: Failure
275 // ERR Expected: ::pw::internal::ConvertToStatus(Status::Unknown()) == pw::OkStatus()
276 // ERR Actual: UNKNOWN == OK
277 // ERR pw_unit_test/framework_test.cc:295: Failure
278 // ERR Expected: ::pw::internal::ConvertToStatus(Status::Unknown()) == pw::OkStatus()
279 // ERR Actual: UNKNOWN == OK
280 // clang-format on
TEST(TestMatchers,SampleFailures)281 TEST(TestMatchers, SampleFailures) {
282 if (false) {
283 PW_TEST_EXPECT_OK(Status::Unknown());
284 PW_TEST_ASSERT_OK(Status::Unknown());
285 }
286 }
287
288 class SkipOnSetUpTest : public ::testing::Test {
289 public:
SetUp()290 void SetUp() override { GTEST_SKIP(); }
291 };
292
TEST_F(SkipOnSetUpTest,FailTest)293 TEST_F(SkipOnSetUpTest, FailTest) {
294 // This code should not run because the test was skipped in SetUp().
295 EXPECT_TRUE(false);
296 }
297
298 class NonCopyable {
299 public:
NonCopyable(int value)300 NonCopyable(int value) : value_(value) {}
301
302 NonCopyable(const NonCopyable&) = delete;
303 NonCopyable& operator=(const NonCopyable&) = delete;
304
operator ==(const NonCopyable & rhs) const305 bool operator==(const NonCopyable& rhs) const { return value_ == rhs.value_; }
operator !=(const NonCopyable & rhs) const306 bool operator!=(const NonCopyable& rhs) const { return value_ != rhs.value_; }
307
operator bool() const308 operator bool() const { return value_ > 0; }
309
310 private:
311 const int value_;
312 };
313
TEST(PigweedTest,NonCopyableType)314 TEST(PigweedTest, NonCopyableType) {
315 EXPECT_TRUE(NonCopyable(6));
316 EXPECT_FALSE(NonCopyable(-1));
317
318 const NonCopyable this_one(100);
319 EXPECT_EQ(this_one, this_one);
320 EXPECT_TRUE(this_one);
321
322 EXPECT_EQ(NonCopyable(5), NonCopyable(5));
323 EXPECT_NE(NonCopyable(5), NonCopyable(6));
324 }
325
Increment(int * i)326 bool Increment(int* i) {
327 (*i)++;
328 return true;
329 }
330
TEST(PigweedTest,MacroArgumentsOnlyAreEvaluatedOnce)331 TEST(PigweedTest, MacroArgumentsOnlyAreEvaluatedOnce) {
332 int i = 1;
333
334 EXPECT_TRUE(Increment(&i));
335 EXPECT_EQ(i, 2);
336 ASSERT_TRUE(Increment(&i));
337 EXPECT_EQ(i, 3);
338
339 EXPECT_EQ(0x600dbeef, [&i]() {
340 i += 1;
341 return 0x600dbeef;
342 }());
343
344 EXPECT_EQ(i, 4);
345 }
346
347 class ClassWithPrivateMethod {
348 FRIEND_TEST(FixtureTest, FriendClass);
349
350 private:
Return314()351 int Return314() { return 314; }
352 };
353
354 class FixtureTest : public ::testing::Test {
355 public:
FixtureTest()356 FixtureTest() : string_("hello world") {}
357
ReturnTrue()358 bool ReturnTrue() { return true; }
StringLength()359 int StringLength() { return std::strlen(string_); }
360
361 protected:
362 const char* string_;
363 };
364
TEST_F(FixtureTest,CustomFixture)365 TEST_F(FixtureTest, CustomFixture) {
366 EXPECT_TRUE(ReturnTrue());
367 EXPECT_EQ(StringLength(), 11);
368 }
369
TEST_F(FixtureTest,FriendClass)370 TEST_F(FixtureTest, FriendClass) {
371 EXPECT_EQ(ClassWithPrivateMethod().Return314(), 314);
372 }
373
374 class PigweedTestFixture : public ::testing::Test {
375 protected:
PigweedTestFixture()376 PigweedTestFixture() : cool_number_(35) {}
377
378 int cool_number_;
379 };
380
TEST_F(PigweedTestFixture,TheNumberIs35)381 TEST_F(PigweedTestFixture, TheNumberIs35) {
382 EXPECT_EQ(cool_number_, 35);
383 cool_number_ += 1;
384 EXPECT_EQ(cool_number_, 36);
385 }
386
TEST_F(PigweedTestFixture,YupTheNumberIs35)387 TEST_F(PigweedTestFixture, YupTheNumberIs35) {
388 EXPECT_EQ(cool_number_, 35);
389 cool_number_ *= 100;
390 EXPECT_EQ(cool_number_, 3500);
391 }
392
393 class Expectations : public ::testing::Test {
394 protected:
Expectations()395 Expectations() : cool_number_(3) { PW_CHECK_INT_EQ(cool_number_, 3); }
396
~Expectations()397 ~Expectations() override { PW_CHECK_INT_EQ(cool_number_, 14159); }
398
399 int cool_number_;
400 };
401
TEST_F(Expectations,SetCoolNumber)402 TEST_F(Expectations, SetCoolNumber) { cool_number_ = 14159; }
403
404 class SetUpAndTearDown : public ::testing::Test {
405 public:
406 static int value;
407
SetUpTestSuite()408 static void SetUpTestSuite() {
409 value = 1;
410 EXPECT_EQ(value, 1);
411 value++;
412 }
413
TearDownTestSuite()414 static void TearDownTestSuite() {
415 EXPECT_EQ(value, 7);
416 value++;
417 }
418
419 protected:
SetUpAndTearDown()420 SetUpAndTearDown() {
421 EXPECT_EQ(value, 2);
422 value++;
423 }
424
~SetUpAndTearDown()425 ~SetUpAndTearDown() override {
426 EXPECT_EQ(value, 6);
427 value++;
428 }
429
SetUp()430 void SetUp() override {
431 EXPECT_EQ(value, 3);
432 value++;
433 }
434
TearDown()435 void TearDown() override {
436 EXPECT_EQ(value, 5);
437 value++;
438 }
439 };
440
441 int SetUpAndTearDown::value = 1;
442
TEST_F(SetUpAndTearDown,MakeSureItIsSet)443 TEST_F(SetUpAndTearDown, MakeSureItIsSet) {
444 EXPECT_EQ(value, 4);
445 value++;
446 }
447
TEST(TestSuiteTearDown,MakeSureItRan)448 TEST(TestSuiteTearDown, MakeSureItRan) {
449 EXPECT_EQ(SetUpAndTearDown::value, 8);
450 }
451
452 class Interleaved : public ::testing::Test {
453 public:
SetUpTestSuite()454 static void SetUpTestSuite() { suites_running++; }
TearDownTestSuite()455 static void TearDownTestSuite() { suites_running--; }
456
457 protected:
458 static int suites_running;
459 };
460
461 int Interleaved::suites_running = 0;
462
463 class InterleavedA : public Interleaved {};
464 class InterleavedB : public Interleaved {};
465
TEST_F(InterleavedA,Test1)466 TEST_F(InterleavedA, Test1) { ASSERT_EQ(suites_running, 1); }
TEST_F(InterleavedB,Test1)467 TEST_F(InterleavedB, Test1) { ASSERT_EQ(suites_running, 1); }
TEST_F(Interleaved,Test12)468 TEST_F(Interleaved, Test12) { ASSERT_EQ(suites_running, 1); }
TEST_F(InterleavedB,Test2)469 TEST_F(InterleavedB, Test2) { ASSERT_EQ(suites_running, 1); }
TEST_F(InterleavedA,Test2)470 TEST_F(InterleavedA, Test2) { ASSERT_EQ(suites_running, 1); }
471
472 } // namespace
473 } // namespace pw
474