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