xref: /aosp_15_r20/external/google-breakpad/src/common/byte_cursor_unittest.cc (revision 9712c20fc9bbfbac4935993a2ca0b3958c5adad2)
1 // Copyright 2010 Google LLC
2 //
3 // Redistribution and use in source and binary forms, with or without
4 // modification, are permitted provided that the following conditions are
5 // met:
6 //
7 //     * Redistributions of source code must retain the above copyright
8 // notice, this list of conditions and the following disclaimer.
9 //     * Redistributions in binary form must reproduce the above
10 // copyright notice, this list of conditions and the following disclaimer
11 // in the documentation and/or other materials provided with the
12 // distribution.
13 //     * Neither the name of Google LLC nor the names of its
14 // contributors may be used to endorse or promote products derived from
15 // this software without specific prior written permission.
16 //
17 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
20 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
21 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
22 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
23 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 
29 // Original author: Jim Blandy <[email protected]> <[email protected]>
30 
31 // byte_cursor_unittest.cc: Unit tests for google_breakpad::ByteBuffer
32 // and google_breakpad::ByteCursor.
33 
34 #ifdef HAVE_CONFIG_H
35 #include <config.h>  // Must come first
36 #endif
37 
38 #include <string>
39 
40 #include <string.h>
41 
42 #include "breakpad_googletest_includes.h"
43 #include "common/byte_cursor.h"
44 #include "common/using_std_string.h"
45 
46 using google_breakpad::ByteBuffer;
47 using google_breakpad::ByteCursor;
48 
TEST(Buffer,SizeOfNothing)49 TEST(Buffer, SizeOfNothing) {
50   uint8_t data[1];
51   ByteBuffer buffer(data, 0);
52   EXPECT_EQ(0U, buffer.Size());
53 }
54 
TEST(Buffer,SizeOfSomething)55 TEST(Buffer, SizeOfSomething) {
56   uint8_t data[10];
57   ByteBuffer buffer(data, sizeof(data));
58   EXPECT_EQ(10U, buffer.Size());
59 }
60 
TEST(Extent,AvailableEmpty)61 TEST(Extent, AvailableEmpty) {
62   uint8_t data[1];
63   ByteBuffer buffer(data, 0);
64   ByteCursor cursor(&buffer);
65   EXPECT_EQ(0U, cursor.Available());
66 }
67 
TEST(Extent,AtEndEmpty)68 TEST(Extent, AtEndEmpty) {
69   uint8_t data[1];
70   ByteBuffer buffer(data, 0);
71   ByteCursor cursor(&buffer);
72   EXPECT_TRUE(cursor.AtEnd());
73 }
74 
TEST(Extent,AsBoolEmpty)75 TEST(Extent, AsBoolEmpty) {
76   uint8_t data[1];
77   ByteBuffer buffer(data, 0);
78   ByteCursor cursor(&buffer);
79   EXPECT_TRUE(cursor);
80 }
81 
TEST(Extent,AvailableSome)82 TEST(Extent, AvailableSome) {
83   uint8_t data[10];
84   ByteBuffer buffer(data, sizeof(data));
85   ByteCursor cursor(&buffer);
86   EXPECT_EQ(10U, cursor.Available());
87 }
88 
TEST(Extent,AtEndSome)89 TEST(Extent, AtEndSome) {
90   uint8_t data[10];
91   ByteBuffer buffer(data, sizeof(data));
92   ByteCursor cursor(&buffer);
93   EXPECT_FALSE(cursor.AtEnd());
94   EXPECT_TRUE(cursor.Skip(sizeof(data)).AtEnd());
95 }
96 
TEST(Extent,AsBoolSome)97 TEST(Extent, AsBoolSome) {
98   uint8_t data[10];
99   ByteBuffer buffer(data, sizeof(data));
100   ByteCursor cursor(&buffer);
101   EXPECT_TRUE(cursor);
102   EXPECT_TRUE(cursor.Skip(sizeof(data)));
103   EXPECT_FALSE(cursor.Skip(1));
104 }
105 
TEST(Extent,Cursor)106 TEST(Extent, Cursor) {
107   uint8_t data[] = { 0xf7,
108                      0x9f, 0xbe,
109                      0x67, 0xfb, 0xd3, 0x58,
110                      0x6f, 0x36, 0xde, 0xd1,
111                      0x2a, 0x2a, 0x2a };
112   ByteBuffer buffer(data, sizeof(data));
113   ByteCursor cursor(&buffer);
114 
115   uint8_t a;
116   uint16_t b;
117   uint32_t c;
118   uint32_t d;
119   uint8_t stars[3];
120 
121   EXPECT_EQ(data + 0U, cursor.here());
122 
123   EXPECT_TRUE(cursor >> a);
124   EXPECT_EQ(data + 1U, cursor.here());
125 
126   EXPECT_TRUE(cursor >> b);
127   EXPECT_EQ(data + 3U, cursor.here());
128 
129   EXPECT_TRUE(cursor >> c);
130   EXPECT_EQ(data + 7U, cursor.here());
131 
132   EXPECT_TRUE(cursor.Skip(4));
133   EXPECT_EQ(data + 11U, cursor.here());
134 
135   EXPECT_TRUE(cursor.Read(stars, 3));
136   EXPECT_EQ(data + 14U, cursor.here());
137 
138   EXPECT_FALSE(cursor >> d);
139   EXPECT_EQ(data + 14U, cursor.here());
140 }
141 
TEST(Extent,SetOffset)142 TEST(Extent, SetOffset) {
143   uint8_t data[] = { 0x5c, 0x79, 0x8c, 0xd5 };
144   ByteBuffer buffer(data, sizeof(data));
145   ByteCursor cursor(&buffer);
146 
147   uint8_t a, b, c, d, e;
148   EXPECT_TRUE(cursor >> a);
149   EXPECT_EQ(0x5cU, a);
150   EXPECT_EQ(data + 1U, cursor.here());
151   EXPECT_TRUE(((cursor >> b).set_here(data + 3) >> c).set_here(data + 1)
152               >> d >> e);
153   EXPECT_EQ(0x79U, b);
154   EXPECT_EQ(0xd5U, c);
155   EXPECT_EQ(0x79U, d);
156   EXPECT_EQ(0x8cU, e);
157   EXPECT_EQ(data + 3U, cursor.here());
158 }
159 
TEST(BigEndian,Signed1)160 TEST(BigEndian, Signed1) {
161   uint8_t data[] = { 0x00, 0x7f, 0x80, 0xff };
162   ByteBuffer buffer(data, sizeof(data));
163   ByteCursor cursor(&buffer);
164   cursor.set_big_endian(true);
165   int a, b, c, d, e;
166   ASSERT_TRUE(cursor
167               .Read(1, true, &a)
168               .Read(1, true, &b)
169               .Read(1, true, &c)
170               .Read(1, true, &d));
171   EXPECT_EQ(0,     a);
172   EXPECT_EQ(0x7f,  b);
173   EXPECT_EQ(-0x80, c);
174   EXPECT_EQ(-1,    d);
175   EXPECT_TRUE(cursor.AtEnd());
176   EXPECT_FALSE(cursor.Read(1, true, &e));
177 }
178 
TEST(BigEndian,Signed2)179 TEST(BigEndian, Signed2) {
180   uint8_t data[] = { 0x00, 0x00,   0x00, 0x80,   0x7f, 0xff,
181                      0x80, 0x00,   0x80, 0x80,   0xff, 0xff,
182                      0x39, 0xf1,   0x8a, 0xbc,   0x5a, 0xec };
183   ByteBuffer buffer(data, sizeof(data));
184   ByteCursor cursor(&buffer, true);
185   int a, b, c, d, e, f, g, h, i, j;
186   ASSERT_TRUE(cursor
187               .Read(2, true, &a)
188               .Read(2, true, &b)
189               .Read(2, true, &c)
190               .Read(2, true, &d)
191               .Read(2, true, &e)
192               .Read(2, true, &f)
193               .Read(2, true, &g)
194               .Read(2, true, &h)
195               .Read(2, true, &i));
196   EXPECT_EQ(0,       a);
197   EXPECT_EQ(0x80,    b);
198   EXPECT_EQ(0x7fff,  c);
199   EXPECT_EQ(-0x8000, d);
200   EXPECT_EQ(-0x7f80, e);
201   EXPECT_EQ(-1,      f);
202   EXPECT_EQ(0x39f1,  g);
203   EXPECT_EQ(-0x7544, h);
204   EXPECT_EQ(0x5aec,  i);
205   EXPECT_TRUE(cursor.AtEnd());
206   EXPECT_FALSE(cursor.Read(2, true, &j));
207 }
208 
TEST(BigEndian,Signed4)209 TEST(BigEndian, Signed4) {
210   uint8_t data[] = { 0x00, 0x00, 0x00, 0x00,
211                      0x7f, 0xff, 0xff, 0xff,
212                      0x80, 0x00, 0x00, 0x00,
213                      0xff, 0xff, 0xff, 0xff,
214                      0xb6, 0xb1, 0xff, 0xef,
215                      0x19, 0x6a, 0xca, 0x46 };
216   ByteBuffer buffer(data, sizeof(data));
217   ByteCursor cursor(&buffer);
218   cursor.set_big_endian(true);
219   int64_t a, b, c, d, e, f, g;
220   ASSERT_TRUE(cursor
221               .Read(4, true, &a)
222               .Read(4, true, &b)
223               .Read(4, true, &c)
224               .Read(4, true, &d)
225               .Read(4, true, &e)
226               .Read(4, true, &f));
227   EXPECT_EQ(0,                    a);
228   EXPECT_EQ(0x7fffffff,           b);
229   EXPECT_EQ(-0x80000000LL,        c);
230   EXPECT_EQ(-1,                   d);
231   EXPECT_EQ((int32_t) 0xb6b1ffef, e);
232   EXPECT_EQ(0x196aca46,           f);
233   EXPECT_TRUE(cursor.AtEnd());
234   EXPECT_FALSE(cursor.Read(4, true, &g));
235 }
236 
TEST(BigEndian,Signed8)237 TEST(BigEndian, Signed8) {
238   uint8_t data[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
239                      0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
240                      0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
241                      0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
242                      0x93, 0x20, 0xd5, 0xe9, 0xd2, 0xd5, 0x87, 0x9c,
243                      0x4e, 0x42, 0x49, 0xd2, 0x7f, 0x84, 0x14, 0xa4 };
244   ByteBuffer buffer(data, sizeof(data));
245   ByteCursor cursor(&buffer, true);
246   int64_t a, b, c, d, e, f, g;
247   ASSERT_TRUE(cursor
248               .Read(8, true, &a)
249               .Read(8, true, &b)
250               .Read(8, true, &c)
251               .Read(8, true, &d)
252               .Read(8, true, &e)
253               .Read(8, true, &f));
254   EXPECT_EQ(0,                               a);
255   EXPECT_EQ(0x7fffffffffffffffLL,            b);
256   EXPECT_EQ(-0x7fffffffffffffffLL - 1,       c);
257   EXPECT_EQ(-1,                              d);
258   EXPECT_EQ((int64_t) 0x9320d5e9d2d5879cULL, e);
259   EXPECT_EQ(0x4e4249d27f8414a4LL,            f);
260   EXPECT_TRUE(cursor.AtEnd());
261   EXPECT_FALSE(cursor.Read(8, true, &g));
262 }
263 
TEST(BigEndian,Unsigned1)264 TEST(BigEndian, Unsigned1) {
265   uint8_t data[] = { 0x00, 0x7f, 0x80, 0xff };
266   ByteBuffer buffer(data, sizeof(data));
267   ByteCursor cursor(&buffer);
268   cursor.set_big_endian(true);
269   int32_t a, b, c, d, e;
270   ASSERT_TRUE(cursor
271               .Read(1, false, &a)
272               .Read(1, false, &b)
273               .Read(1, false, &c)
274               .Read(1, false, &d));
275   EXPECT_EQ(0,    a);
276   EXPECT_EQ(0x7f, b);
277   EXPECT_EQ(0x80, c);
278   EXPECT_EQ(0xff, d);
279   EXPECT_TRUE(cursor.AtEnd());
280   EXPECT_FALSE(cursor.Read(1, false, &e));
281 }
282 
TEST(BigEndian,Unsigned2)283 TEST(BigEndian, Unsigned2) {
284   uint8_t data[] = { 0x00, 0x00,   0x00, 0x80,   0x7f, 0xff,
285                      0x80, 0x00,   0x80, 0x80,   0xff, 0xff,
286                      0x39, 0xf1,   0x8a, 0xbc,   0x5a, 0xec };
287   ByteBuffer buffer(data, sizeof(data));
288   ByteCursor cursor(&buffer, true);
289   int64_t a, b, c, d, e, f, g, h, i, j;
290   ASSERT_TRUE(cursor
291               .Read(2, false, &a)
292               .Read(2, false, &b)
293               .Read(2, false, &c)
294               .Read(2, false, &d)
295               .Read(2, false, &e)
296               .Read(2, false, &f)
297               .Read(2, false, &g)
298               .Read(2, false, &h)
299               .Read(2, false, &i));
300   EXPECT_EQ(0,      a);
301   EXPECT_EQ(0x80,   b);
302   EXPECT_EQ(0x7fff, c);
303   EXPECT_EQ(0x8000, d);
304   EXPECT_EQ(0x8080, e);
305   EXPECT_EQ(0xffff, f);
306   EXPECT_EQ(0x39f1, g);
307   EXPECT_EQ(0x8abc, h);
308   EXPECT_EQ(0x5aec, i);
309   EXPECT_TRUE(cursor.AtEnd());
310   EXPECT_FALSE(cursor.Read(2, false, &j));
311 }
312 
TEST(BigEndian,Unsigned4)313 TEST(BigEndian, Unsigned4) {
314   uint8_t data[] = { 0x00, 0x00, 0x00, 0x00,
315                      0x7f, 0xff, 0xff, 0xff,
316                      0x80, 0x00, 0x00, 0x00,
317                      0xff, 0xff, 0xff, 0xff,
318                      0xb6, 0xb1, 0xff, 0xef,
319                      0x19, 0x6a, 0xca, 0x46 };
320   ByteBuffer buffer(data, sizeof(data));
321   ByteCursor cursor(&buffer);
322   cursor.set_big_endian(true);
323   int64_t a, b, c, d, e, f, g;
324   ASSERT_TRUE(cursor
325               .Read(4, false, &a)
326               .Read(4, false, &b)
327               .Read(4, false, &c)
328               .Read(4, false, &d)
329               .Read(4, false, &e)
330               .Read(4, false, &f));
331   EXPECT_EQ(0,          a);
332   EXPECT_EQ(0x7fffffff, b);
333   EXPECT_EQ(0x80000000, c);
334   EXPECT_EQ(0xffffffff, d);
335   EXPECT_EQ(0xb6b1ffef, e);
336   EXPECT_EQ(0x196aca46, f);
337   EXPECT_TRUE(cursor.AtEnd());
338   EXPECT_FALSE(cursor.Read(4, false, &g));
339 }
340 
TEST(BigEndian,Unsigned8)341 TEST(BigEndian, Unsigned8) {
342   uint8_t data[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
343                      0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
344                      0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
345                      0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
346                      0x93, 0x20, 0xd5, 0xe9, 0xd2, 0xd5, 0x87, 0x9c,
347                      0x4e, 0x42, 0x49, 0xd2, 0x7f, 0x84, 0x14, 0xa4 };
348   ByteBuffer buffer(data, sizeof(data));
349   ByteCursor cursor(&buffer, true);
350   uint64_t a, b, c, d, e, f, g;
351   ASSERT_TRUE(cursor
352               .Read(8, false, &a)
353               .Read(8, false, &b)
354               .Read(8, false, &c)
355               .Read(8, false, &d)
356               .Read(8, false, &e)
357               .Read(8, false, &f));
358   EXPECT_EQ(0U,                    a);
359   EXPECT_EQ(0x7fffffffffffffffULL, b);
360   EXPECT_EQ(0x8000000000000000ULL, c);
361   EXPECT_EQ(0xffffffffffffffffULL, d);
362   EXPECT_EQ(0x9320d5e9d2d5879cULL, e);
363   EXPECT_EQ(0x4e4249d27f8414a4ULL, f);
364   EXPECT_TRUE(cursor.AtEnd());
365   EXPECT_FALSE(cursor.Read(8, false, &g));
366 }
367 
TEST(LittleEndian,Signed1)368 TEST(LittleEndian, Signed1) {
369   uint8_t data[] = { 0x00, 0x7f, 0x80, 0xff };
370   ByteBuffer buffer(data, sizeof(data));
371   ByteCursor cursor(&buffer);
372   int32_t a, b, c, d, e;
373   ASSERT_TRUE(cursor
374               .Read(1, true, &a)
375               .Read(1, true, &b)
376               .Read(1, true, &c)
377               .Read(1, true, &d));
378   EXPECT_EQ(0,     a);
379   EXPECT_EQ(0x7f,  b);
380   EXPECT_EQ(-0x80, c);
381   EXPECT_EQ(-1,    d);
382   EXPECT_TRUE(cursor.AtEnd());
383   EXPECT_FALSE(cursor.Read(1, true, &e));
384 }
385 
TEST(LittleEndian,Signed2)386 TEST(LittleEndian, Signed2) {
387   uint8_t data[] = { 0x00, 0x00,   0x80, 0x00,   0xff, 0x7f,
388                      0x00, 0x80,   0x80, 0x80,   0xff, 0xff,
389                      0xf1, 0x39,   0xbc, 0x8a,   0xec, 0x5a };
390   ByteBuffer buffer(data, sizeof(data));
391   ByteCursor cursor(&buffer, false);
392   int32_t a, b, c, d, e, f, g, h, i, j;
393   ASSERT_TRUE(cursor
394               .Read(2, true, &a)
395               .Read(2, true, &b)
396               .Read(2, true, &c)
397               .Read(2, true, &d)
398               .Read(2, true, &e)
399               .Read(2, true, &f)
400               .Read(2, true, &g)
401               .Read(2, true, &h)
402               .Read(2, true, &i));
403   EXPECT_EQ(0,       a);
404   EXPECT_EQ(0x80,    b);
405   EXPECT_EQ(0x7fff,  c);
406   EXPECT_EQ(-0x8000, d);
407   EXPECT_EQ(-0x7f80, e);
408   EXPECT_EQ(-1,      f);
409   EXPECT_EQ(0x39f1,  g);
410   EXPECT_EQ(-0x7544, h);
411   EXPECT_EQ(0x5aec,  i);
412   EXPECT_TRUE(cursor.AtEnd());
413   EXPECT_FALSE(cursor.Read(2, true, &j));
414 }
415 
TEST(LittleEndian,Signed4)416 TEST(LittleEndian, Signed4) {
417   uint8_t data[] = { 0x00, 0x00, 0x00, 0x00,
418                      0xff, 0xff, 0xff, 0x7f,
419                      0x00, 0x00, 0x00, 0x80,
420                      0xff, 0xff, 0xff, 0xff,
421                      0xef, 0xff, 0xb1, 0xb6,
422                      0x46, 0xca, 0x6a, 0x19 };
423   ByteBuffer buffer(data, sizeof(data));
424   ByteCursor cursor(&buffer);
425   int64_t a, b, c, d, e, f, g;
426   ASSERT_TRUE(cursor
427               .Read(4, true, &a)
428               .Read(4, true, &b)
429               .Read(4, true, &c)
430               .Read(4, true, &d)
431               .Read(4, true, &e)
432               .Read(4, true, &f));
433   EXPECT_EQ(0,                    a);
434   EXPECT_EQ(0x7fffffff,           b);
435   EXPECT_EQ(-0x80000000LL,        c);
436   EXPECT_EQ(-1,                   d);
437   EXPECT_EQ((int32_t) 0xb6b1ffef, e);
438   EXPECT_EQ(0x196aca46,           f);
439   EXPECT_TRUE(cursor.AtEnd());
440   EXPECT_FALSE(cursor.Read(4, true, &g));
441 }
442 
TEST(LittleEndian,Signed8)443 TEST(LittleEndian, Signed8) {
444   uint8_t data[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
445                      0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f,
446                      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80,
447                      0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
448                      0x9c, 0x87, 0xd5, 0xd2, 0xe9, 0xd5, 0x20, 0x93,
449                      0xa4, 0x14, 0x84, 0x7f, 0xd2, 0x49, 0x42, 0x4e };
450   ByteBuffer buffer(data, sizeof(data));
451   ByteCursor cursor(&buffer, false);
452   int64_t a, b, c, d, e, f, g;
453   ASSERT_TRUE(cursor
454               .Read(8, true, &a)
455               .Read(8, true, &b)
456               .Read(8, true, &c)
457               .Read(8, true, &d)
458               .Read(8, true, &e)
459               .Read(8, true, &f));
460   EXPECT_EQ(0,                               a);
461   EXPECT_EQ(0x7fffffffffffffffLL,            b);
462   EXPECT_EQ(-0x7fffffffffffffffLL - 1,       c);
463   EXPECT_EQ(-1,                              d);
464   EXPECT_EQ((int64_t) 0x9320d5e9d2d5879cULL, e);
465   EXPECT_EQ(0x4e4249d27f8414a4LL,            f);
466   EXPECT_TRUE(cursor.AtEnd());
467   EXPECT_FALSE(cursor.Read(8, true, &g));
468 }
469 
TEST(LittleEndian,Unsigned1)470 TEST(LittleEndian, Unsigned1) {
471   uint8_t data[] = { 0x00, 0x7f, 0x80, 0xff };
472   ByteBuffer buffer(data, sizeof(data));
473   ByteCursor cursor(&buffer);
474   int32_t a, b, c, d, e;
475   ASSERT_TRUE(cursor
476               .Read(1, false, &a)
477               .Read(1, false, &b)
478               .Read(1, false, &c)
479               .Read(1, false, &d));
480   EXPECT_EQ(0,    a);
481   EXPECT_EQ(0x7f, b);
482   EXPECT_EQ(0x80, c);
483   EXPECT_EQ(0xff, d);
484   EXPECT_TRUE(cursor.AtEnd());
485   EXPECT_FALSE(cursor.Read(1, false, &e));
486 }
487 
TEST(LittleEndian,Unsigned2)488 TEST(LittleEndian, Unsigned2) {
489   uint8_t data[] = { 0x00, 0x00,   0x80, 0x00,   0xff, 0x7f,
490                      0x00, 0x80,   0x80, 0x80,   0xff, 0xff,
491                      0xf1, 0x39,   0xbc, 0x8a,   0xec, 0x5a };
492   ByteBuffer buffer(data, sizeof(data));
493   ByteCursor cursor(&buffer);
494   int32_t a, b, c, d, e, f, g, h, i, j;
495   ASSERT_TRUE(cursor
496               .Read(2, false, &a)
497               .Read(2, false, &b)
498               .Read(2, false, &c)
499               .Read(2, false, &d)
500               .Read(2, false, &e)
501               .Read(2, false, &f)
502               .Read(2, false, &g)
503               .Read(2, false, &h)
504               .Read(2, false, &i));
505   EXPECT_EQ(0,      a);
506   EXPECT_EQ(0x80,   b);
507   EXPECT_EQ(0x7fff, c);
508   EXPECT_EQ(0x8000, d);
509   EXPECT_EQ(0x8080, e);
510   EXPECT_EQ(0xffff, f);
511   EXPECT_EQ(0x39f1, g);
512   EXPECT_EQ(0x8abc, h);
513   EXPECT_EQ(0x5aec, i);
514   EXPECT_TRUE(cursor.AtEnd());
515   EXPECT_FALSE(cursor.Read(2, false, &j));
516 }
517 
TEST(LittleEndian,Unsigned4)518 TEST(LittleEndian, Unsigned4) {
519   uint8_t data[] = { 0x00, 0x00, 0x00, 0x00,
520                      0xff, 0xff, 0xff, 0x7f,
521                      0x00, 0x00, 0x00, 0x80,
522                      0xff, 0xff, 0xff, 0xff,
523                      0xef, 0xff, 0xb1, 0xb6,
524                      0x46, 0xca, 0x6a, 0x19 };
525   ByteBuffer buffer(data, sizeof(data));
526   ByteCursor cursor(&buffer);
527   int64_t a, b, c, d, e, f, g;
528   ASSERT_TRUE(cursor
529               .Read(4, false, &a)
530               .Read(4, false, &b)
531               .Read(4, false, &c)
532               .Read(4, false, &d)
533               .Read(4, false, &e)
534               .Read(4, false, &f));
535   EXPECT_EQ(0,          a);
536   EXPECT_EQ(0x7fffffff, b);
537   EXPECT_EQ(0x80000000, c);
538   EXPECT_EQ(0xffffffff, d);
539   EXPECT_EQ(0xb6b1ffef, e);
540   EXPECT_EQ(0x196aca46, f);
541   EXPECT_TRUE(cursor.AtEnd());
542   EXPECT_FALSE(cursor.Read(4, false, &g));
543 }
544 
TEST(LittleEndian,Unsigned8)545 TEST(LittleEndian, Unsigned8) {
546   uint8_t data[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
547                      0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f,
548                      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80,
549                      0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
550                      0x9c, 0x87, 0xd5, 0xd2, 0xe9, 0xd5, 0x20, 0x93,
551                      0xa4, 0x14, 0x84, 0x7f, 0xd2, 0x49, 0x42, 0x4e };
552   ByteBuffer buffer(data, sizeof(data));
553   ByteCursor cursor(&buffer);
554   uint64_t a, b, c, d, e, f, g;
555   ASSERT_TRUE(cursor
556               .Read(8, false, &a)
557               .Read(8, false, &b)
558               .Read(8, false, &c)
559               .Read(8, false, &d)
560               .Read(8, false, &e)
561               .Read(8, false, &f));
562   EXPECT_EQ(0U,                    a);
563   EXPECT_EQ(0x7fffffffffffffffULL, b);
564   EXPECT_EQ(0x8000000000000000ULL, c);
565   EXPECT_EQ(0xffffffffffffffffULL, d);
566   EXPECT_EQ(0x9320d5e9d2d5879cULL, e);
567   EXPECT_EQ(0x4e4249d27f8414a4ULL, f);
568   EXPECT_TRUE(cursor.AtEnd());
569   EXPECT_FALSE(cursor.Read(8, false, &g));
570 }
571 
TEST(Extractor,Signed1)572 TEST(Extractor, Signed1) {
573   uint8_t data[] = { 0xfd };
574   ByteBuffer buffer(data, sizeof(data));
575   ByteCursor cursor(&buffer);
576   int8_t a;
577   EXPECT_TRUE(cursor >> a);
578   EXPECT_EQ(-3, a);
579   EXPECT_FALSE(cursor >> a);
580 }
581 
TEST(Extractor,Signed2)582 TEST(Extractor, Signed2) {
583   uint8_t data[] = { 0x13, 0xcd };
584   ByteBuffer buffer(data, sizeof(data));
585   ByteCursor cursor(&buffer);
586   int16_t a;
587   EXPECT_TRUE(cursor >> a);
588   EXPECT_EQ(-13037, a);
589   EXPECT_FALSE(cursor >> a);
590 }
591 
TEST(Extractor,Signed4)592 TEST(Extractor, Signed4) {
593   uint8_t data[] = { 0xd2, 0xe4, 0x53, 0xe9 };
594   ByteBuffer buffer(data, sizeof(data));
595   ByteCursor cursor(&buffer);
596   int32_t a;
597   // For some reason, G++ 4.4.1 complains:
598   //   warning: array subscript is above array bounds
599   // in ByteCursor::Read(size_t, bool, T*) as it inlines this call, but
600   // I'm not able to see how such a reference would occur.
601   EXPECT_TRUE(cursor >> a);
602   EXPECT_EQ(-380377902, a);
603   EXPECT_FALSE(cursor >> a);
604 }
605 
TEST(Extractor,Unsigned1)606 TEST(Extractor, Unsigned1) {
607   uint8_t data[] = { 0xfd };
608   ByteBuffer buffer(data, sizeof(data));
609   ByteCursor cursor(&buffer);
610   uint8_t a;
611   EXPECT_TRUE(cursor >> a);
612   EXPECT_EQ(0xfd, a);
613   EXPECT_FALSE(cursor >> a);
614 }
615 
TEST(Extractor,Unsigned2)616 TEST(Extractor, Unsigned2) {
617   uint8_t data[] = { 0x13, 0xcd };
618   ByteBuffer buffer(data, sizeof(data));
619   ByteCursor cursor(&buffer);
620   uint16_t a;
621   EXPECT_TRUE(cursor >> a);
622   EXPECT_EQ(0xcd13, a);
623   EXPECT_FALSE(cursor >> a);
624 }
625 
TEST(Extractor,Unsigned4)626 TEST(Extractor, Unsigned4) {
627   uint8_t data[] = { 0xd2, 0xe4, 0x53, 0xe9 };
628   ByteBuffer buffer(data, sizeof(data));
629   ByteCursor cursor(&buffer);
630   uint32_t a;
631   // For some reason, G++ 4.4.1 complains:
632   //   warning: array subscript is above array bounds
633   // in ByteCursor::Read(size_t, bool, T*) as it inlines this call, but
634   // I'm not able to see how such a reference would occur.
635   EXPECT_TRUE(cursor >> a);
636   EXPECT_EQ(0xe953e4d2, a);
637   EXPECT_FALSE(cursor >> a);
638   EXPECT_FALSE(cursor >> a);
639 }
640 
TEST(Extractor,Mixed)641 TEST(Extractor, Mixed) {
642   uint8_t data[] = { 0x42,
643                      0x25, 0x0b,
644                      0x3d, 0x25, 0xed, 0x2a,
645                      0xec, 0x16, 0x9e, 0x14, 0x61, 0x5b, 0x2c, 0xcf,
646                      0xd8,
647                      0x22, 0xa5,
648                      0x3a, 0x02, 0x6a, 0xd7,
649                      0x93, 0x2a, 0x2d, 0x8d, 0xb4, 0x95, 0xe0, 0xc6 };
650   ByteBuffer buffer(data, sizeof(data));
651   ByteCursor cursor(&buffer);
652   cursor.set_big_endian(true);
653 
654   uint8_t a;
655   uint16_t b;
656   uint32_t c;
657   uint64_t d;
658   int8_t e;
659   int16_t f;
660   int32_t g;
661   int64_t h;
662   int z;
663   EXPECT_FALSE(cursor.AtEnd());
664   EXPECT_TRUE(cursor >> a >> b >> c >> d >> e >> f >> g >> h);
665   EXPECT_EQ(0x42U, a);
666   EXPECT_EQ(0x250bU, b);
667   EXPECT_EQ(0x3d25ed2aU, c);
668   EXPECT_EQ(0xec169e14615b2ccfULL, d);
669   EXPECT_EQ(-40, e);
670   EXPECT_EQ(0x22a5, f);
671   EXPECT_EQ(0x3a026ad7, g);
672   EXPECT_EQ(-7842405714468937530LL, h);
673 
674   EXPECT_TRUE(cursor.AtEnd());
675   EXPECT_FALSE(cursor >> z);
676 }
677 
TEST(Strings,Zero)678 TEST(Strings, Zero) {
679   uint8_t data[] = { 0xa6 };
680   ByteBuffer buffer(data, 0);
681   ByteCursor cursor(&buffer);
682 
683   uint8_t received[1];
684   received[0] = 0xc2;
685   EXPECT_TRUE(cursor.Read(received, 0));
686   EXPECT_EQ(0xc2U, received[0]);
687 }
688 
TEST(Strings,Some)689 TEST(Strings, Some) {
690   uint8_t data[] = { 0x5d, 0x31, 0x09, 0xa6, 0x2e, 0x2c, 0x83, 0xbb };
691   ByteBuffer buffer(data, sizeof(data));
692   ByteCursor cursor(&buffer);
693 
694   uint8_t received[7] = { 0xa7, 0xf7, 0x43, 0x0c, 0x27, 0xea, 0xed };
695   EXPECT_TRUE(cursor.Skip(2).Read(received, 5));
696   uint8_t expected[7] = { 0x09, 0xa6, 0x2e, 0x2c, 0x83, 0xea, 0xed };
697   EXPECT_TRUE(memcmp(received, expected, 7) == 0);
698 }
699 
TEST(Strings,TooMuch)700 TEST(Strings, TooMuch) {
701   uint8_t data[] = { 0x5d, 0x31, 0x09, 0xa6, 0x2e, 0x2c, 0x83, 0xbb };
702   ByteBuffer buffer(data, sizeof(data));
703   ByteCursor cursor(&buffer);
704 
705   uint8_t received1[3];
706   uint8_t received2[3];
707   uint8_t received3[3];
708   EXPECT_FALSE(cursor
709                .Read(received1, 3)
710                .Read(received2, 3)
711                .Read(received3, 3));
712   uint8_t expected1[3] = { 0x5d, 0x31, 0x09 };
713   uint8_t expected2[3] = { 0xa6, 0x2e, 0x2c };
714 
715   EXPECT_TRUE(memcmp(received1, expected1, 3) == 0);
716   EXPECT_TRUE(memcmp(received2, expected2, 3) == 0);
717 }
718 
TEST(Strings,PointTo)719 TEST(Strings, PointTo) {
720   uint8_t data[] = { 0x83, 0x80, 0xb4, 0x38, 0x00, 0x2c, 0x0a, 0x27 };
721   ByteBuffer buffer(data, sizeof(data));
722   ByteCursor cursor(&buffer);
723 
724   const uint8_t* received1;
725   const uint8_t* received2;
726   const uint8_t* received3;
727   const uint8_t* received4;
728   EXPECT_FALSE(cursor
729                .PointTo(&received1, 3)
730                .PointTo(&received2, 3)
731                .PointTo(&received3)
732                .PointTo(&received4, 3));
733   EXPECT_EQ(data + 0, received1);
734   EXPECT_EQ(data + 3, received2);
735   EXPECT_EQ(data + 6, received3);
736   EXPECT_EQ(NULL, received4);
737 }
738 
TEST(Strings,CString)739 TEST(Strings, CString) {
740   uint8_t data[] = "abc\0\0foo";
741   ByteBuffer buffer(data, sizeof(data) - 1);  // don't include terminating '\0'
742   ByteCursor cursor(&buffer);
743 
744   string a, b, c;
745   EXPECT_TRUE(cursor.CString(&a).CString(&b));
746   EXPECT_EQ("abc", a);
747   EXPECT_EQ("", b);
748   EXPECT_FALSE(cursor.CString(&c));
749   EXPECT_EQ("", c);
750   EXPECT_TRUE(cursor.AtEnd());
751 }
752 
TEST(Strings,CStringLimit)753 TEST(Strings, CStringLimit) {
754   uint8_t data[] = "abcdef\0\0foobar";
755   ByteBuffer buffer(data, sizeof(data) - 1);  // don't include terminating '\0'
756   ByteCursor cursor(&buffer);
757 
758   string a, b, c, d, e;
759 
760   EXPECT_TRUE(cursor.CString(&a, 3));
761   EXPECT_EQ("abc", a);
762 
763   EXPECT_TRUE(cursor.CString(&b, 0));
764   EXPECT_EQ("", b);
765 
766   EXPECT_TRUE(cursor.CString(&c, 6));
767   EXPECT_EQ("def", c);
768 
769   EXPECT_TRUE(cursor.CString(&d, 4));
770   EXPECT_EQ("ooba", d);
771 
772   EXPECT_FALSE(cursor.CString(&e, 4));
773   EXPECT_EQ("", e);
774 
775   EXPECT_TRUE(cursor.AtEnd());
776 }
777 
778 //  uint8_t data[] = { 0xa6, 0x54, 0xdf, 0x67, 0x51, 0x43, 0xac, 0xf1 };
779 //  ByteBuffer buffer(data, sizeof(data));
780