codegen for WriteContext based serialization

pull/7576/head
Jan Tattermusch 5 years ago
parent ca7bc464a9
commit dda621749c
  1. 6
      src/google/protobuf/compiler/csharp/csharp_field_base.cc
  2. 1
      src/google/protobuf/compiler/csharp/csharp_field_base.h
  3. 8
      src/google/protobuf/compiler/csharp/csharp_map_field.cc
  4. 1
      src/google/protobuf/compiler/csharp/csharp_map_field.h
  5. 75
      src/google/protobuf/compiler/csharp/csharp_message.cc
  6. 1
      src/google/protobuf/compiler/csharp/csharp_message.h
  7. 8
      src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.cc
  8. 1
      src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.h
  9. 8
      src/google/protobuf/compiler/csharp/csharp_repeated_message_field.cc
  10. 1
      src/google/protobuf/compiler/csharp/csharp_repeated_message_field.h
  11. 8
      src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.cc
  12. 1
      src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.h
  13. 28
      src/google/protobuf/compiler/csharp/csharp_wrapper_field.cc
  14. 2
      src/google/protobuf/compiler/csharp/csharp_wrapper_field.h

@ -167,6 +167,12 @@ void FieldGeneratorBase::GenerateParsingCode(io::Printer* printer, bool use_pars
GenerateParsingCode(printer);
}
void FieldGeneratorBase::GenerateSerializationCode(io::Printer* printer, bool use_write_context) {
// for some field types the value of "use_write_context" doesn't matter,
// so we fallback to the default implementation.
GenerateSerializationCode(printer);
}
void FieldGeneratorBase::AddDeprecatedFlag(io::Printer* printer) {
if (descriptor_->options().deprecated()) {
printer->Print("[global::System.ObsoleteAttribute]\n");

@ -63,6 +63,7 @@ class FieldGeneratorBase : public SourceGeneratorBase {
virtual void GenerateParsingCode(io::Printer* printer) = 0;
virtual void GenerateParsingCode(io::Printer* printer, bool use_parse_context);
virtual void GenerateSerializationCode(io::Printer* printer) = 0;
virtual void GenerateSerializationCode(io::Printer* printer, bool use_write_context);
virtual void GenerateSerializedSizeCode(io::Printer* printer) = 0;
virtual void WriteHash(io::Printer* printer) = 0;

@ -106,9 +106,15 @@ void MapFieldGenerator::GenerateParsingCode(io::Printer* printer, bool use_parse
}
void MapFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
GenerateSerializationCode(printer, true);
}
void MapFieldGenerator::GenerateSerializationCode(io::Printer* printer, bool use_write_context) {
printer->Print(
variables_,
"$name$_.WriteTo(output, _map_$name$_codec);\n");
use_write_context
? "$name$_.WriteTo(ref output, _map_$name$_codec);\n"
: "$name$_.WriteTo(output, _map_$name$_codec);\n");
}
void MapFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {

@ -58,6 +58,7 @@ class MapFieldGenerator : public FieldGeneratorBase {
virtual void GenerateParsingCode(io::Printer* printer);
virtual void GenerateParsingCode(io::Printer* printer, bool use_parse_context);
virtual void GenerateSerializationCode(io::Printer* printer);
virtual void GenerateSerializationCode(io::Printer* printer, bool use_write_context);
virtual void GenerateSerializedSizeCode(io::Printer* printer);
virtual void WriteHash(io::Printer* printer);

@ -520,34 +520,26 @@ void MessageGenerator::GenerateMessageSerializationMethods(io::Printer* printer)
WriteGeneratedCodeAttributes(printer);
printer->Print(
"public void WriteTo(pb::CodedOutputStream output) {\n");
printer->Print("#if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE\n");
printer->Indent();
printer->Print("output.WriteRawMessage(this);\n");
printer->Outdent();
printer->Print("#else\n");
printer->Indent();
GenerateWriteToBody(printer, false);
printer->Outdent();
printer->Print("#endif\n");
printer->Print("}\n\n");
// Serialize all the fields
for (int i = 0; i < fields_by_number().size(); i++) {
std::unique_ptr<FieldGeneratorBase> generator(
CreateFieldGeneratorInternal(fields_by_number()[i]));
generator->GenerateSerializationCode(printer);
}
if (has_extension_ranges_) {
// Serialize extensions
printer->Print(
"if (_extensions != null) {\n"
" _extensions.WriteTo(output);\n"
"}\n");
}
// Serialize unknown fields
printer->Print(
"if (_unknownFields != null) {\n"
" _unknownFields.WriteTo(output);\n"
"}\n");
// TODO(jonskeet): Memoize size of frozen messages?
printer->Print("#if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE\n");
WriteGeneratedCodeAttributes(printer);
printer->Print("void pb::IBufferMessage.InternalWriteTo(ref pb::WriteContext output) {\n");
printer->Indent();
GenerateWriteToBody(printer, true);
printer->Outdent();
printer->Print(
"}\n"
"\n");
printer->Print("}\n");
printer->Print("#endif\n\n");
WriteGeneratedCodeAttributes(printer);
printer->Print(
"public int CalculateSize() {\n");
@ -576,6 +568,39 @@ void MessageGenerator::GenerateMessageSerializationMethods(io::Printer* printer)
printer->Print("}\n\n");
}
void MessageGenerator::GenerateWriteToBody(io::Printer* printer, bool use_write_context) {
// Serialize all the fields
for (int i = 0; i < fields_by_number().size(); i++) {
std::unique_ptr<FieldGeneratorBase> generator(
CreateFieldGeneratorInternal(fields_by_number()[i]));
generator->GenerateSerializationCode(printer, use_write_context);
}
if (has_extension_ranges_) {
// Serialize extensions
printer->Print(
use_write_context
? "if (_extensions != null) {\n"
" _extensions.WriteTo(ref output);\n"
"}\n"
: "if (_extensions != null) {\n"
" _extensions.WriteTo(output);\n"
"}\n");
}
// Serialize unknown fields
printer->Print(
use_write_context
? "if (_unknownFields != null) {\n"
" _unknownFields.WriteTo(ref output);\n"
"}\n"
: "if (_unknownFields != null) {\n"
" _unknownFields.WriteTo(output);\n"
"}\n");
// TODO(jonskeet): Memoize size of frozen messages?
}
void MessageGenerator::GenerateMergingMethods(io::Printer* printer) {
// Note: These are separate from GenerateMessageSerializationMethods()
// because they need to be generated even for messages that are optimized

@ -66,6 +66,7 @@ class MessageGenerator : public SourceGeneratorBase {
bool has_extension_ranges_;
void GenerateMessageSerializationMethods(io::Printer* printer);
void GenerateWriteToBody(io::Printer* printer, bool use_write_context);
void GenerateMergingMethods(io::Printer* printer);
void GenerateMainParseLoop(io::Printer* printer, bool use_parse_context);

@ -90,9 +90,15 @@ void RepeatedEnumFieldGenerator::GenerateParsingCode(io::Printer* printer, bool
}
void RepeatedEnumFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
GenerateSerializationCode(printer, true);
}
void RepeatedEnumFieldGenerator::GenerateSerializationCode(io::Printer* printer, bool use_write_context) {
printer->Print(
variables_,
"$name$_.WriteTo(output, _repeated_$name$_codec);\n");
use_write_context
? "$name$_.WriteTo(ref output, _repeated_$name$_codec);\n"
: "$name$_.WriteTo(ref output, _repeated_$name$_codec);\n");
}
void RepeatedEnumFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {

@ -61,6 +61,7 @@ class RepeatedEnumFieldGenerator : public FieldGeneratorBase {
virtual void GenerateParsingCode(io::Printer* printer);
virtual void GenerateParsingCode(io::Printer* printer, bool use_parse_context);
virtual void GenerateSerializationCode(io::Printer* printer);
virtual void GenerateSerializationCode(io::Printer* printer, bool use_write_context);
virtual void GenerateSerializedSizeCode(io::Printer* printer);
virtual void GenerateExtensionCode(io::Printer* printer);

@ -105,9 +105,15 @@ void RepeatedMessageFieldGenerator::GenerateParsingCode(io::Printer* printer, bo
}
void RepeatedMessageFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
GenerateSerializationCode(printer, true);
}
void RepeatedMessageFieldGenerator::GenerateSerializationCode(io::Printer* printer, bool use_write_context) {
printer->Print(
variables_,
"$name$_.WriteTo(output, _repeated_$name$_codec);\n");
use_write_context
? "$name$_.WriteTo(ref output, _repeated_$name$_codec);\n"
: "$name$_.WriteTo(output, _repeated_$name$_codec);\n");
}
void RepeatedMessageFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {

@ -61,6 +61,7 @@ class RepeatedMessageFieldGenerator : public FieldGeneratorBase {
virtual void GenerateParsingCode(io::Printer* printer);
virtual void GenerateParsingCode(io::Printer* printer, bool use_parse_context);
virtual void GenerateSerializationCode(io::Printer* printer);
virtual void GenerateSerializationCode(io::Printer* printer, bool use_write_context);
virtual void GenerateSerializedSizeCode(io::Printer* printer);
virtual void GenerateExtensionCode(io::Printer* printer);

@ -90,9 +90,15 @@ void RepeatedPrimitiveFieldGenerator::GenerateParsingCode(io::Printer* printer,
}
void RepeatedPrimitiveFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
GenerateSerializationCode(printer, true);
}
void RepeatedPrimitiveFieldGenerator::GenerateSerializationCode(io::Printer* printer, bool use_write_context) {
printer->Print(
variables_,
"$name$_.WriteTo(output, _repeated_$name$_codec);\n");
use_write_context
? "$name$_.WriteTo(ref output, _repeated_$name$_codec);\n"
: "$name$_.WriteTo(output, _repeated_$name$_codec);\n");
}
void RepeatedPrimitiveFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {

@ -57,6 +57,7 @@ class RepeatedPrimitiveFieldGenerator : public FieldGeneratorBase {
virtual void GenerateParsingCode(io::Printer* printer);
virtual void GenerateParsingCode(io::Printer* printer, bool use_parse_context);
virtual void GenerateSerializationCode(io::Printer* printer);
virtual void GenerateSerializationCode(io::Printer* printer, bool use_write_context);
virtual void GenerateSerializedSizeCode(io::Printer* printer);
virtual void GenerateExtensionCode(io::Printer* printer);

@ -132,11 +132,19 @@ void WrapperFieldGenerator::GenerateParsingCode(io::Printer* printer, bool use_p
}
void WrapperFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
GenerateSerializationCode(printer, true);
}
void WrapperFieldGenerator::GenerateSerializationCode(io::Printer* printer, bool use_write_context) {
printer->Print(
variables_,
"if ($has_property_check$) {\n"
" _single_$name$_codec.WriteTagAndValue(output, $property_name$);\n"
"}\n");
use_write_context
? "if ($has_property_check$) {\n"
" _single_$name$_codec.WriteTagAndValue(ref output, $property_name$);\n"
"}\n"
: "if ($has_property_check$) {\n"
" _single_$name$_codec.WriteTagAndValue(output, $property_name$);\n"
"}\n");
}
void WrapperFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
@ -269,12 +277,20 @@ void WrapperOneofFieldGenerator::GenerateParsingCode(io::Printer* printer, bool
}
void WrapperOneofFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
GenerateSerializationCode(printer, true);
}
void WrapperOneofFieldGenerator::GenerateSerializationCode(io::Printer* printer, bool use_write_context) {
// TODO: I suspect this is wrong...
printer->Print(
variables_,
"if ($has_property_check$) {\n"
" _oneof_$name$_codec.WriteTagAndValue(output, ($type_name$) $oneof_name$_);\n"
"}\n");
use_write_context
? "if ($has_property_check$) {\n"
" _oneof_$name$_codec.WriteTagAndValue(ref output, ($type_name$) $oneof_name$_);\n"
"}\n"
: "if ($has_property_check$) {\n"
" _oneof_$name$_codec.WriteTagAndValue(output, ($type_name$) $oneof_name$_);\n"
"}\n");
}
void WrapperOneofFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {

@ -60,6 +60,7 @@ class WrapperFieldGenerator : public FieldGeneratorBase {
virtual void GenerateParsingCode(io::Printer* printer);
virtual void GenerateParsingCode(io::Printer* printer, bool use_parse_context);
virtual void GenerateSerializationCode(io::Printer* printer);
virtual void GenerateSerializationCode(io::Printer* printer, bool use_write_context);
virtual void GenerateSerializedSizeCode(io::Printer* printer);
virtual void GenerateExtensionCode(io::Printer* printer);
@ -86,6 +87,7 @@ class WrapperOneofFieldGenerator : public WrapperFieldGenerator {
virtual void GenerateParsingCode(io::Printer* printer);
virtual void GenerateParsingCode(io::Printer* printer, bool use_parse_context);
virtual void GenerateSerializationCode(io::Printer* printer);
virtual void GenerateSerializationCode(io::Printer* printer, bool use_write_context);
virtual void GenerateSerializedSizeCode(io::Printer* printer);
};

Loading…
Cancel
Save