1 /*
2 * Copyright 2019 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 #include "packet/packet_view.h"
18
19 #include <gtest/gtest.h>
20 #include <forward_list>
21 #include <memory>
22
23 #include "hci/address.h"
24
25 using bluetooth::hci::Address;
26 using bluetooth::packet::PacketView;
27 using bluetooth::packet::View;
28 using std::vector;
29
30 namespace {
31 vector<uint8_t> count_all = {
32 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
33 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
34 };
35
36 vector<uint8_t> count_1 = {
37 0x00,
38 0x01,
39 0x02,
40 };
41
42 vector<uint8_t> count_2 = {
43 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c,
44 };
45
46 vector<uint8_t> count_3 = {
47 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
48 };
49 } // namespace
50
51 namespace bluetooth {
52 namespace packet {
53
54 template <typename T>
55 class IteratorTest : public ::testing::Test {
56 public:
57 IteratorTest() = default;
58 ~IteratorTest() override = default;
59
SetUp()60 void SetUp() override {
61 packet = std::shared_ptr<T>(new T({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())}));
62 }
63
TearDown()64 void TearDown() override {
65 packet.reset();
66 }
67
68 std::shared_ptr<T> packet;
69 };
70
71 using PacketViewTypes = ::testing::Types<PacketView<true>, PacketView<false>>;
72 TYPED_TEST_CASE(IteratorTest, PacketViewTypes);
73
74 class IteratorExtractTest : public ::testing::Test {
75 public:
76 IteratorExtractTest() = default;
77 ~IteratorExtractTest() override = default;
78 };
79
80 template <typename T>
81 class PacketViewTest : public IteratorTest<T> {
82 public:
83 PacketViewTest() = default;
84 ~PacketViewTest() = default;
85 };
86
87 using PacketViewTypes = ::testing::Types<PacketView<true>, PacketView<false>>;
88 TYPED_TEST_CASE(PacketViewTest, PacketViewTypes);
89
90 class PacketViewMultiViewTest : public ::testing::Test {
91 public:
92 PacketViewMultiViewTest() = default;
93 ~PacketViewMultiViewTest() override = default;
94
95 const PacketView<true> single_view =
96 PacketView<true>({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
97 const PacketView<true> multi_view = PacketView<true>({
98 View(std::make_shared<const vector<uint8_t>>(count_1), 0, count_1.size()),
99 View(std::make_shared<const vector<uint8_t>>(count_2), 0, count_2.size()),
100 View(std::make_shared<const vector<uint8_t>>(count_3), 0, count_3.size()),
101 });
102 };
103
104 class PacketViewMultiViewAppendTest : public ::testing::Test {
105 public:
106 PacketViewMultiViewAppendTest() = default;
107 ~PacketViewMultiViewAppendTest() override = default;
108
109 class AppendedPacketView : public PacketView<true> {
110 public:
AppendedPacketView(PacketView<true> first,std::forward_list<PacketView<true>> to_append)111 AppendedPacketView(PacketView<true> first, std::forward_list<PacketView<true>> to_append)
112 : PacketView<true>(first) {
113 for (const auto& packet_view : to_append) {
114 Append(packet_view);
115 }
116 }
117 };
118 const PacketView<true> single_view =
119 PacketView<true>({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
120 const PacketView<true> multi_view = AppendedPacketView(
121 PacketView<true>({View(std::make_shared<const vector<uint8_t>>(count_1), 0, count_1.size())}),
122 {PacketView<true>({View(std::make_shared<const vector<uint8_t>>(count_2), 0, count_2.size())}),
123 PacketView<true>({View(std::make_shared<const vector<uint8_t>>(count_3), 0, count_3.size())})});
124 };
125
126 class ViewTest : public ::testing::Test {
127 public:
128 ViewTest() = default;
129 ~ViewTest() override = default;
130 };
131
TEST(IteratorExtractTest,extractLeTest)132 TEST(IteratorExtractTest, extractLeTest) {
133 PacketView<true> packet({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
134 auto general_case = packet.begin();
135
136 ASSERT_EQ(0x00, general_case.extract<uint8_t>());
137 ASSERT_EQ(0x0201, general_case.extract<uint16_t>());
138 ASSERT_EQ(0x06050403u, general_case.extract<uint32_t>());
139 ASSERT_EQ(0x0e0d0c0b0a090807u, general_case.extract<uint64_t>());
140 ASSERT_EQ(0x0f, general_case.extract<uint8_t>());
141 Address raw({0x10, 0x11, 0x12, 0x13, 0x14, 0x15});
142 ASSERT_EQ(raw, general_case.extract<Address>());
143 ASSERT_EQ(0x16, general_case.extract<uint8_t>());
144 }
145
TEST(IteratorExtractTest,extractBeTest)146 TEST(IteratorExtractTest, extractBeTest) {
147 PacketView<false> packet({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
148 auto general_case = packet.begin();
149
150 ASSERT_EQ(0x00, general_case.extract<uint8_t>());
151 ASSERT_EQ(0x0102, general_case.extract<uint16_t>());
152 ASSERT_EQ(0x03040506u, general_case.extract<uint32_t>());
153 ASSERT_EQ(0x0708090a0b0c0d0eu, general_case.extract<uint64_t>());
154 ASSERT_EQ(0x0f, general_case.extract<uint8_t>());
155 Address raw({0x15, 0x14, 0x13, 0x12, 0x11, 0x10});
156 ASSERT_EQ(raw, general_case.extract<Address>());
157 ASSERT_EQ(0x16, general_case.extract<uint8_t>());
158 }
159
TYPED_TEST(IteratorTest,extractBoundsDeathTest)160 TYPED_TEST(IteratorTest, extractBoundsDeathTest) {
161 auto bounds_test = this->packet->end();
162
163 ASSERT_DEATH(bounds_test.template extract<uint8_t>(), "");
164 ASSERT_DEATH(bounds_test.template extract<uint16_t>(), "");
165 ASSERT_DEATH(bounds_test.template extract<uint32_t>(), "");
166 ASSERT_DEATH(bounds_test.template extract<uint64_t>(), "");
167 }
168
TYPED_TEST(IteratorTest,dereferenceDeathTest)169 TYPED_TEST(IteratorTest, dereferenceDeathTest) {
170 auto dereference_test = this->packet->end();
171
172 ASSERT_DEATH(*dereference_test, "");
173 ASSERT_EQ(0x1f, *(dereference_test - 1));
174 }
175
TYPED_TEST(IteratorTest,plusEqTest)176 TYPED_TEST(IteratorTest, plusEqTest) {
177 auto plus_eq = this->packet->begin();
178 for (size_t i = 0; i < count_all.size(); i += 2) {
179 ASSERT_EQ(count_all[i], *plus_eq) << "+= test: Dereferenced iterator does not equal expected at index " << i;
180 plus_eq += 2;
181 }
182 }
183
TYPED_TEST(IteratorTest,preIncrementTest)184 TYPED_TEST(IteratorTest, preIncrementTest) {
185 auto plus_plus = this->packet->begin();
186 for (size_t i = 0; i < count_all.size() - 1; i++) {
187 ASSERT_EQ(count_all[i + 1], *(++plus_plus)) << "Pre-increment test: Dereferenced iterator does not equal expected "
188 << "at index " << i;
189 }
190 }
191
TYPED_TEST(IteratorTest,postIncrementTest)192 TYPED_TEST(IteratorTest, postIncrementTest) {
193 auto plus_plus = this->packet->begin();
194 for (size_t i = 0; i < count_all.size(); i++) {
195 ASSERT_EQ(count_all[i], plus_plus.operator*())
196 << "Post-increment test: Dereferenced iterator does not equal expected "
197 << "at index " << i;
198 plus_plus.operator++();
199 }
200 }
201
TYPED_TEST(IteratorTest,additionTest)202 TYPED_TEST(IteratorTest, additionTest) {
203 auto plus = this->packet->begin();
204 for (size_t i = 0; i < count_all.size(); i++) {
205 ASSERT_EQ(count_all[i], *plus) << "+ test: Dereferenced iterator does not equal expected at index " << i;
206 plus = plus + 1;
207 }
208 }
209
TYPED_TEST(IteratorTest,minusEqTest)210 TYPED_TEST(IteratorTest, minusEqTest) {
211 auto minus_eq = this->packet->end();
212 minus_eq -= 1;
213 size_t index = count_all.size() - 1;
214 for (size_t i = 0; index > i; i++) {
215 ASSERT_EQ(count_all[index], *minus_eq)
216 << "-= test: Dereferenced iterator does not equal expected at index " << index;
217 index -= i;
218 minus_eq -= i;
219 }
220 }
221
TYPED_TEST(IteratorTest,preDecrementTest)222 TYPED_TEST(IteratorTest, preDecrementTest) {
223 auto minus_minus = this->packet->end();
224 for (size_t i = count_all.size(); i > 0; i--) {
225 ASSERT_EQ(count_all[i - 1], *(--minus_minus))
226 << "Pre-decrement test: Dereferenced iterator does not equal expected "
227 << "at index " << i;
228 }
229 }
230
TYPED_TEST(IteratorTest,postDecrementTest)231 TYPED_TEST(IteratorTest, postDecrementTest) {
232 auto minus_minus = this->packet->end();
233 minus_minus.operator--();
234 for (size_t i = count_all.size() - 1; i > 0; i--) {
235 ASSERT_EQ(count_all[i], minus_minus.operator*())
236 << "Post-decrement test: Dereferenced iterator does not equal expected "
237 << "at index " << i;
238 minus_minus.operator--();
239 }
240 }
241
TYPED_TEST(IteratorTest,subtractionTest)242 TYPED_TEST(IteratorTest, subtractionTest) {
243 auto minus = this->packet->end();
244 minus = minus - 1;
245 for (size_t i = count_all.size() - 1; i > 0; i--) {
246 ASSERT_EQ(count_all[i], *minus) << "- test: Dereferenced iterator does not equal expected at index " << i;
247 minus = minus - 1;
248 }
249 }
250
TYPED_TEST(IteratorTest,differenceTest)251 TYPED_TEST(IteratorTest, differenceTest) {
252 auto begin = this->packet->begin();
253 auto end = this->packet->end();
254 int difference = end - begin;
255 ASSERT_EQ(difference, static_cast<int>(count_all.size()));
256 int neg_difference = begin - end;
257 ASSERT_EQ(neg_difference, -static_cast<int>(count_all.size()));
258 }
259
TYPED_TEST(IteratorTest,equalityTest)260 TYPED_TEST(IteratorTest, equalityTest) {
261 auto begin = this->packet->begin();
262 auto end = this->packet->end();
263 auto begin_copy = this->packet->begin();
264 auto end_copy = this->packet->end();
265 ASSERT_EQ(begin_copy, begin);
266 ASSERT_EQ(end_copy, end);
267 }
268
TYPED_TEST(IteratorTest,comparisonsTest)269 TYPED_TEST(IteratorTest, comparisonsTest) {
270 auto begin = this->packet->begin();
271 auto end = this->packet->end();
272 auto begin_copy = this->packet->begin();
273 auto end_copy = this->packet->end();
274 ASSERT_EQ(begin_copy, begin);
275 ASSERT_EQ(end_copy, end);
276 ASSERT_NE(begin, end);
277 ASSERT_TRUE(begin < end);
278 ASSERT_FALSE(end < end);
279 ASSERT_FALSE(end < begin);
280 ASSERT_FALSE(begin > end);
281 ASSERT_FALSE(end > end);
282 ASSERT_TRUE(end > begin);
283 ASSERT_TRUE(begin <= end);
284 ASSERT_TRUE(end <= end);
285 ASSERT_FALSE(end <= begin);
286 ASSERT_FALSE(begin >= end);
287 ASSERT_TRUE(end >= end);
288 ASSERT_TRUE(end >= begin);
289 }
290
TYPED_TEST(PacketViewTest,getLengthTest)291 TYPED_TEST(PacketViewTest, getLengthTest) {
292 size_t length = this->packet->size();
293 ASSERT_EQ(length, count_all.size());
294 }
295
TYPED_TEST(PacketViewTest,getAtIndexTest)296 TYPED_TEST(PacketViewTest, getAtIndexTest) {
297 size_t past_end = this->packet->size();
298 ASSERT_DEATH(this->packet->at(past_end), "");
299 size_t working_index = 0x1f;
300 ASSERT_EQ(0x1f, this->packet->at(working_index));
301 }
302
TYPED_TEST(PacketViewTest,arrayOperatorTest)303 TYPED_TEST(PacketViewTest, arrayOperatorTest) {
304 size_t past_end = this->packet->size();
305 ASSERT_DEATH((*(this->packet))[past_end], "");
306 size_t working_index = 0x1f;
307 ASSERT_EQ(0x1f, (*(this->packet))[working_index]);
308 }
309
TYPED_TEST(IteratorTest,numBytesRemainingTest)310 TYPED_TEST(IteratorTest, numBytesRemainingTest) {
311 auto all = this->packet->begin();
312 size_t remaining = all.NumBytesRemaining();
313 for (size_t n = remaining; n > 0; n--) {
314 ASSERT_EQ(remaining, all.NumBytesRemaining());
315 all.operator++();
316 remaining--;
317 }
318 ASSERT_EQ(static_cast<size_t>(0), all.NumBytesRemaining());
319 all.operator++();
320 ASSERT_DEATH(all.operator*(), "");
321 all.operator++();
322 ASSERT_EQ(static_cast<size_t>(0), all.NumBytesRemaining());
323 all.operator++();
324 ASSERT_DEATH(all.operator*(), "");
325 }
326
TYPED_TEST(IteratorTest,subrangeTest)327 TYPED_TEST(IteratorTest, subrangeTest) {
328 auto empty = this->packet->begin().Subrange(0, 0);
329 ASSERT_EQ(static_cast<size_t>(0), empty.NumBytesRemaining());
330 ASSERT_DEATH(*empty, "");
331
332 empty = this->packet->begin().Subrange(this->packet->size(), 1);
333 ASSERT_EQ(static_cast<size_t>(0), empty.NumBytesRemaining());
334 ASSERT_DEATH(*empty, "");
335
336 auto all = this->packet->begin();
337 auto fullrange = all.Subrange(0, all.NumBytesRemaining());
338 ASSERT_EQ(all.NumBytesRemaining(), fullrange.NumBytesRemaining());
339 ASSERT_EQ(*(all + 1), 1);
340
341 fullrange = all.Subrange(0, all.NumBytesRemaining() + 1);
342 ASSERT_EQ(all.NumBytesRemaining(), fullrange.NumBytesRemaining());
343 ASSERT_EQ(*(all + 1), 1);
344
345 fullrange = all.Subrange(0, all.NumBytesRemaining() + 10);
346 ASSERT_EQ(all.NumBytesRemaining(), fullrange.NumBytesRemaining());
347 ASSERT_EQ(*(all + 1), 1);
348
349 auto subrange = all.Subrange(0, 1);
350 ASSERT_EQ(1, subrange.NumBytesRemaining());
351 ASSERT_EQ(*(subrange), 0);
352
353 subrange = this->packet->begin().Subrange(0, 4);
354 ASSERT_EQ(4, subrange.NumBytesRemaining());
355 ASSERT_EQ(*(subrange + 1), 1);
356
357 subrange = all.Subrange(0, 3);
358 ASSERT_EQ(3, subrange.NumBytesRemaining());
359 ASSERT_EQ(*(subrange + 1), 1);
360
361 subrange = all.Subrange(0, all.NumBytesRemaining() - 1);
362 ASSERT_EQ(all.NumBytesRemaining() - 1, subrange.NumBytesRemaining());
363 ASSERT_EQ(*(subrange + 1), 1);
364
365 subrange = all.Subrange(0, all.NumBytesRemaining() - 2);
366 ASSERT_EQ(all.NumBytesRemaining() - 2, subrange.NumBytesRemaining());
367 ASSERT_EQ(*(subrange + 1), 1);
368
369 subrange = all.Subrange(1, all.NumBytesRemaining());
370 ASSERT_EQ(all.NumBytesRemaining() - 1, subrange.NumBytesRemaining());
371 ASSERT_EQ(*subrange, 1);
372
373 subrange = all.Subrange(2, all.NumBytesRemaining());
374 ASSERT_EQ(all.NumBytesRemaining() - 2, subrange.NumBytesRemaining());
375 ASSERT_EQ(*subrange, 2);
376
377 subrange = all.Subrange(1, all.NumBytesRemaining() - 1);
378 ASSERT_EQ(all.NumBytesRemaining() - 1, subrange.NumBytesRemaining());
379 ASSERT_EQ(*subrange, 1);
380
381 subrange = all.Subrange(2, all.NumBytesRemaining() - 2);
382 ASSERT_EQ(all.NumBytesRemaining() - 2, subrange.NumBytesRemaining());
383 ASSERT_EQ(*subrange, 2);
384
385 subrange = all.Subrange(1, 1);
386 ASSERT_EQ(1, subrange.NumBytesRemaining());
387 ASSERT_EQ(*(subrange), 1);
388
389 subrange = all.Subrange(1, 2);
390 ASSERT_EQ(2, subrange.NumBytesRemaining());
391 ASSERT_EQ(*(subrange), 1);
392
393 subrange = all.Subrange(2, 1);
394 ASSERT_EQ(1, subrange.NumBytesRemaining());
395 ASSERT_EQ(*(subrange), 2);
396
397 subrange = this->packet->begin().Subrange(this->packet->size() - 1, 2);
398 ASSERT_EQ(static_cast<size_t>(1), subrange.NumBytesRemaining());
399 ASSERT_EQ(*(subrange), this->packet->size() - 1);
400 }
401
402 using SubviewTestParam = std::pair<size_t, size_t>;
403 class SubviewBaseTest : public ::testing::TestWithParam<SubviewTestParam> {
404 public:
405 class SubPacketView : public PacketView<true> {
406 public:
407 using PacketView<true>::PacketView;
Slice(size_t header,size_t tail)408 PacketView<true> Slice(size_t header, size_t tail) {
409 return PacketView<true>::GetLittleEndianSubview(header, tail);
410 }
411 };
412 };
413
414 class SubviewPassTest : public SubviewBaseTest {};
415
TEST_P(SubviewPassTest,subviewTest)416 TEST_P(SubviewPassTest, subviewTest) {
417 auto header = GetParam().first;
418 auto tail = GetParam().second;
419 SubPacketView single_view({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
420 SubPacketView multi_view({
421 View(std::make_shared<const vector<uint8_t>>(count_1), 0, count_1.size()),
422 View(std::make_shared<const vector<uint8_t>>(count_2), 0, count_2.size()),
423 View(std::make_shared<const vector<uint8_t>>(count_3), 0, count_3.size()),
424 });
425
426 auto single_slice = single_view.Slice(header, tail);
427 auto multi_slice = multi_view.Slice(header, tail);
428
429 ASSERT_EQ(single_slice.size(), tail - header);
430 ASSERT_EQ(single_slice.size(), multi_slice.size());
431 for (size_t i = 0; i < single_slice.size(); i++) {
432 ASSERT_EQ(single_slice[i], multi_slice[i]);
433 }
434 }
435
436 static const size_t boundary_1 = count_1.size();
437 static const size_t boundary_2 = count_1.size() + count_2.size();
438
439 INSTANTIATE_TEST_CASE_P(
440 chopomatic, SubviewPassTest,
441 ::testing::Values(
442 // {begin, end} pairs for subsets into the PacketView
443 SubviewTestParam{0, 0}, SubviewTestParam{0, boundary_1}, SubviewTestParam{0, boundary_1 + 1},
444 SubviewTestParam{0, boundary_2}, SubviewTestParam{0, boundary_2 + 1}, SubviewTestParam{0, count_all.size()},
445 SubviewTestParam{boundary_1 - 1, boundary_1}, SubviewTestParam{boundary_1 - 1, boundary_1 + 1},
446 SubviewTestParam{boundary_1 - 1, boundary_2}, SubviewTestParam{boundary_1 - 1, boundary_2 + 1},
447 SubviewTestParam{boundary_1 - 1, count_all.size()}, SubviewTestParam{boundary_1, boundary_1},
448 SubviewTestParam{boundary_1, boundary_2}, SubviewTestParam{boundary_1, boundary_2 + 1},
449 SubviewTestParam{boundary_1, count_all.size()}, SubviewTestParam{boundary_2 - 1, boundary_2},
450 SubviewTestParam{boundary_2 - 1, boundary_2 + 1}, SubviewTestParam{boundary_2 - 1, count_all.size()},
451 SubviewTestParam{boundary_2, boundary_2}, SubviewTestParam{boundary_2, boundary_2 + 1},
452 SubviewTestParam{boundary_2, count_all.size()}, SubviewTestParam{count_all.size() - 1, count_all.size()},
453 SubviewTestParam{count_all.size(), count_all.size()}));
454
455 class SubviewDeathTest : public SubviewBaseTest {};
456
TEST_P(SubviewDeathTest,subviewDeathTest)457 TEST_P(SubviewDeathTest, subviewDeathTest) {
458 auto header = GetParam().first;
459 auto tail = GetParam().second;
460 SubPacketView single_view({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
461 SubPacketView multi_view({
462 View(std::make_shared<const vector<uint8_t>>(count_1), 0, count_1.size()),
463 View(std::make_shared<const vector<uint8_t>>(count_2), 0, count_2.size()),
464 View(std::make_shared<const vector<uint8_t>>(count_3), 0, count_3.size()),
465 });
466
467 ASSERT_DEATH(auto single_slice = single_view.Slice(header, tail), "");
468 ASSERT_DEATH(auto multi_slice = multi_view.Slice(header, tail), "");
469 }
470
471 INSTANTIATE_TEST_CASE_P(chopomaticDeath, SubviewDeathTest,
472 ::testing::Values(
473 // {begin, end} pairs for subsets into the PacketView
474 SubviewTestParam{1, 0}, SubviewTestParam{count_all.size(), count_all.size() - 1},
475 SubviewTestParam{count_all.size(), count_all.size() + 1}));
476
TEST(SubviewTest,simpleSubviewTest)477 TEST(SubviewTest, simpleSubviewTest) {
478 PacketView<true> view({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
479 PacketView<true> sub_1_view = view.GetLittleEndianSubview(0, view.size());
480 PacketView<true> sub_2_view = sub_1_view.GetLittleEndianSubview(0, sub_1_view.size());
481 PacketView<true> sub_3_view = sub_2_view.GetLittleEndianSubview(0, sub_2_view.size());
482 PacketView<true> sub_4_view = sub_3_view.GetLittleEndianSubview(0, sub_3_view.size());
483 ASSERT_EQ(sub_1_view.size(), view.size());
484 ASSERT_EQ(sub_2_view.size(), view.size());
485 ASSERT_EQ(sub_3_view.size(), view.size());
486 ASSERT_EQ(sub_4_view.size(), view.size());
487 }
488
TEST(SubviewTest,realSubviewTest)489 TEST(SubviewTest, realSubviewTest) {
490 PacketView<true> view({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
491 std::vector<PacketView<true>> sub_views{view};
492 for (size_t i = 1; i < 6; i++) {
493 size_t parent_size = sub_views[i - 1].size();
494 sub_views.push_back(sub_views[i - 1].GetLittleEndianSubview(1, parent_size - 1));
495 ASSERT_EQ(sub_views[i][0], i);
496 ASSERT_EQ(sub_views[i].size(), parent_size - 2);
497 }
498 }
499
TEST(SubviewTest,subSubviewTest)500 TEST(SubviewTest, subSubviewTest) {
501 PacketView<true> single_view({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
502 PacketView<true> multi_view({
503 View(std::make_shared<const vector<uint8_t>>(count_1), 0, count_1.size()),
504 View(std::make_shared<const vector<uint8_t>>(count_2), 0, count_2.size()),
505 View(std::make_shared<const vector<uint8_t>>(count_3), 0, count_3.size()),
506 });
507 ASSERT_EQ(single_view.size(), multi_view.size());
508 for (size_t i = 0; i < count_all.size() / 2; i++) {
509 PacketView<true> sub_single_view = single_view.GetLittleEndianSubview(i, count_all.size() - i);
510 PacketView<true> sub_multi_view = multi_view.GetLittleEndianSubview(i, count_all.size() - i);
511 ASSERT_EQ(count_all.size() - 2 * i, sub_single_view.size());
512 ASSERT_EQ(sub_single_view.size(), sub_multi_view.size());
513 for (size_t j = 0; j < sub_single_view.size() / 2; j++) {
514 PacketView<true> sub_sub_single_view = sub_single_view.GetLittleEndianSubview(j, sub_single_view.size() - j);
515 PacketView<true> sub_sub_multi_view = sub_multi_view.GetLittleEndianSubview(j, sub_multi_view.size() - j);
516 ASSERT_EQ(sub_single_view.size() - 2 * j, sub_sub_single_view.size());
517 ASSERT_EQ(sub_sub_single_view.size(), sub_sub_multi_view.size());
518 }
519 }
520 }
521
TEST_F(PacketViewMultiViewTest,sizeTest)522 TEST_F(PacketViewMultiViewTest, sizeTest) {
523 ASSERT_EQ(single_view.size(), multi_view.size());
524 }
525
TEST_F(PacketViewMultiViewTest,dereferenceTestLittleEndian)526 TEST_F(PacketViewMultiViewTest, dereferenceTestLittleEndian) {
527 auto single_itr = single_view.begin();
528 auto multi_itr = multi_view.begin();
529 for (size_t i = 0; i < single_view.size(); i++) {
530 ASSERT_EQ(single_itr.operator*(), multi_itr.operator*());
531 single_itr.operator++();
532 multi_itr.operator++();
533 }
534 ASSERT_DEATH(*multi_itr, "");
535 }
536
TEST_F(PacketViewMultiViewTest,dereferenceTestBigEndian)537 TEST_F(PacketViewMultiViewTest, dereferenceTestBigEndian) {
538 auto single_itr = single_view.begin();
539 auto multi_itr = multi_view.begin();
540 for (size_t i = 0; i < single_view.size(); i++) {
541 ASSERT_EQ(single_itr.operator*(), multi_itr.operator*());
542 single_itr.operator++();
543 multi_itr.operator++();
544 }
545 ASSERT_DEATH(*multi_itr, "");
546 }
547
TEST_F(PacketViewMultiViewTest,arrayOperatorTest)548 TEST_F(PacketViewMultiViewTest, arrayOperatorTest) {
549 for (size_t i = 0; i < single_view.size(); i++) {
550 ASSERT_EQ(single_view[i], multi_view[i]);
551 }
552 ASSERT_DEATH(multi_view[single_view.size()], "");
553 }
554
TEST_F(PacketViewMultiViewAppendTest,sizeTestAppend)555 TEST_F(PacketViewMultiViewAppendTest, sizeTestAppend) {
556 ASSERT_EQ(single_view.size(), multi_view.size());
557 }
558
TEST_F(PacketViewMultiViewAppendTest,dereferenceTestLittleEndianAppend)559 TEST_F(PacketViewMultiViewAppendTest, dereferenceTestLittleEndianAppend) {
560 auto single_itr = single_view.begin();
561 auto multi_itr = multi_view.begin();
562 for (size_t i = 0; i < single_view.size(); i++) {
563 ASSERT_EQ(single_itr.operator*(), multi_itr.operator*());
564 single_itr.operator++();
565 multi_itr.operator++();
566 }
567 ASSERT_DEATH(*multi_itr, "");
568 }
569
TEST_F(PacketViewMultiViewAppendTest,dereferenceTestBigEndianAppend)570 TEST_F(PacketViewMultiViewAppendTest, dereferenceTestBigEndianAppend) {
571 auto single_itr = single_view.begin();
572 auto multi_itr = multi_view.begin();
573 for (size_t i = 0; i < single_view.size(); i++) {
574 ASSERT_EQ(single_itr.operator*(), multi_itr.operator*());
575 single_itr.operator++();
576 multi_itr.operator++();
577 }
578 ASSERT_DEATH(*multi_itr, "");
579 }
580
TEST_F(PacketViewMultiViewAppendTest,arrayOperatorTestAppend)581 TEST_F(PacketViewMultiViewAppendTest, arrayOperatorTestAppend) {
582 for (size_t i = 0; i < single_view.size(); i++) {
583 ASSERT_EQ(single_view[i], multi_view[i]);
584 }
585 ASSERT_DEATH(multi_view[single_view.size()], "");
586 }
587
TEST(ViewTest,arrayOperatorTest)588 TEST(ViewTest, arrayOperatorTest) {
589 View view_all(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size());
590 size_t past_end = view_all.size();
591 for (size_t i = 0; i < past_end; i++) {
592 ASSERT_EQ(view_all[i], count_all[i]);
593 }
594 ASSERT_DEATH(view_all[past_end], "");
595
596 size_t header_size = 2;
597 size_t tail_size = 3;
598 View view_subset(std::make_shared<const vector<uint8_t>>(count_all), header_size, count_all.size() - tail_size);
599 View view_subset2(view_all, header_size, count_all.size() - tail_size);
600 size_t subset_length = view_subset.size();
601 for (size_t i = 0; i < subset_length; i++) {
602 ASSERT_EQ(view_subset[i], count_all[header_size + i]);
603 ASSERT_EQ(view_subset[i], view_subset2[i]);
604 }
605 ASSERT_DEATH(view_subset[subset_length + 1], "");
606 ASSERT_DEATH(view_subset2[subset_length + 1], "");
607 }
608
TEST(ViewTest,earlySubSubviewTest)609 TEST(ViewTest, earlySubSubviewTest) {
610 View view(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size());
611 View sub_1_view(view, view.size() - 3, view.size() - 1);
612 View sub_2_view(sub_1_view, 1, 2);
613 ASSERT_EQ(sub_1_view.size(), 2u);
614 ASSERT_EQ(sub_2_view.size(), 1u);
615 }
616
TEST(ViewTest,subSubviewTest)617 TEST(ViewTest, subSubviewTest) {
618 View view(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size());
619 std::vector<View> sub_views{view};
620 for (size_t i = 1; i < 6; i++) {
621 size_t parent_size = sub_views[i - 1].size();
622 sub_views.push_back({View(sub_views[i - 1], 1, parent_size - 1)});
623 ASSERT_EQ(sub_views[i][0], i);
624 ASSERT_EQ(sub_views[i].size(), parent_size - 2);
625 }
626 }
627
TEST(ViewTest,zeroSubviewTest)628 TEST(ViewTest, zeroSubviewTest) {
629 View view(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size());
630 View subview(view, view.size(), view.size() + 1);
631 ASSERT_EQ(subview.size(), 0u);
632 }
633 } // namespace packet
634 } // namespace bluetooth
635