Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-31 10:11:59

0001 // Protocol Buffers - Google's data interchange format
0002 // Copyright 2008 Google Inc.  All rights reserved.
0003 //
0004 // Use of this source code is governed by a BSD-style
0005 // license that can be found in the LICENSE file or at
0006 // https://developers.google.com/open-source/licenses/bsd
0007 
0008 #ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_SERIALIZATION_H__
0009 #define GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_SERIALIZATION_H__
0010 
0011 #include <algorithm>
0012 #include <cstddef>
0013 #include <vector>
0014 
0015 #include "absl/types/span.h"
0016 #include "google/protobuf/compiler/java/generator_common.h"
0017 #include "google/protobuf/descriptor.h"
0018 #include "google/protobuf/io/printer.h"
0019 
0020 namespace google {
0021 namespace protobuf {
0022 namespace compiler {
0023 namespace java {
0024 
0025 // Generates code to serialize a single extension range.
0026 void GenerateSerializeExtensionRange(io::Printer* printer,
0027                                      const Descriptor::ExtensionRange* range);
0028 
0029 // Generates code to serialize all fields and extension ranges for the specified
0030 // message descriptor, sorting serialization calls in increasing order by field
0031 // number.
0032 inline void GenerateSerializeFieldsAndExtensions(
0033     io::Printer* printer,
0034     const std::vector<const FieldGenerator*>& field_generators,
0035     const Descriptor* descriptor, const FieldDescriptor** sorted_fields) {
0036   std::vector<const Descriptor::ExtensionRange*> sorted_extensions;
0037   sorted_extensions.reserve(descriptor->extension_range_count());
0038   for (int i = 0; i < descriptor->extension_range_count(); ++i) {
0039     sorted_extensions.push_back(descriptor->extension_range(i));
0040   }
0041   std::sort(sorted_extensions.begin(), sorted_extensions.end(),
0042             ExtensionRangeOrdering());
0043 
0044   std::size_t range_idx = 0;
0045 
0046   // Merge the fields and the extension ranges, both sorted by field number.
0047   for (int i = 0; i < descriptor->field_count(); ++i) {
0048     const FieldDescriptor* field = sorted_fields[i];
0049 
0050     // Collapse all extension ranges up until the next field. This leads to
0051     // shorter and more efficient codegen for messages containing a large
0052     // number of extension ranges without fields in between them.
0053     const Descriptor::ExtensionRange* range = nullptr;
0054     while (range_idx < sorted_extensions.size() &&
0055            sorted_extensions[range_idx]->end_number() <= field->number()) {
0056       range = sorted_extensions[range_idx++];
0057     }
0058 
0059     if (range != nullptr) {
0060       GenerateSerializeExtensionRange(printer, range);
0061     }
0062     size_t idx = static_cast<size_t>(field->index());
0063     field_generators[idx]->GenerateSerializationCode(printer);
0064   }
0065 
0066   // After serializing all fields, serialize any remaining extensions via a
0067   // single writeUntil call.
0068   if (range_idx < sorted_extensions.size()) {
0069     GenerateSerializeExtensionRange(printer, sorted_extensions.back());
0070   }
0071 }
0072 
0073 }  // namespace java
0074 }  // namespace compiler
0075 }  // namespace protobuf
0076 }  // namespace google
0077 
0078 #endif  // GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_SERIALIZATION_H__