1 /*
2 * Copyright (C) 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 <stdint.h>
18 #include <cstddef>
19 #include <cstdint>
20 #include <string>
21
22 #include "perfetto/ext/base/string_utils.h"
23 #include "perfetto/protozero/packed_repeated_fields.h"
24 #include "perfetto/protozero/scattered_heap_buffer.h"
25 #include "src/protozero/test/example_proto/test_messages.pbzero.h"
26 #include "src/trace_processor/importers/proto/track_event.descriptor.h"
27 #include "src/trace_processor/test_messages.descriptor.h"
28 #include "src/trace_processor/util/descriptors.h"
29 #include "src/trace_processor/util/protozero_to_text.h"
30 #include "test/gtest_and_gmock.h"
31
32 #include "protos/perfetto/trace/track_event/chrome_compositor_scheduler_state.pbzero.h"
33 #include "protos/perfetto/trace/track_event/track_event.pbzero.h"
34
35 namespace perfetto::trace_processor::protozero_to_text {
36
37 namespace {
38
39 constexpr size_t kChunkSize = 42;
40
41 using ::protozero::test::protos::pbzero::EveryField;
42 using ::protozero::test::protos::pbzero::PackedRepeatedFields;
43 using ::testing::_;
44 using ::testing::ElementsAre;
45 using ::testing::Eq;
46 using ::testing::StartsWith;
47
TEST(ProtozeroToTextTest,CustomDescriptorPoolBasic)48 TEST(ProtozeroToTextTest, CustomDescriptorPoolBasic) {
49 using perfetto::protos::pbzero::TrackEvent;
50 protozero::HeapBuffered<TrackEvent> msg{kChunkSize, kChunkSize};
51 msg->set_track_uuid(4);
52 msg->set_timestamp_delta_us(3);
53 auto binary_proto = msg.SerializeAsArray();
54 DescriptorPool pool;
55 auto status = pool.AddFromFileDescriptorSet(kTrackEventDescriptor.data(),
56 kTrackEventDescriptor.size());
57 ASSERT_TRUE(status.ok());
58 EXPECT_EQ("track_uuid: 4\ntimestamp_delta_us: 3",
59 ProtozeroToText(pool, ".perfetto.protos.TrackEvent", binary_proto,
60 kIncludeNewLines));
61 EXPECT_EQ("track_uuid: 4 timestamp_delta_us: 3",
62 ProtozeroToText(pool, ".perfetto.protos.TrackEvent", binary_proto,
63 kSkipNewLines));
64 }
65
TEST(ProtozeroToTextTest,CustomDescriptorPoolNestedMsg)66 TEST(ProtozeroToTextTest, CustomDescriptorPoolNestedMsg) {
67 using perfetto::protos::pbzero::TrackEvent;
68 protozero::HeapBuffered<TrackEvent> msg{kChunkSize, kChunkSize};
69 msg->set_track_uuid(4);
70 auto* state = msg->set_cc_scheduler_state();
71 state->set_deadline_us(7);
72 auto* machine = state->set_state_machine();
73 auto* minor_state = machine->set_minor_state();
74 minor_state->set_commit_count(8);
75 state->set_observing_begin_frame_source(true);
76 msg->set_timestamp_delta_us(3);
77 auto binary_proto = msg.SerializeAsArray();
78
79 DescriptorPool pool;
80 auto status = pool.AddFromFileDescriptorSet(kTrackEventDescriptor.data(),
81 kTrackEventDescriptor.size());
82 ASSERT_TRUE(status.ok());
83
84 EXPECT_EQ(
85 R"(track_uuid: 4
86 cc_scheduler_state {
87 deadline_us: 7
88 state_machine {
89 minor_state {
90 commit_count: 8
91 }
92 }
93 observing_begin_frame_source: true
94 }
95 timestamp_delta_us: 3)",
96 ProtozeroToText(pool, ".perfetto.protos.TrackEvent", binary_proto,
97 kIncludeNewLines));
98
99 EXPECT_EQ(
100 "track_uuid: 4 cc_scheduler_state { deadline_us: 7 state_machine { "
101 "minor_state { commit_count: 8 } } observing_begin_frame_source: true } "
102 "timestamp_delta_us: 3",
103 ProtozeroToText(pool, ".perfetto.protos.TrackEvent", binary_proto,
104 kSkipNewLines));
105 }
106
107 // Sets up a descriptor pool with all the messages from
108 // "src/protozero/test/example_proto/test_messages.proto"
109 class ProtozeroToTextTestMessageTest : public testing::Test {
110 protected:
SetUp()111 void SetUp() override {
112 auto status = pool_.AddFromFileDescriptorSet(
113 kTestMessagesDescriptor.data(), kTestMessagesDescriptor.size());
114 ASSERT_TRUE(status.ok());
115 }
116
117 DescriptorPool pool_;
118 };
119
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntInt32)120 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntInt32) {
121 protozero::HeapBuffered<EveryField> msg;
122 msg->set_field_int32(42);
123
124 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
125 msg.SerializeAsArray(), kIncludeNewLines),
126 "field_int32: 42");
127 }
128
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntSint32)129 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntSint32) {
130 protozero::HeapBuffered<EveryField> msg;
131 msg->set_field_sint32(-42);
132
133 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
134 msg.SerializeAsArray(), kIncludeNewLines),
135 "field_sint32: -42");
136 }
137
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntUint32)138 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntUint32) {
139 protozero::HeapBuffered<EveryField> msg;
140 msg->set_field_uint32(3000000000);
141
142 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
143 msg.SerializeAsArray(), kIncludeNewLines),
144 "field_uint32: 3000000000");
145 }
146
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntInt64)147 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntInt64) {
148 protozero::HeapBuffered<EveryField> msg;
149 msg->set_field_int64(3000000000);
150
151 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
152 msg.SerializeAsArray(), kIncludeNewLines),
153 "field_int64: 3000000000");
154 }
155
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntSint64)156 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntSint64) {
157 protozero::HeapBuffered<EveryField> msg;
158 msg->set_field_sint64(INT64_C(-3000000000));
159
160 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
161 msg.SerializeAsArray(), kIncludeNewLines),
162 "field_sint64: -3000000000");
163 }
164
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntBool)165 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntBool) {
166 protozero::HeapBuffered<EveryField> msg;
167 msg->set_field_bool(true);
168
169 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
170 msg.SerializeAsArray(), kIncludeNewLines),
171 "field_bool: true");
172 }
173
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntSmallEnum)174 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntSmallEnum) {
175 protozero::HeapBuffered<EveryField> msg;
176 msg->set_small_enum(protozero::test::protos::pbzero::TO_BE);
177
178 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
179 msg.SerializeAsArray(), kIncludeNewLines),
180 "small_enum: TO_BE");
181 }
182
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntSignedEnum)183 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntSignedEnum) {
184 protozero::HeapBuffered<EveryField> msg;
185 msg->set_signed_enum(protozero::test::protos::pbzero::NEGATIVE);
186
187 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
188 msg.SerializeAsArray(), kIncludeNewLines),
189 "signed_enum: NEGATIVE");
190 }
191
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntBigEnum)192 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntBigEnum) {
193 protozero::HeapBuffered<EveryField> msg;
194 msg->set_big_enum(protozero::test::protos::pbzero::END);
195
196 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
197 msg.SerializeAsArray(), kIncludeNewLines),
198 "big_enum: END");
199 }
200
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntEnumUnknown)201 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntEnumUnknown) {
202 protozero::HeapBuffered<EveryField> msg;
203 msg->AppendVarInt(EveryField::kSmallEnumFieldNumber, 42);
204 ASSERT_EQ(EveryField::kSmallEnumFieldNumber, 51);
205
206 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
207 msg.SerializeAsArray(), kIncludeNewLines),
208 "51: 42");
209 }
210
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntUnknown)211 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntUnknown) {
212 protozero::HeapBuffered<EveryField> msg;
213 msg->AppendVarInt(/*field_id=*/9999, /*value=*/42);
214
215 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
216 msg.SerializeAsArray(), kIncludeNewLines),
217 "9999: 42");
218 }
219
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntMismatch)220 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntMismatch) {
221 protozero::HeapBuffered<EveryField> msg;
222 ASSERT_EQ(EveryField::kFieldStringFieldNumber, 500);
223 msg->AppendVarInt(EveryField::kFieldStringFieldNumber, 42);
224
225 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
226 msg.SerializeAsArray(), kIncludeNewLines),
227 "500: 42");
228 }
229
TEST_F(ProtozeroToTextTestMessageTest,FieldVarIntForPacked)230 TEST_F(ProtozeroToTextTestMessageTest, FieldVarIntForPacked) {
231 // Even though field_int32 has [packed = true], it still accepts a non-packed
232 // representation.
233 protozero::HeapBuffered<PackedRepeatedFields> msg;
234 msg->AppendVarInt(PackedRepeatedFields::kFieldInt32FieldNumber, 42);
235
236 EXPECT_EQ(
237 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
238 msg.SerializeAsArray(), kIncludeNewLines),
239 "field_int32: 42");
240 }
241
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed32Signed)242 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed32Signed) {
243 protozero::HeapBuffered<EveryField> msg;
244 msg->set_field_sfixed32(-42);
245
246 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
247 msg.SerializeAsArray(), kIncludeNewLines),
248 "field_sfixed32: -42");
249 }
250
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed32Unsigned)251 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed32Unsigned) {
252 protozero::HeapBuffered<EveryField> msg;
253 msg->set_field_fixed32(3000000000);
254
255 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
256 msg.SerializeAsArray(), kIncludeNewLines),
257 "field_fixed32: 3000000000");
258 }
259
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed32Float)260 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed32Float) {
261 protozero::HeapBuffered<EveryField> msg;
262 msg->set_field_float(24.125);
263
264 EXPECT_THAT(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
265 msg.SerializeAsArray(), kIncludeNewLines),
266 StartsWith("field_float: 24.125"));
267 }
268
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed32Unknown)269 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed32Unknown) {
270 protozero::HeapBuffered<EveryField> msg;
271 msg->AppendFixed<uint32_t>(/*field_id=*/9999, /*value=*/0x1);
272
273 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
274 msg.SerializeAsArray(), kIncludeNewLines),
275 "9999: 0x00000001");
276 }
277
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed32Mismatch)278 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed32Mismatch) {
279 protozero::HeapBuffered<EveryField> msg;
280 ASSERT_EQ(EveryField::kFieldStringFieldNumber, 500);
281 msg->AppendFixed<uint32_t>(EveryField::kFieldStringFieldNumber, 0x1);
282
283 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
284 msg.SerializeAsArray(), kIncludeNewLines),
285 "500: 0x00000001");
286 }
287
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed64Signed)288 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed64Signed) {
289 protozero::HeapBuffered<EveryField> msg;
290 msg->set_field_sfixed64(-42);
291
292 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
293 msg.SerializeAsArray(), kIncludeNewLines),
294 "field_sfixed64: -42");
295 }
296
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed64Unsigned)297 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed64Unsigned) {
298 protozero::HeapBuffered<EveryField> msg;
299 msg->set_field_fixed64(3000000000);
300
301 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
302 msg.SerializeAsArray(), kIncludeNewLines),
303 "field_fixed64: 3000000000");
304 }
305
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed64Double)306 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed64Double) {
307 protozero::HeapBuffered<EveryField> msg;
308 msg->set_field_double(24.125);
309
310 EXPECT_THAT(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
311 msg.SerializeAsArray(), kIncludeNewLines),
312 StartsWith("field_double: 24.125"));
313 }
314
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed64Unknown)315 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed64Unknown) {
316 protozero::HeapBuffered<EveryField> msg;
317 msg->AppendFixed<uint64_t>(/*field_id=*/9999, /*value=*/0x1);
318
319 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
320 msg.SerializeAsArray(), kIncludeNewLines),
321 "9999: 0x0000000000000001");
322 }
323
TEST_F(ProtozeroToTextTestMessageTest,FieldFixed64Mismatch)324 TEST_F(ProtozeroToTextTestMessageTest, FieldFixed64Mismatch) {
325 protozero::HeapBuffered<EveryField> msg;
326 ASSERT_EQ(EveryField::kFieldStringFieldNumber, 500);
327 msg->AppendFixed<uint64_t>(EveryField::kFieldStringFieldNumber, 0x1);
328
329 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
330 msg.SerializeAsArray(), kIncludeNewLines),
331 "500: 0x0000000000000001");
332 }
333
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedString)334 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedString) {
335 protozero::HeapBuffered<EveryField> msg;
336 msg->set_field_string("Hello");
337
338 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
339 msg.SerializeAsArray(), kIncludeNewLines),
340 R"(field_string: "Hello")");
341 }
342
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedBytes)343 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedBytes) {
344 protozero::HeapBuffered<EveryField> msg;
345 msg->set_field_bytes("Hello");
346
347 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
348 msg.SerializeAsArray(), kIncludeNewLines),
349 R"(field_bytes: "Hello")");
350 }
351
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedUnknown)352 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedUnknown) {
353 protozero::HeapBuffered<EveryField> msg;
354 msg->AppendString(9999, "Hello");
355
356 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
357 msg.SerializeAsArray(), kIncludeNewLines),
358 R"(9999: "Hello")");
359 }
360
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedMismatch)361 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedMismatch) {
362 protozero::HeapBuffered<EveryField> msg;
363 ASSERT_EQ(EveryField::kFieldBoolFieldNumber, 13);
364 msg->AppendString(EveryField::kFieldBoolFieldNumber, "Hello");
365
366 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
367 msg.SerializeAsArray(), kIncludeNewLines),
368 "# Packed type 8 not supported. Printing raw string.\n"
369 R"(13: "Hello")");
370 }
371
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedForNonPacked)372 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedForNonPacked) {
373 // Even though repeated_int32 doesn't have [packed = true], it still accepts a
374 // packed representation.
375 protozero::HeapBuffered<EveryField> msg;
376 protozero::PackedVarInt buf;
377 buf.Append<int32_t>(-42);
378 buf.Append<int32_t>(2147483647);
379 msg->AppendBytes(EveryField::kRepeatedInt32FieldNumber, buf.data(),
380 buf.size());
381
382 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
383 msg.SerializeAsArray(), kIncludeNewLines),
384 "repeated_int32: -42\nrepeated_int32: 2147483647");
385 }
386
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedVarIntInt32)387 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedVarIntInt32) {
388 protozero::HeapBuffered<PackedRepeatedFields> msg;
389 protozero::PackedVarInt buf;
390 buf.Append<int32_t>(-42);
391 buf.Append<int32_t>(2147483647);
392 msg->set_field_int32(buf);
393
394 EXPECT_EQ(
395 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
396 msg.SerializeAsArray(), kIncludeNewLines),
397 "field_int32: -42\nfield_int32: 2147483647");
398 }
399
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedVarIntInt64)400 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedVarIntInt64) {
401 protozero::HeapBuffered<PackedRepeatedFields> msg;
402 protozero::PackedVarInt buf;
403 buf.Append<int64_t>(-42);
404 buf.Append<int64_t>(3000000000);
405 msg->set_field_int64(buf);
406
407 EXPECT_EQ(
408 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
409 msg.SerializeAsArray(), kIncludeNewLines),
410 "field_int64: -42\nfield_int64: 3000000000");
411 }
412
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedVarIntUint32)413 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedVarIntUint32) {
414 protozero::HeapBuffered<PackedRepeatedFields> msg;
415 protozero::PackedVarInt buf;
416 buf.Append<uint32_t>(42);
417 buf.Append<uint32_t>(3000000000);
418 msg->set_field_uint32(buf);
419
420 EXPECT_EQ(
421 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
422 msg.SerializeAsArray(), kIncludeNewLines),
423 "field_uint32: 42\nfield_uint32: 3000000000");
424 }
425
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedVarIntUint64)426 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedVarIntUint64) {
427 protozero::HeapBuffered<PackedRepeatedFields> msg;
428 protozero::PackedVarInt buf;
429 buf.Append<uint64_t>(42);
430 buf.Append<uint64_t>(3000000000000);
431 msg->set_field_uint64(buf);
432
433 EXPECT_EQ(
434 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
435 msg.SerializeAsArray(), kIncludeNewLines),
436 "field_uint64: 42\nfield_uint64: 3000000000000");
437 }
438
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedFixed32Uint32)439 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedFixed32Uint32) {
440 protozero::HeapBuffered<PackedRepeatedFields> msg;
441 protozero::PackedFixedSizeInt<uint32_t> buf;
442 buf.Append(42);
443 buf.Append(3000000000);
444 msg->set_field_fixed32(buf);
445
446 EXPECT_EQ(
447 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
448 msg.SerializeAsArray(), kIncludeNewLines),
449 "field_fixed32: 42\nfield_fixed32: 3000000000");
450 }
451
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedFixed32Int32)452 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedFixed32Int32) {
453 protozero::HeapBuffered<PackedRepeatedFields> msg;
454 protozero::PackedFixedSizeInt<int32_t> buf;
455 buf.Append(-42);
456 buf.Append(42);
457 msg->set_field_sfixed32(buf);
458
459 EXPECT_EQ(
460 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
461 msg.SerializeAsArray(), kIncludeNewLines),
462 "field_sfixed32: -42\nfield_sfixed32: 42");
463 }
464
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedFixed32Float)465 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedFixed32Float) {
466 protozero::HeapBuffered<PackedRepeatedFields> msg;
467 protozero::PackedFixedSizeInt<float> buf;
468 buf.Append(-42);
469 buf.Append(42.125);
470 msg->set_field_float(buf);
471
472 std::string output =
473 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
474 msg.SerializeAsArray(), kIncludeNewLines);
475
476 EXPECT_THAT(base::SplitString(output, "\n"),
477 ElementsAre(StartsWith("field_float: -42"),
478 StartsWith("field_float: 42.125")));
479 }
480
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedFixed64Uint64)481 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedFixed64Uint64) {
482 protozero::HeapBuffered<PackedRepeatedFields> msg;
483 protozero::PackedFixedSizeInt<uint64_t> buf;
484 buf.Append(42);
485 buf.Append(3000000000000);
486 msg->set_field_fixed64(buf);
487
488 EXPECT_EQ(
489 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
490 msg.SerializeAsArray(), kIncludeNewLines),
491 "field_fixed64: 42\nfield_fixed64: 3000000000000");
492 }
493
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedFixed64Int64)494 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedFixed64Int64) {
495 protozero::HeapBuffered<PackedRepeatedFields> msg;
496 protozero::PackedFixedSizeInt<int64_t> buf;
497 buf.Append(-42);
498 buf.Append(3000000000000);
499 msg->set_field_sfixed64(buf);
500
501 EXPECT_EQ(
502 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
503 msg.SerializeAsArray(), kIncludeNewLines),
504 "field_sfixed64: -42\nfield_sfixed64: 3000000000000");
505 }
506
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedFixed64Double)507 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedFixed64Double) {
508 protozero::HeapBuffered<PackedRepeatedFields> msg;
509 protozero::PackedFixedSizeInt<double> buf;
510 buf.Append(-42);
511 buf.Append(42.125);
512 msg->set_field_double(buf);
513
514 EXPECT_THAT(
515 base::SplitString(
516 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
517 msg.SerializeAsArray(), kIncludeNewLines),
518 "\n"),
519 ElementsAre(StartsWith("field_double: -42"),
520 StartsWith("field_double: 42.125")));
521 }
522
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedSmallEnum)523 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedSmallEnum) {
524 protozero::HeapBuffered<PackedRepeatedFields> msg;
525 protozero::PackedVarInt buf;
526 buf.Append(1);
527 buf.Append(0);
528 buf.Append(-1);
529 msg->set_small_enum(buf);
530
531 EXPECT_THAT(
532 base::SplitString(
533 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
534 msg.SerializeAsArray(), kIncludeNewLines),
535 "\n"),
536 ElementsAre(Eq("small_enum: TO_BE"), Eq("small_enum: NOT_TO_BE"),
537 Eq("51: -1")));
538 }
539
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedSignedEnum)540 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedSignedEnum) {
541 protozero::HeapBuffered<PackedRepeatedFields> msg;
542 protozero::PackedVarInt buf;
543 buf.Append(1);
544 buf.Append(0);
545 buf.Append(-1);
546 buf.Append(-100);
547 msg->set_signed_enum(buf);
548
549 EXPECT_THAT(
550 base::SplitString(
551 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
552 msg.SerializeAsArray(), kIncludeNewLines),
553 "\n"),
554 ElementsAre(Eq("signed_enum: POSITIVE"), Eq("signed_enum: NEUTRAL"),
555 Eq("signed_enum: NEGATIVE"), Eq("52: -100")));
556 }
557
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedBigEnum)558 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedBigEnum) {
559 protozero::HeapBuffered<PackedRepeatedFields> msg;
560 protozero::PackedVarInt buf;
561 buf.Append(10);
562 buf.Append(100500);
563 buf.Append(-1);
564 msg->set_big_enum(buf);
565
566 EXPECT_THAT(
567 base::SplitString(
568 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
569 msg.SerializeAsArray(), kIncludeNewLines),
570 "\n"),
571 ElementsAre(Eq("big_enum: BEGIN"), Eq("big_enum: END"), Eq("53: -1")));
572 }
573
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedFixedErrShort)574 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedFixedErrShort) {
575 protozero::HeapBuffered<PackedRepeatedFields> msg;
576 std::string buf;
577 buf = "\x01";
578 // buf does not contain enough data for a fixed 64
579 msg->AppendBytes(PackedRepeatedFields::kFieldFixed64FieldNumber, buf.data(),
580 buf.size());
581
582 // "protoc --decode", instead, returns an error on stderr and doesn't output
583 // anything at all.
584 EXPECT_EQ(
585 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
586 msg.SerializeAsArray(), kIncludeNewLines),
587 "# Packed decoding failure for field field_fixed64\n");
588 }
589
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedFixedGarbage)590 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedFixedGarbage) {
591 protozero::HeapBuffered<PackedRepeatedFields> msg;
592 protozero::PackedFixedSizeInt<uint64_t> buf;
593 buf.Append(42);
594 buf.Append(3000000000000);
595 std::string buf_and_garbage(reinterpret_cast<const char*>(buf.data()),
596 buf.size());
597 buf_and_garbage += "\x01";
598 // buf contains extra garbage
599 msg->AppendBytes(PackedRepeatedFields::kFieldFixed64FieldNumber,
600 buf_and_garbage.data(), buf_and_garbage.size());
601
602 // "protoc --decode", instead, returns an error on stderr and doesn't output
603 // anything at all.
604 EXPECT_EQ(
605 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
606 msg.SerializeAsArray(), kIncludeNewLines),
607 "# Packed decoding failure for field field_fixed64\n");
608 }
609
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedVarIntShort)610 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedVarIntShort) {
611 protozero::HeapBuffered<PackedRepeatedFields> msg;
612 std::string buf;
613 buf = "\xFF";
614 // for the varint to be valid, buf should contain another byte.
615 msg->AppendBytes(PackedRepeatedFields::kFieldInt32FieldNumber, buf.data(),
616 buf.size());
617
618 // "protoc --decode", instead, returns an error on stderr and doesn't output
619 // anything at all.
620 EXPECT_EQ(
621 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
622 msg.SerializeAsArray(), kIncludeNewLines),
623 "# Packed decoding failure for field field_int32\n");
624 }
625
TEST_F(ProtozeroToTextTestMessageTest,FieldLengthLimitedPackedVarIntGarbage)626 TEST_F(ProtozeroToTextTestMessageTest, FieldLengthLimitedPackedVarIntGarbage) {
627 protozero::HeapBuffered<PackedRepeatedFields> msg;
628 protozero::PackedVarInt buf;
629 buf.Append(42);
630 buf.Append(105);
631 std::string buf_and_garbage(reinterpret_cast<const char*>(buf.data()),
632 buf.size());
633 buf_and_garbage += "\xFF";
634 // buf contains extra garbage
635 msg->AppendBytes(PackedRepeatedFields::kFieldInt32FieldNumber,
636 buf_and_garbage.data(), buf_and_garbage.size());
637
638 // "protoc --decode", instead:
639 // * doesn't output anything.
640 // * returns an error on stderr.
641 EXPECT_EQ(
642 ProtozeroToText(pool_, ".protozero.test.protos.PackedRepeatedFields",
643 msg.SerializeAsArray(), kIncludeNewLines),
644 "field_int32: 42\n"
645 "field_int32: 105\n"
646 "# Packed decoding failure for field field_int32\n");
647 }
648
TEST_F(ProtozeroToTextTestMessageTest,ExtraBytes)649 TEST_F(ProtozeroToTextTestMessageTest, ExtraBytes) {
650 protozero::HeapBuffered<EveryField> msg;
651 EveryField* nested = msg->add_field_nested();
652 nested->set_field_string("hello");
653 std::string garbage("\377\377");
654 nested->AppendRawProtoBytes(garbage.data(), garbage.size());
655
656 // "protoc --decode", instead:
657 // * doesn't output anything.
658 // * returns an error on stderr.
659 EXPECT_EQ(ProtozeroToText(pool_, ".protozero.test.protos.EveryField",
660 msg.SerializeAsArray(), kIncludeNewLines),
661 R"(field_nested {
662 field_string: "hello"
663 # Extra bytes: "\377\377"
664
665 })");
666 }
667
TEST_F(ProtozeroToTextTestMessageTest,NonExistingType)668 TEST_F(ProtozeroToTextTestMessageTest, NonExistingType) {
669 protozero::HeapBuffered<EveryField> msg;
670 msg->set_field_string("hello");
671 ASSERT_EQ(EveryField::kFieldStringFieldNumber, 500);
672
673 // "protoc --decode", instead:
674 // * doesn't output anything.
675 // * returns an error on stderr.
676 EXPECT_EQ(ProtozeroToText(pool_, ".non.existing.type", msg.SerializeAsArray(),
677 kIncludeNewLines),
678 R"(500: "hello")");
679 }
680
681 } // namespace
682 } // namespace perfetto::trace_processor::protozero_to_text
683