blob: 21cffd67a34b5a9331e84bf12bc6024c247637cb [file] [log] [blame]
Noah Richardsbbf7c862015-04-21 16:30:13 -07001/*
2 * Copyright 2015 The WebRTC Project Authors. All rights reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10
11#include "webrtc/base/bitbuffer.h"
12#include "webrtc/base/bytebuffer.h"
13#include "webrtc/base/common.h"
14#include "webrtc/base/gunit.h"
15
16namespace rtc {
17
18TEST(BitBufferTest, ConsumeBits) {
19 const uint8 bytes[64] = {0};
20 BitBuffer buffer(bytes, 32);
21 uint64 total_bits = 32 * 8;
22 EXPECT_EQ(total_bits, buffer.RemainingBitCount());
23 EXPECT_TRUE(buffer.ConsumeBits(3));
24 total_bits -= 3;
25 EXPECT_EQ(total_bits, buffer.RemainingBitCount());
26 EXPECT_TRUE(buffer.ConsumeBits(3));
27 total_bits -= 3;
28 EXPECT_EQ(total_bits, buffer.RemainingBitCount());
29 EXPECT_TRUE(buffer.ConsumeBits(15));
30 total_bits -= 15;
31 EXPECT_EQ(total_bits, buffer.RemainingBitCount());
32 EXPECT_TRUE(buffer.ConsumeBits(37));
33 total_bits -= 37;
34 EXPECT_EQ(total_bits, buffer.RemainingBitCount());
35
36 EXPECT_FALSE(buffer.ConsumeBits(32 * 8));
37 EXPECT_EQ(total_bits, buffer.RemainingBitCount());
38}
39
40TEST(BitBufferTest, ReadBytesAligned) {
41 const uint8 bytes[] = {0x0A, 0xBC, 0xDE, 0xF1, 0x23, 0x45, 0x67, 0x89};
42 uint8 val8;
43 uint16 val16;
44 uint32 val32;
45 BitBuffer buffer(bytes, 8);
46 EXPECT_TRUE(buffer.ReadUInt8(&val8));
47 EXPECT_EQ(0x0Au, val8);
48 EXPECT_TRUE(buffer.ReadUInt8(&val8));
49 EXPECT_EQ(0xBCu, val8);
50 EXPECT_TRUE(buffer.ReadUInt16(&val16));
51 EXPECT_EQ(0xDEF1u, val16);
52 EXPECT_TRUE(buffer.ReadUInt32(&val32));
53 EXPECT_EQ(0x23456789u, val32);
54}
55
56TEST(BitBufferTest, ReadBytesOffset4) {
57 const uint8 bytes[] = {0x0A, 0xBC, 0xDE, 0xF1, 0x23, 0x45, 0x67, 0x89, 0x0A};
58 uint8 val8;
59 uint16 val16;
60 uint32 val32;
61 BitBuffer buffer(bytes, 9);
62 EXPECT_TRUE(buffer.ConsumeBits(4));
63
64 EXPECT_TRUE(buffer.ReadUInt8(&val8));
65 EXPECT_EQ(0xABu, val8);
66 EXPECT_TRUE(buffer.ReadUInt8(&val8));
67 EXPECT_EQ(0xCDu, val8);
68 EXPECT_TRUE(buffer.ReadUInt16(&val16));
69 EXPECT_EQ(0xEF12u, val16);
70 EXPECT_TRUE(buffer.ReadUInt32(&val32));
71 EXPECT_EQ(0x34567890u, val32);
72}
73
74TEST(BitBufferTest, ReadBytesOffset3) {
75 // The pattern we'll check against is counting down from 0b1111. It looks
76 // weird here because it's all offset by 3.
77 // Byte pattern is:
78 // 56701234
79 // 0b00011111,
80 // 0b11011011,
81 // 0b10010111,
82 // 0b01010011,
83 // 0b00001110,
84 // 0b11001010,
85 // 0b10000110,
86 // 0b01000010
87 // xxxxx <-- last 5 bits unused.
88
89 // The bytes. It almost looks like counting down by two at a time, except the
90 // jump at 5->3->0, since that's when the high bit is turned off.
91 const uint8 bytes[] = {0x1F, 0xDB, 0x97, 0x53, 0x0E, 0xCA, 0x86, 0x42};
92
93 uint8 val8;
94 uint16 val16;
95 uint32 val32;
96 BitBuffer buffer(bytes, 8);
97 EXPECT_TRUE(buffer.ConsumeBits(3));
98 EXPECT_TRUE(buffer.ReadUInt8(&val8));
99 EXPECT_EQ(0xFEu, val8);
100 EXPECT_TRUE(buffer.ReadUInt16(&val16));
101 EXPECT_EQ(0xDCBAu, val16);
102 EXPECT_TRUE(buffer.ReadUInt32(&val32));
103 EXPECT_EQ(0x98765432u, val32);
104 // 5 bits left unread. Not enough to read a uint8.
105 EXPECT_EQ(5u, buffer.RemainingBitCount());
106 EXPECT_FALSE(buffer.ReadUInt8(&val8));
107}
108
109TEST(BitBufferTest, ReadBits) {
110 // Bit values are:
111 // 0b01001101,
112 // 0b00110010
113 const uint8 bytes[] = {0x4D, 0x32};
114 uint32_t val;
115 BitBuffer buffer(bytes, 2);
116 EXPECT_TRUE(buffer.ReadBits(&val, 3));
117 // 0b010
118 EXPECT_EQ(0x2u, val);
119 EXPECT_TRUE(buffer.ReadBits(&val, 2));
120 // 0b01
121 EXPECT_EQ(0x1u, val);
122 EXPECT_TRUE(buffer.ReadBits(&val, 7));
123 // 0b1010011
124 EXPECT_EQ(0x53u, val);
125 EXPECT_TRUE(buffer.ReadBits(&val, 2));
126 // 0b00
127 EXPECT_EQ(0x0u, val);
128 EXPECT_TRUE(buffer.ReadBits(&val, 1));
129 // 0b1
130 EXPECT_EQ(0x1u, val);
131 EXPECT_TRUE(buffer.ReadBits(&val, 1));
132 // 0b0
133 EXPECT_EQ(0x0u, val);
134
135 EXPECT_FALSE(buffer.ReadBits(&val, 1));
136}
137
Noah Richards86153c22015-04-28 15:13:44 -0700138TEST(BitBufferTest, SetOffsetValues) {
139 uint8 bytes[4] = {0};
140 BitBufferWriter buffer(bytes, 4);
141
142 size_t byte_offset, bit_offset;
143 // Bit offsets are [0,7].
144 EXPECT_TRUE(buffer.Seek(0, 0));
145 EXPECT_TRUE(buffer.Seek(0, 7));
146 buffer.GetCurrentOffset(&byte_offset, &bit_offset);
147 EXPECT_EQ(0u, byte_offset);
148 EXPECT_EQ(7u, bit_offset);
149 EXPECT_FALSE(buffer.Seek(0, 8));
150 buffer.GetCurrentOffset(&byte_offset, &bit_offset);
151 EXPECT_EQ(0u, byte_offset);
152 EXPECT_EQ(7u, bit_offset);
153 // Byte offsets are [0,length]. At byte offset length, the bit offset must be
154 // 0.
155 EXPECT_TRUE(buffer.Seek(0, 0));
156 EXPECT_TRUE(buffer.Seek(2, 4));
157 buffer.GetCurrentOffset(&byte_offset, &bit_offset);
158 EXPECT_EQ(2u, byte_offset);
159 EXPECT_EQ(4u, bit_offset);
160 EXPECT_TRUE(buffer.Seek(4, 0));
161 EXPECT_FALSE(buffer.Seek(5, 0));
162 buffer.GetCurrentOffset(&byte_offset, &bit_offset);
163 EXPECT_EQ(4u, byte_offset);
164 EXPECT_EQ(0u, bit_offset);
165 EXPECT_FALSE(buffer.Seek(4, 1));
166
167 // Passing a NULL out parameter is death.
168 EXPECT_DEATH(buffer.GetCurrentOffset(&byte_offset, NULL), "");
169}
170
Noah Richardsbbf7c862015-04-21 16:30:13 -0700171uint64 GolombEncoded(uint32 val) {
172 val++;
173 uint32 bit_counter = val;
174 uint64 bit_count = 0;
175 while (bit_counter > 0) {
176 bit_count++;
177 bit_counter >>= 1;
178 }
179 return static_cast<uint64>(val) << (64 - (bit_count * 2 - 1));
180}
181
Noah Richards86153c22015-04-28 15:13:44 -0700182TEST(BitBufferTest, GolombUint32Values) {
183 ByteBuffer byteBuffer;
184 byteBuffer.Resize(16);
185 BitBuffer buffer(reinterpret_cast<const uint8*>(byteBuffer.Data()),
186 byteBuffer.Capacity());
187 // Test over the uint32 range with a large enough step that the test doesn't
188 // take forever. Around 20,000 iterations should do.
189 const int kStep = std::numeric_limits<uint32>::max() / 20000;
190 for (uint32 i = 0; i < std::numeric_limits<uint32>::max() - kStep;
191 i += kStep) {
192 uint64 encoded_val = GolombEncoded(i);
193 byteBuffer.Clear();
Noah Richardsbbf7c862015-04-21 16:30:13 -0700194 byteBuffer.WriteUInt64(encoded_val);
Noah Richardsbbf7c862015-04-21 16:30:13 -0700195 uint32 decoded_val;
Noah Richards86153c22015-04-28 15:13:44 -0700196 EXPECT_TRUE(buffer.Seek(0, 0));
Noah Richardsbbf7c862015-04-21 16:30:13 -0700197 EXPECT_TRUE(buffer.ReadExponentialGolomb(&decoded_val));
Noah Richards86153c22015-04-28 15:13:44 -0700198 EXPECT_EQ(i, decoded_val);
Noah Richardsbbf7c862015-04-21 16:30:13 -0700199 }
200}
201
202TEST(BitBufferTest, NoGolombOverread) {
203 const uint8 bytes[] = {0x00, 0xFF, 0xFF};
204 // Make sure the bit buffer correctly enforces byte length on golomb reads.
205 // If it didn't, the above buffer would be valid at 3 bytes.
206 BitBuffer buffer(bytes, 1);
207 uint32 decoded_val;
208 EXPECT_FALSE(buffer.ReadExponentialGolomb(&decoded_val));
209
210 BitBuffer longer_buffer(bytes, 2);
211 EXPECT_FALSE(longer_buffer.ReadExponentialGolomb(&decoded_val));
212
213 BitBuffer longest_buffer(bytes, 3);
214 EXPECT_TRUE(longest_buffer.ReadExponentialGolomb(&decoded_val));
215 // Golomb should have read 9 bits, so 0x01FF, and since it is golomb, the
216 // result is 0x01FF - 1 = 0x01FE.
217 EXPECT_EQ(0x01FEu, decoded_val);
218}
219
Noah Richards86153c22015-04-28 15:13:44 -0700220TEST(BitBufferWriterTest, SymmetricReadWrite) {
221 uint8 bytes[16] = {0};
222 BitBufferWriter buffer(bytes, 4);
223
224 // Write some bit data at various sizes.
225 EXPECT_TRUE(buffer.WriteBits(0x2u, 3));
226 EXPECT_TRUE(buffer.WriteBits(0x1u, 2));
227 EXPECT_TRUE(buffer.WriteBits(0x53u, 7));
228 EXPECT_TRUE(buffer.WriteBits(0x0u, 2));
229 EXPECT_TRUE(buffer.WriteBits(0x1u, 1));
230 EXPECT_TRUE(buffer.WriteBits(0x1ABCDu, 17));
231 // That should be all that fits in the buffer.
232 EXPECT_FALSE(buffer.WriteBits(1, 1));
233
234 EXPECT_TRUE(buffer.Seek(0, 0));
235 uint32 val;
236 EXPECT_TRUE(buffer.ReadBits(&val, 3));
237 EXPECT_EQ(0x2u, val);
238 EXPECT_TRUE(buffer.ReadBits(&val, 2));
239 EXPECT_EQ(0x1u, val);
240 EXPECT_TRUE(buffer.ReadBits(&val, 7));
241 EXPECT_EQ(0x53u, val);
242 EXPECT_TRUE(buffer.ReadBits(&val, 2));
243 EXPECT_EQ(0x0u, val);
244 EXPECT_TRUE(buffer.ReadBits(&val, 1));
245 EXPECT_EQ(0x1u, val);
246 EXPECT_TRUE(buffer.ReadBits(&val, 17));
247 EXPECT_EQ(0x1ABCDu, val);
248 // And there should be nothing left.
249 EXPECT_FALSE(buffer.ReadBits(&val, 1));
250}
251
252TEST(BitBufferWriterTest, SymmetricBytesMisaligned) {
253 uint8 bytes[16] = {0};
254 BitBufferWriter buffer(bytes, 16);
255
256 // Offset 3, to get things misaligned.
257 EXPECT_TRUE(buffer.ConsumeBits(3));
258 EXPECT_TRUE(buffer.WriteUInt8(0x12u));
259 EXPECT_TRUE(buffer.WriteUInt16(0x3456u));
260 EXPECT_TRUE(buffer.WriteUInt32(0x789ABCDEu));
261
262 buffer.Seek(0, 3);
263 uint8 val8;
264 uint16 val16;
265 uint32 val32;
266 EXPECT_TRUE(buffer.ReadUInt8(&val8));
267 EXPECT_EQ(0x12u, val8);
268 EXPECT_TRUE(buffer.ReadUInt16(&val16));
269 EXPECT_EQ(0x3456u, val16);
270 EXPECT_TRUE(buffer.ReadUInt32(&val32));
271 EXPECT_EQ(0x789ABCDEu, val32);
272}
273
274TEST(BitBufferWriterTest, SymmetricGolomb) {
275 char test_string[] = "my precious";
276 uint8 bytes[64] = {0};
277 BitBufferWriter buffer(bytes, 64);
278 for (size_t i = 0; i < ARRAY_SIZE(test_string); ++i) {
279 EXPECT_TRUE(buffer.WriteExponentialGolomb(test_string[i]));
280 }
281 buffer.Seek(0, 0);
282 for (size_t i = 0; i < ARRAY_SIZE(test_string); ++i) {
283 uint32 val;
284 EXPECT_TRUE(buffer.ReadExponentialGolomb(&val));
285 EXPECT_LE(val, std::numeric_limits<uint8>::max());
286 EXPECT_EQ(test_string[i], static_cast<char>(val));
287 }
288}
289
290TEST(BitBufferWriterTest, WriteClearsBits) {
291 uint8 bytes[] = {0xFF, 0xFF};
292 BitBufferWriter buffer(bytes, 2);
293 EXPECT_TRUE(buffer.ConsumeBits(3));
294 EXPECT_TRUE(buffer.WriteBits(0, 1));
295 EXPECT_EQ(0xEFu, bytes[0]);
296 EXPECT_TRUE(buffer.WriteBits(0, 3));
297 EXPECT_EQ(0xE1u, bytes[0]);
298 EXPECT_TRUE(buffer.WriteBits(0, 2));
299 EXPECT_EQ(0xE0u, bytes[0]);
300 EXPECT_EQ(0x7F, bytes[1]);
301}
302
Noah Richardsbbf7c862015-04-21 16:30:13 -0700303} // namespace rtc