1 // Copyright 2019 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "platform/api/serial_delete_ptr.h"
6
7 #include "gtest/gtest.h"
8 #include "platform/test/fake_clock.h"
9 #include "platform/test/fake_task_runner.h"
10
11 namespace openscreen {
12
13 class SerialDeletePtrTest : public ::testing::Test {
14 public:
SerialDeletePtrTest()15 SerialDeletePtrTest() : clock_(Clock::now()), task_runner_(&clock_) {}
16
17 protected:
FunctionPointerDeleter(int * pointer)18 static void FunctionPointerDeleter(int* pointer) {
19 deleter_called_ = true;
20 delete pointer;
21 }
22
23 FakeClock clock_;
24 FakeTaskRunner task_runner_;
25
26 static bool deleter_called_;
27 };
28
29 // static
30 bool SerialDeletePtrTest::deleter_called_ = false;
31
TEST_F(SerialDeletePtrTest,Empty)32 TEST_F(SerialDeletePtrTest, Empty) {
33 SerialDeletePtr<int> pointer(&task_runner_);
34 }
35
TEST_F(SerialDeletePtrTest,Nullptr)36 TEST_F(SerialDeletePtrTest, Nullptr) {
37 SerialDeletePtr<int> pointer(&task_runner_, nullptr);
38 }
39
TEST_F(SerialDeletePtrTest,DefaultDeleter)40 TEST_F(SerialDeletePtrTest, DefaultDeleter) {
41 { SerialDeletePtr<int> pointer(&task_runner_, new int); }
42 task_runner_.RunTasksUntilIdle();
43 }
44
TEST_F(SerialDeletePtrTest,FuncitonPointerDeleter)45 TEST_F(SerialDeletePtrTest, FuncitonPointerDeleter) {
46 deleter_called_ = false;
47 {
48 SerialDeletePtr<int, decltype(&FunctionPointerDeleter)> pointer(
49 &task_runner_, new int, FunctionPointerDeleter);
50 }
51 task_runner_.RunTasksUntilIdle();
52 EXPECT_TRUE(deleter_called_);
53 }
54
TEST_F(SerialDeletePtrTest,LambdaDeleter)55 TEST_F(SerialDeletePtrTest, LambdaDeleter) {
56 deleter_called_ = false;
57 auto deleter = [](int* pointer) {
58 deleter_called_ = true;
59 delete pointer;
60 };
61
62 {
63 SerialDeletePtr<int, decltype(deleter)> pointer(&task_runner_, new int,
64 deleter);
65 }
66
67 task_runner_.RunTasksUntilIdle();
68 EXPECT_TRUE(deleter_called_);
69 }
70
TEST_F(SerialDeletePtrTest,BindDeleter)71 TEST_F(SerialDeletePtrTest, BindDeleter) {
72 deleter_called_ = false;
73 auto deleter = std::bind(FunctionPointerDeleter, std::placeholders::_1);
74
75 {
76 SerialDeletePtr<int, decltype(deleter)> pointer(&task_runner_, new int,
77 deleter);
78 }
79
80 task_runner_.RunTasksUntilIdle();
81 EXPECT_TRUE(deleter_called_);
82 }
83
TEST_F(SerialDeletePtrTest,FunctionDeleter)84 TEST_F(SerialDeletePtrTest, FunctionDeleter) {
85 deleter_called_ = false;
86 std::function<void(int*)> deleter = FunctionPointerDeleter;
87
88 {
89 SerialDeletePtr<int, std::function<void(int*)>> pointer(&task_runner_,
90 new int, deleter);
91 }
92
93 task_runner_.RunTasksUntilIdle();
94 EXPECT_TRUE(deleter_called_);
95 }
96
TEST_F(SerialDeletePtrTest,FunctionDeleterWithFunctionPointer)97 TEST_F(SerialDeletePtrTest, FunctionDeleterWithFunctionPointer) {
98 deleter_called_ = false;
99
100 {
101 SerialDeletePtr<int, std::function<void(int*)>> pointer(
102 &task_runner_, new int, FunctionPointerDeleter);
103 }
104
105 task_runner_.RunTasksUntilIdle();
106 EXPECT_TRUE(deleter_called_);
107 }
108
TEST_F(SerialDeletePtrTest,FunctionDeleterWithLambda)109 TEST_F(SerialDeletePtrTest, FunctionDeleterWithLambda) {
110 deleter_called_ = false;
111 auto deleter = [](int* pointer) {
112 deleter_called_ = true;
113 delete pointer;
114 };
115
116 {
117 SerialDeletePtr<int, std::function<void(int*)>> pointer(&task_runner_,
118 new int, deleter);
119 }
120
121 task_runner_.RunTasksUntilIdle();
122 EXPECT_TRUE(deleter_called_);
123 }
124
TEST_F(SerialDeletePtrTest,FunctionDeleterWithBind)125 TEST_F(SerialDeletePtrTest, FunctionDeleterWithBind) {
126 deleter_called_ = false;
127 auto deleter = std::bind(FunctionPointerDeleter, std::placeholders::_1);
128
129 {
130 SerialDeletePtr<int, std::function<void(int*)>> pointer(&task_runner_,
131 new int, deleter);
132 }
133
134 task_runner_.RunTasksUntilIdle();
135 EXPECT_TRUE(deleter_called_);
136 }
137
TEST_F(SerialDeletePtrTest,StructDeleter)138 TEST_F(SerialDeletePtrTest, StructDeleter) {
139 struct TestDeleter {
140 void operator()(int* pointer) const { delete pointer; }
141 };
142
143 TestDeleter deleter;
144 {
145 SerialDeletePtr<int, TestDeleter> pointer(&task_runner_, new int, deleter);
146 }
147
148 task_runner_.RunTasksUntilIdle();
149 }
150
TEST_F(SerialDeletePtrTest,Move)151 TEST_F(SerialDeletePtrTest, Move) {
152 deleter_called_ = false;
153
154 {
155 SerialDeletePtr<int, decltype(&FunctionPointerDeleter)> pointer(
156 &task_runner_);
157 {
158 SerialDeletePtr<int, decltype(&FunctionPointerDeleter)> temp_pointer(
159 &task_runner_, new int, FunctionPointerDeleter);
160 pointer = std::move(temp_pointer);
161
162 // No deletion should happen on move
163 task_runner_.RunTasksUntilIdle();
164 EXPECT_FALSE(deleter_called_);
165 }
166 }
167
168 task_runner_.RunTasksUntilIdle();
169 EXPECT_TRUE(deleter_called_);
170 }
171
172 } // namespace openscreen
173