浏览代码

Regenerate C# code with the new generator, adding unittest_proto3_optional.proto

The changes in the existing proto2 code are solely around presence bits. The new generator allocated presence bits more efficiently. (Previously bits were sometimes allocated but never used.)
Jon Skeet 5 年之前
父节点
当前提交
b0649a088a

+ 2 - 1
csharp/generate_protos.sh

@@ -63,7 +63,8 @@ $PROTOC -Isrc -Icsharp/protos \
     csharp/protos/unittest_issue6936_c.proto \
     src/google/protobuf/unittest_well_known_types.proto \
     src/google/protobuf/test_messages_proto3.proto \
-    src/google/protobuf/test_messages_proto2.proto
+    src/google/protobuf/test_messages_proto2.proto \
+    src/google/protobuf/unittest_proto3_optional.proto
 
 # AddressBook sample protos
 $PROTOC -Iexamples -Isrc --csharp_out=csharp/src/AddressBook \

+ 72 - 72
csharp/src/Google.Protobuf.Test.TestProtos/TestMessagesProto2.cs

@@ -1872,21 +1872,21 @@ namespace ProtobufTestMessages.Proto2 {
     /// </summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int Fieldname1 {
-      get { if ((_hasBits0 & 2097152) != 0) { return fieldname1_; } else { return Fieldname1DefaultValue; } }
+      get { if ((_hasBits0 & 32768) != 0) { return fieldname1_; } else { return Fieldname1DefaultValue; } }
       set {
-        _hasBits0 |= 2097152;
+        _hasBits0 |= 32768;
         fieldname1_ = value;
       }
     }
     /// <summary>Gets whether the "fieldname1" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldname1 {
-      get { return (_hasBits0 & 2097152) != 0; }
+      get { return (_hasBits0 & 32768) != 0; }
     }
     /// <summary>Clears the value of the "fieldname1" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldname1() {
-      _hasBits0 &= ~2097152;
+      _hasBits0 &= ~32768;
     }
 
     /// <summary>Field number for the "field_name2" field.</summary>
@@ -1896,21 +1896,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName2_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName2 {
-      get { if ((_hasBits0 & 4194304) != 0) { return fieldName2_; } else { return FieldName2DefaultValue; } }
+      get { if ((_hasBits0 & 65536) != 0) { return fieldName2_; } else { return FieldName2DefaultValue; } }
       set {
-        _hasBits0 |= 4194304;
+        _hasBits0 |= 65536;
         fieldName2_ = value;
       }
     }
     /// <summary>Gets whether the "field_name2" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName2 {
-      get { return (_hasBits0 & 4194304) != 0; }
+      get { return (_hasBits0 & 65536) != 0; }
     }
     /// <summary>Clears the value of the "field_name2" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName2() {
-      _hasBits0 &= ~4194304;
+      _hasBits0 &= ~65536;
     }
 
     /// <summary>Field number for the "_field_name3" field.</summary>
@@ -1920,21 +1920,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int FieldName3_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName3 {
-      get { if ((_hasBits0 & 8388608) != 0) { return FieldName3_; } else { return FieldName3DefaultValue; } }
+      get { if ((_hasBits0 & 131072) != 0) { return FieldName3_; } else { return FieldName3DefaultValue; } }
       set {
-        _hasBits0 |= 8388608;
+        _hasBits0 |= 131072;
         FieldName3_ = value;
       }
     }
     /// <summary>Gets whether the "_field_name3" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName3 {
-      get { return (_hasBits0 & 8388608) != 0; }
+      get { return (_hasBits0 & 131072) != 0; }
     }
     /// <summary>Clears the value of the "_field_name3" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName3() {
-      _hasBits0 &= ~8388608;
+      _hasBits0 &= ~131072;
     }
 
     /// <summary>Field number for the "field__name4_" field.</summary>
@@ -1944,21 +1944,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName4_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName4 {
-      get { if ((_hasBits0 & 16777216) != 0) { return fieldName4_; } else { return FieldName4DefaultValue; } }
+      get { if ((_hasBits0 & 262144) != 0) { return fieldName4_; } else { return FieldName4DefaultValue; } }
       set {
-        _hasBits0 |= 16777216;
+        _hasBits0 |= 262144;
         fieldName4_ = value;
       }
     }
     /// <summary>Gets whether the "field__name4_" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName4 {
-      get { return (_hasBits0 & 16777216) != 0; }
+      get { return (_hasBits0 & 262144) != 0; }
     }
     /// <summary>Clears the value of the "field__name4_" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName4() {
-      _hasBits0 &= ~16777216;
+      _hasBits0 &= ~262144;
     }
 
     /// <summary>Field number for the "field0name5" field.</summary>
@@ -1968,21 +1968,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int field0Name5_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int Field0Name5 {
-      get { if ((_hasBits0 & 33554432) != 0) { return field0Name5_; } else { return Field0Name5DefaultValue; } }
+      get { if ((_hasBits0 & 524288) != 0) { return field0Name5_; } else { return Field0Name5DefaultValue; } }
       set {
-        _hasBits0 |= 33554432;
+        _hasBits0 |= 524288;
         field0Name5_ = value;
       }
     }
     /// <summary>Gets whether the "field0name5" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasField0Name5 {
-      get { return (_hasBits0 & 33554432) != 0; }
+      get { return (_hasBits0 & 524288) != 0; }
     }
     /// <summary>Clears the value of the "field0name5" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearField0Name5() {
-      _hasBits0 &= ~33554432;
+      _hasBits0 &= ~524288;
     }
 
     /// <summary>Field number for the "field_0_name6" field.</summary>
@@ -1992,21 +1992,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int field0Name6_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int Field0Name6 {
-      get { if ((_hasBits0 & 67108864) != 0) { return field0Name6_; } else { return Field0Name6DefaultValue; } }
+      get { if ((_hasBits0 & 1048576) != 0) { return field0Name6_; } else { return Field0Name6DefaultValue; } }
       set {
-        _hasBits0 |= 67108864;
+        _hasBits0 |= 1048576;
         field0Name6_ = value;
       }
     }
     /// <summary>Gets whether the "field_0_name6" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasField0Name6 {
-      get { return (_hasBits0 & 67108864) != 0; }
+      get { return (_hasBits0 & 1048576) != 0; }
     }
     /// <summary>Clears the value of the "field_0_name6" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearField0Name6() {
-      _hasBits0 &= ~67108864;
+      _hasBits0 &= ~1048576;
     }
 
     /// <summary>Field number for the "fieldName7" field.</summary>
@@ -2016,21 +2016,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName7_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName7 {
-      get { if ((_hasBits0 & 134217728) != 0) { return fieldName7_; } else { return FieldName7DefaultValue; } }
+      get { if ((_hasBits0 & 2097152) != 0) { return fieldName7_; } else { return FieldName7DefaultValue; } }
       set {
-        _hasBits0 |= 134217728;
+        _hasBits0 |= 2097152;
         fieldName7_ = value;
       }
     }
     /// <summary>Gets whether the "fieldName7" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName7 {
-      get { return (_hasBits0 & 134217728) != 0; }
+      get { return (_hasBits0 & 2097152) != 0; }
     }
     /// <summary>Clears the value of the "fieldName7" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName7() {
-      _hasBits0 &= ~134217728;
+      _hasBits0 &= ~2097152;
     }
 
     /// <summary>Field number for the "FieldName8" field.</summary>
@@ -2040,21 +2040,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName8_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName8 {
-      get { if ((_hasBits0 & 268435456) != 0) { return fieldName8_; } else { return FieldName8DefaultValue; } }
+      get { if ((_hasBits0 & 4194304) != 0) { return fieldName8_; } else { return FieldName8DefaultValue; } }
       set {
-        _hasBits0 |= 268435456;
+        _hasBits0 |= 4194304;
         fieldName8_ = value;
       }
     }
     /// <summary>Gets whether the "FieldName8" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName8 {
-      get { return (_hasBits0 & 268435456) != 0; }
+      get { return (_hasBits0 & 4194304) != 0; }
     }
     /// <summary>Clears the value of the "FieldName8" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName8() {
-      _hasBits0 &= ~268435456;
+      _hasBits0 &= ~4194304;
     }
 
     /// <summary>Field number for the "field_Name9" field.</summary>
@@ -2064,21 +2064,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName9_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName9 {
-      get { if ((_hasBits0 & 536870912) != 0) { return fieldName9_; } else { return FieldName9DefaultValue; } }
+      get { if ((_hasBits0 & 8388608) != 0) { return fieldName9_; } else { return FieldName9DefaultValue; } }
       set {
-        _hasBits0 |= 536870912;
+        _hasBits0 |= 8388608;
         fieldName9_ = value;
       }
     }
     /// <summary>Gets whether the "field_Name9" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName9 {
-      get { return (_hasBits0 & 536870912) != 0; }
+      get { return (_hasBits0 & 8388608) != 0; }
     }
     /// <summary>Clears the value of the "field_Name9" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName9() {
-      _hasBits0 &= ~536870912;
+      _hasBits0 &= ~8388608;
     }
 
     /// <summary>Field number for the "Field_Name10" field.</summary>
@@ -2088,21 +2088,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName10_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName10 {
-      get { if ((_hasBits0 & 1073741824) != 0) { return fieldName10_; } else { return FieldName10DefaultValue; } }
+      get { if ((_hasBits0 & 16777216) != 0) { return fieldName10_; } else { return FieldName10DefaultValue; } }
       set {
-        _hasBits0 |= 1073741824;
+        _hasBits0 |= 16777216;
         fieldName10_ = value;
       }
     }
     /// <summary>Gets whether the "Field_Name10" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName10 {
-      get { return (_hasBits0 & 1073741824) != 0; }
+      get { return (_hasBits0 & 16777216) != 0; }
     }
     /// <summary>Clears the value of the "Field_Name10" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName10() {
-      _hasBits0 &= ~1073741824;
+      _hasBits0 &= ~16777216;
     }
 
     /// <summary>Field number for the "FIELD_NAME11" field.</summary>
@@ -2112,21 +2112,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fIELDNAME11_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FIELDNAME11 {
-      get { if ((_hasBits0 & -2147483648) != 0) { return fIELDNAME11_; } else { return FIELDNAME11DefaultValue; } }
+      get { if ((_hasBits0 & 33554432) != 0) { return fIELDNAME11_; } else { return FIELDNAME11DefaultValue; } }
       set {
-        _hasBits0 |= -2147483648;
+        _hasBits0 |= 33554432;
         fIELDNAME11_ = value;
       }
     }
     /// <summary>Gets whether the "FIELD_NAME11" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFIELDNAME11 {
-      get { return (_hasBits0 & -2147483648) != 0; }
+      get { return (_hasBits0 & 33554432) != 0; }
     }
     /// <summary>Clears the value of the "FIELD_NAME11" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFIELDNAME11() {
-      _hasBits0 &= ~-2147483648;
+      _hasBits0 &= ~33554432;
     }
 
     /// <summary>Field number for the "FIELD_name12" field.</summary>
@@ -2136,21 +2136,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fIELDName12_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FIELDName12 {
-      get { if ((_hasBits1 & 1) != 0) { return fIELDName12_; } else { return FIELDName12DefaultValue; } }
+      get { if ((_hasBits0 & 67108864) != 0) { return fIELDName12_; } else { return FIELDName12DefaultValue; } }
       set {
-        _hasBits1 |= 1;
+        _hasBits0 |= 67108864;
         fIELDName12_ = value;
       }
     }
     /// <summary>Gets whether the "FIELD_name12" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFIELDName12 {
-      get { return (_hasBits1 & 1) != 0; }
+      get { return (_hasBits0 & 67108864) != 0; }
     }
     /// <summary>Clears the value of the "FIELD_name12" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFIELDName12() {
-      _hasBits1 &= ~1;
+      _hasBits0 &= ~67108864;
     }
 
     /// <summary>Field number for the "__field_name13" field.</summary>
@@ -2160,21 +2160,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int FieldName13_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName13 {
-      get { if ((_hasBits1 & 2) != 0) { return FieldName13_; } else { return FieldName13DefaultValue; } }
+      get { if ((_hasBits0 & 134217728) != 0) { return FieldName13_; } else { return FieldName13DefaultValue; } }
       set {
-        _hasBits1 |= 2;
+        _hasBits0 |= 134217728;
         FieldName13_ = value;
       }
     }
     /// <summary>Gets whether the "__field_name13" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName13 {
-      get { return (_hasBits1 & 2) != 0; }
+      get { return (_hasBits0 & 134217728) != 0; }
     }
     /// <summary>Clears the value of the "__field_name13" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName13() {
-      _hasBits1 &= ~2;
+      _hasBits0 &= ~134217728;
     }
 
     /// <summary>Field number for the "__Field_name14" field.</summary>
@@ -2184,21 +2184,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int FieldName14_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName14 {
-      get { if ((_hasBits1 & 4) != 0) { return FieldName14_; } else { return FieldName14DefaultValue; } }
+      get { if ((_hasBits0 & 268435456) != 0) { return FieldName14_; } else { return FieldName14DefaultValue; } }
       set {
-        _hasBits1 |= 4;
+        _hasBits0 |= 268435456;
         FieldName14_ = value;
       }
     }
     /// <summary>Gets whether the "__Field_name14" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName14 {
-      get { return (_hasBits1 & 4) != 0; }
+      get { return (_hasBits0 & 268435456) != 0; }
     }
     /// <summary>Clears the value of the "__Field_name14" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName14() {
-      _hasBits1 &= ~4;
+      _hasBits0 &= ~268435456;
     }
 
     /// <summary>Field number for the "field__name15" field.</summary>
@@ -2208,21 +2208,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName15_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName15 {
-      get { if ((_hasBits1 & 8) != 0) { return fieldName15_; } else { return FieldName15DefaultValue; } }
+      get { if ((_hasBits0 & 536870912) != 0) { return fieldName15_; } else { return FieldName15DefaultValue; } }
       set {
-        _hasBits1 |= 8;
+        _hasBits0 |= 536870912;
         fieldName15_ = value;
       }
     }
     /// <summary>Gets whether the "field__name15" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName15 {
-      get { return (_hasBits1 & 8) != 0; }
+      get { return (_hasBits0 & 536870912) != 0; }
     }
     /// <summary>Clears the value of the "field__name15" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName15() {
-      _hasBits1 &= ~8;
+      _hasBits0 &= ~536870912;
     }
 
     /// <summary>Field number for the "field__Name16" field.</summary>
@@ -2232,21 +2232,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName16_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName16 {
-      get { if ((_hasBits1 & 16) != 0) { return fieldName16_; } else { return FieldName16DefaultValue; } }
+      get { if ((_hasBits0 & 1073741824) != 0) { return fieldName16_; } else { return FieldName16DefaultValue; } }
       set {
-        _hasBits1 |= 16;
+        _hasBits0 |= 1073741824;
         fieldName16_ = value;
       }
     }
     /// <summary>Gets whether the "field__Name16" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName16 {
-      get { return (_hasBits1 & 16) != 0; }
+      get { return (_hasBits0 & 1073741824) != 0; }
     }
     /// <summary>Clears the value of the "field__Name16" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName16() {
-      _hasBits1 &= ~16;
+      _hasBits0 &= ~1073741824;
     }
 
     /// <summary>Field number for the "field_name17__" field.</summary>
@@ -2256,21 +2256,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName17_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName17 {
-      get { if ((_hasBits1 & 32) != 0) { return fieldName17_; } else { return FieldName17DefaultValue; } }
+      get { if ((_hasBits0 & -2147483648) != 0) { return fieldName17_; } else { return FieldName17DefaultValue; } }
       set {
-        _hasBits1 |= 32;
+        _hasBits0 |= -2147483648;
         fieldName17_ = value;
       }
     }
     /// <summary>Gets whether the "field_name17__" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName17 {
-      get { return (_hasBits1 & 32) != 0; }
+      get { return (_hasBits0 & -2147483648) != 0; }
     }
     /// <summary>Clears the value of the "field_name17__" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName17() {
-      _hasBits1 &= ~32;
+      _hasBits0 &= ~-2147483648;
     }
 
     /// <summary>Field number for the "Field_name18__" field.</summary>
@@ -2280,21 +2280,21 @@ namespace ProtobufTestMessages.Proto2 {
     private int fieldName18_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int FieldName18 {
-      get { if ((_hasBits1 & 64) != 0) { return fieldName18_; } else { return FieldName18DefaultValue; } }
+      get { if ((_hasBits1 & 1) != 0) { return fieldName18_; } else { return FieldName18DefaultValue; } }
       set {
-        _hasBits1 |= 64;
+        _hasBits1 |= 1;
         fieldName18_ = value;
       }
     }
     /// <summary>Gets whether the "Field_name18__" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasFieldName18 {
-      get { return (_hasBits1 & 64) != 0; }
+      get { return (_hasBits1 & 1) != 0; }
     }
     /// <summary>Clears the value of the "Field_name18__" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearFieldName18() {
-      _hasBits1 &= ~64;
+      _hasBits1 &= ~1;
     }
 
     private object oneofField_;

+ 4 - 8
csharp/src/Google.Protobuf.Test.TestProtos/Unittest.cs

@@ -15521,7 +15521,6 @@ namespace Google.Protobuf.TestProtos.Proto2 {
   public sealed partial class TestOneof : pb::IMessage<TestOneof> {
     private static readonly pb::MessageParser<TestOneof> _parser = new pb::MessageParser<TestOneof>(() => new TestOneof());
     private pb::UnknownFieldSet _unknownFields;
-    private int _hasBits0;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public static pb::MessageParser<TestOneof> Parser { get { return _parser; } }
 
@@ -15544,7 +15543,6 @@ namespace Google.Protobuf.TestProtos.Proto2 {
 
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public TestOneof(TestOneof other) : this() {
-      _hasBits0 = other._hasBits0;
       switch (other.FooCase) {
         case FooOneofCase.FooInt:
           FooInt = other.FooInt;
@@ -16934,21 +16932,21 @@ namespace Google.Protobuf.TestProtos.Proto2 {
     private int bazInt_;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public int BazInt {
-      get { if ((_hasBits0 & 16) != 0) { return bazInt_; } else { return BazIntDefaultValue; } }
+      get { if ((_hasBits0 & 1) != 0) { return bazInt_; } else { return BazIntDefaultValue; } }
       set {
-        _hasBits0 |= 16;
+        _hasBits0 |= 1;
         bazInt_ = value;
       }
     }
     /// <summary>Gets whether the "baz_int" field is set</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public bool HasBazInt {
-      get { return (_hasBits0 & 16) != 0; }
+      get { return (_hasBits0 & 1) != 0; }
     }
     /// <summary>Clears the value of the "baz_int" field</summary>
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public void ClearBazInt() {
-      _hasBits0 &= ~16;
+      _hasBits0 &= ~1;
     }
 
     /// <summary>Field number for the "baz_string" field.</summary>
@@ -17767,7 +17765,6 @@ namespace Google.Protobuf.TestProtos.Proto2 {
   public sealed partial class TestRequiredOneof : pb::IMessage<TestRequiredOneof> {
     private static readonly pb::MessageParser<TestRequiredOneof> _parser = new pb::MessageParser<TestRequiredOneof>(() => new TestRequiredOneof());
     private pb::UnknownFieldSet _unknownFields;
-    private int _hasBits0;
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public static pb::MessageParser<TestRequiredOneof> Parser { get { return _parser; } }
 
@@ -17790,7 +17787,6 @@ namespace Google.Protobuf.TestProtos.Proto2 {
 
     [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
     public TestRequiredOneof(TestRequiredOneof other) : this() {
-      _hasBits0 = other._hasBits0;
       switch (other.FooCase) {
         case FooOneofCase.FooInt:
           FooInt = other.FooInt;

+ 1072 - 0
csharp/src/Google.Protobuf.Test.TestProtos/UnittestProto3Optional.cs

@@ -0,0 +1,1072 @@
+// <auto-generated>
+//     Generated by the protocol buffer compiler.  DO NOT EDIT!
+//     source: google/protobuf/unittest_proto3_optional.proto
+// </auto-generated>
+#pragma warning disable 1591, 0612, 3021
+#region Designer generated code
+
+using pb = global::Google.Protobuf;
+using pbc = global::Google.Protobuf.Collections;
+using pbr = global::Google.Protobuf.Reflection;
+using scg = global::System.Collections.Generic;
+namespace ProtobufUnittest {
+
+  /// <summary>Holder for reflection information generated from google/protobuf/unittest_proto3_optional.proto</summary>
+  public static partial class UnittestProto3OptionalReflection {
+
+    #region Descriptor
+    /// <summary>File descriptor for google/protobuf/unittest_proto3_optional.proto</summary>
+    public static pbr::FileDescriptor Descriptor {
+      get { return descriptor; }
+    }
+    private static pbr::FileDescriptor descriptor;
+
+    static UnittestProto3OptionalReflection() {
+      byte[] descriptorData = global::System.Convert.FromBase64String(
+          string.Concat(
+            "Ci5nb29nbGUvcHJvdG9idWYvdW5pdHRlc3RfcHJvdG8zX29wdGlvbmFsLnBy",
+            "b3RvEhFwcm90b2J1Zl91bml0dGVzdCKBCgoSVGVzdFByb3RvM09wdGlvbmFs",
+            "EhsKDm9wdGlvbmFsX2ludDMyGAEgASgFSACIAQESGwoOb3B0aW9uYWxfaW50",
+            "NjQYAiABKANIAYgBARIcCg9vcHRpb25hbF91aW50MzIYAyABKA1IAogBARIc",
+            "Cg9vcHRpb25hbF91aW50NjQYBCABKARIA4gBARIcCg9vcHRpb25hbF9zaW50",
+            "MzIYBSABKBFIBIgBARIcCg9vcHRpb25hbF9zaW50NjQYBiABKBJIBYgBARId",
+            "ChBvcHRpb25hbF9maXhlZDMyGAcgASgHSAaIAQESHQoQb3B0aW9uYWxfZml4",
+            "ZWQ2NBgIIAEoBkgHiAEBEh4KEW9wdGlvbmFsX3NmaXhlZDMyGAkgASgPSAiI",
+            "AQESHgoRb3B0aW9uYWxfc2ZpeGVkNjQYCiABKBBICYgBARIbCg5vcHRpb25h",
+            "bF9mbG9hdBgLIAEoAkgKiAEBEhwKD29wdGlvbmFsX2RvdWJsZRgMIAEoAUgL",
+            "iAEBEhoKDW9wdGlvbmFsX2Jvb2wYDSABKAhIDIgBARIcCg9vcHRpb25hbF9z",
+            "dHJpbmcYDiABKAlIDYgBARIbCg5vcHRpb25hbF9ieXRlcxgPIAEoDEgOiAEB",
+            "Eh4KDW9wdGlvbmFsX2NvcmQYECABKAlCAggBSA+IAQESWQoXb3B0aW9uYWxf",
+            "bmVzdGVkX21lc3NhZ2UYEiABKAsyMy5wcm90b2J1Zl91bml0dGVzdC5UZXN0",
+            "UHJvdG8zT3B0aW9uYWwuTmVzdGVkTWVzc2FnZUgQiAEBElkKE2xhenlfbmVz",
+            "dGVkX21lc3NhZ2UYEyABKAsyMy5wcm90b2J1Zl91bml0dGVzdC5UZXN0UHJv",
+            "dG8zT3B0aW9uYWwuTmVzdGVkTWVzc2FnZUICKAFIEYgBARJTChRvcHRpb25h",
+            "bF9uZXN0ZWRfZW51bRgVIAEoDjIwLnByb3RvYnVmX3VuaXR0ZXN0LlRlc3RQ",
+            "cm90bzNPcHRpb25hbC5OZXN0ZWRFbnVtSBKIAQEaJwoNTmVzdGVkTWVzc2Fn",
+            "ZRIPCgJiYhgBIAEoBUgAiAEBQgUKA19iYiJKCgpOZXN0ZWRFbnVtEg8KC1VO",
+            "U1BFQ0lGSUVEEAASBwoDRk9PEAESBwoDQkFSEAISBwoDQkFaEAMSEAoDTkVH",
+            "EP///////////wFCEQoPX29wdGlvbmFsX2ludDMyQhEKD19vcHRpb25hbF9p",
+            "bnQ2NEISChBfb3B0aW9uYWxfdWludDMyQhIKEF9vcHRpb25hbF91aW50NjRC",
+            "EgoQX29wdGlvbmFsX3NpbnQzMkISChBfb3B0aW9uYWxfc2ludDY0QhMKEV9v",
+            "cHRpb25hbF9maXhlZDMyQhMKEV9vcHRpb25hbF9maXhlZDY0QhQKEl9vcHRp",
+            "b25hbF9zZml4ZWQzMkIUChJfb3B0aW9uYWxfc2ZpeGVkNjRCEQoPX29wdGlv",
+            "bmFsX2Zsb2F0QhIKEF9vcHRpb25hbF9kb3VibGVCEAoOX29wdGlvbmFsX2Jv",
+            "b2xCEgoQX29wdGlvbmFsX3N0cmluZ0IRCg9fb3B0aW9uYWxfYnl0ZXNCEAoO",
+            "X29wdGlvbmFsX2NvcmRCGgoYX29wdGlvbmFsX25lc3RlZF9tZXNzYWdlQhYK",
+            "FF9sYXp5X25lc3RlZF9tZXNzYWdlQhcKFV9vcHRpb25hbF9uZXN0ZWRfZW51",
+            "bUIlCiFjb20uZ29vZ2xlLnByb3RvYnVmLnRlc3RpbmcucHJvdG9QAWIGcHJv",
+            "dG8z"));
+      descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,
+          new pbr::FileDescriptor[] { },
+          new pbr::GeneratedClrTypeInfo(null, null, new pbr::GeneratedClrTypeInfo[] {
+            new pbr::GeneratedClrTypeInfo(typeof(global::ProtobufUnittest.TestProto3Optional), global::ProtobufUnittest.TestProto3Optional.Parser, new[]{ "OptionalInt32", "OptionalInt64", "OptionalUint32", "OptionalUint64", "OptionalSint32", "OptionalSint64", "OptionalFixed32", "OptionalFixed64", "OptionalSfixed32", "OptionalSfixed64", "OptionalFloat", "OptionalDouble", "OptionalBool", "OptionalString", "OptionalBytes", "OptionalCord", "OptionalNestedMessage", "LazyNestedMessage", "OptionalNestedEnum" }, new[]{ "OptionalInt32", "OptionalInt64", "OptionalUint32", "OptionalUint64", "OptionalSint32", "OptionalSint64", "OptionalFixed32", "OptionalFixed64", "OptionalSfixed32", "OptionalSfixed64", "OptionalFloat", "OptionalDouble", "OptionalBool", "OptionalString", "OptionalBytes", "OptionalCord", "OptionalNestedMessage", "LazyNestedMessage", "OptionalNestedEnum" }, new[]{ typeof(global::ProtobufUnittest.TestProto3Optional.Types.NestedEnum) }, null, new pbr::GeneratedClrTypeInfo[] { new pbr::GeneratedClrTypeInfo(typeof(global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage), global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage.Parser, new[]{ "Bb" }, new[]{ "Bb" }, null, null, null)})
+          }));
+    }
+    #endregion
+
+  }
+  #region Messages
+  public sealed partial class TestProto3Optional : pb::IMessage<TestProto3Optional> {
+    private static readonly pb::MessageParser<TestProto3Optional> _parser = new pb::MessageParser<TestProto3Optional>(() => new TestProto3Optional());
+    private pb::UnknownFieldSet _unknownFields;
+    private int _hasBits0;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public static pb::MessageParser<TestProto3Optional> Parser { get { return _parser; } }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public static pbr::MessageDescriptor Descriptor {
+      get { return global::ProtobufUnittest.UnittestProto3OptionalReflection.Descriptor.MessageTypes[0]; }
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    pbr::MessageDescriptor pb::IMessage.Descriptor {
+      get { return Descriptor; }
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public TestProto3Optional() {
+      OnConstruction();
+    }
+
+    partial void OnConstruction();
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public TestProto3Optional(TestProto3Optional other) : this() {
+      _hasBits0 = other._hasBits0;
+      optionalInt32_ = other.optionalInt32_;
+      optionalInt64_ = other.optionalInt64_;
+      optionalUint32_ = other.optionalUint32_;
+      optionalUint64_ = other.optionalUint64_;
+      optionalSint32_ = other.optionalSint32_;
+      optionalSint64_ = other.optionalSint64_;
+      optionalFixed32_ = other.optionalFixed32_;
+      optionalFixed64_ = other.optionalFixed64_;
+      optionalSfixed32_ = other.optionalSfixed32_;
+      optionalSfixed64_ = other.optionalSfixed64_;
+      optionalFloat_ = other.optionalFloat_;
+      optionalDouble_ = other.optionalDouble_;
+      optionalBool_ = other.optionalBool_;
+      optionalString_ = other.optionalString_;
+      optionalBytes_ = other.optionalBytes_;
+      optionalCord_ = other.optionalCord_;
+      optionalNestedMessage_ = other.optionalNestedMessage_ != null ? other.optionalNestedMessage_.Clone() : null;
+      lazyNestedMessage_ = other.lazyNestedMessage_ != null ? other.lazyNestedMessage_.Clone() : null;
+      optionalNestedEnum_ = other.optionalNestedEnum_;
+      _unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields);
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public TestProto3Optional Clone() {
+      return new TestProto3Optional(this);
+    }
+
+    /// <summary>Field number for the "optional_int32" field.</summary>
+    public const int OptionalInt32FieldNumber = 1;
+    private int optionalInt32_;
+    /// <summary>
+    /// Singular
+    /// </summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public int OptionalInt32 {
+      get { if ((_hasBits0 & 1) != 0) { return optionalInt32_; } else { return 0; } }
+      set {
+        _hasBits0 |= 1;
+        optionalInt32_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_int32" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalInt32 {
+      get { return (_hasBits0 & 1) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_int32" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalInt32() {
+      _hasBits0 &= ~1;
+    }
+
+    /// <summary>Field number for the "optional_int64" field.</summary>
+    public const int OptionalInt64FieldNumber = 2;
+    private long optionalInt64_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public long OptionalInt64 {
+      get { if ((_hasBits0 & 2) != 0) { return optionalInt64_; } else { return 0L; } }
+      set {
+        _hasBits0 |= 2;
+        optionalInt64_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_int64" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalInt64 {
+      get { return (_hasBits0 & 2) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_int64" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalInt64() {
+      _hasBits0 &= ~2;
+    }
+
+    /// <summary>Field number for the "optional_uint32" field.</summary>
+    public const int OptionalUint32FieldNumber = 3;
+    private uint optionalUint32_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public uint OptionalUint32 {
+      get { if ((_hasBits0 & 4) != 0) { return optionalUint32_; } else { return 0; } }
+      set {
+        _hasBits0 |= 4;
+        optionalUint32_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_uint32" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalUint32 {
+      get { return (_hasBits0 & 4) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_uint32" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalUint32() {
+      _hasBits0 &= ~4;
+    }
+
+    /// <summary>Field number for the "optional_uint64" field.</summary>
+    public const int OptionalUint64FieldNumber = 4;
+    private ulong optionalUint64_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public ulong OptionalUint64 {
+      get { if ((_hasBits0 & 8) != 0) { return optionalUint64_; } else { return 0UL; } }
+      set {
+        _hasBits0 |= 8;
+        optionalUint64_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_uint64" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalUint64 {
+      get { return (_hasBits0 & 8) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_uint64" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalUint64() {
+      _hasBits0 &= ~8;
+    }
+
+    /// <summary>Field number for the "optional_sint32" field.</summary>
+    public const int OptionalSint32FieldNumber = 5;
+    private int optionalSint32_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public int OptionalSint32 {
+      get { if ((_hasBits0 & 16) != 0) { return optionalSint32_; } else { return 0; } }
+      set {
+        _hasBits0 |= 16;
+        optionalSint32_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_sint32" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalSint32 {
+      get { return (_hasBits0 & 16) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_sint32" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalSint32() {
+      _hasBits0 &= ~16;
+    }
+
+    /// <summary>Field number for the "optional_sint64" field.</summary>
+    public const int OptionalSint64FieldNumber = 6;
+    private long optionalSint64_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public long OptionalSint64 {
+      get { if ((_hasBits0 & 32) != 0) { return optionalSint64_; } else { return 0L; } }
+      set {
+        _hasBits0 |= 32;
+        optionalSint64_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_sint64" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalSint64 {
+      get { return (_hasBits0 & 32) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_sint64" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalSint64() {
+      _hasBits0 &= ~32;
+    }
+
+    /// <summary>Field number for the "optional_fixed32" field.</summary>
+    public const int OptionalFixed32FieldNumber = 7;
+    private uint optionalFixed32_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public uint OptionalFixed32 {
+      get { if ((_hasBits0 & 64) != 0) { return optionalFixed32_; } else { return 0; } }
+      set {
+        _hasBits0 |= 64;
+        optionalFixed32_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_fixed32" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalFixed32 {
+      get { return (_hasBits0 & 64) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_fixed32" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalFixed32() {
+      _hasBits0 &= ~64;
+    }
+
+    /// <summary>Field number for the "optional_fixed64" field.</summary>
+    public const int OptionalFixed64FieldNumber = 8;
+    private ulong optionalFixed64_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public ulong OptionalFixed64 {
+      get { if ((_hasBits0 & 128) != 0) { return optionalFixed64_; } else { return 0UL; } }
+      set {
+        _hasBits0 |= 128;
+        optionalFixed64_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_fixed64" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalFixed64 {
+      get { return (_hasBits0 & 128) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_fixed64" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalFixed64() {
+      _hasBits0 &= ~128;
+    }
+
+    /// <summary>Field number for the "optional_sfixed32" field.</summary>
+    public const int OptionalSfixed32FieldNumber = 9;
+    private int optionalSfixed32_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public int OptionalSfixed32 {
+      get { if ((_hasBits0 & 256) != 0) { return optionalSfixed32_; } else { return 0; } }
+      set {
+        _hasBits0 |= 256;
+        optionalSfixed32_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_sfixed32" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalSfixed32 {
+      get { return (_hasBits0 & 256) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_sfixed32" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalSfixed32() {
+      _hasBits0 &= ~256;
+    }
+
+    /// <summary>Field number for the "optional_sfixed64" field.</summary>
+    public const int OptionalSfixed64FieldNumber = 10;
+    private long optionalSfixed64_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public long OptionalSfixed64 {
+      get { if ((_hasBits0 & 512) != 0) { return optionalSfixed64_; } else { return 0L; } }
+      set {
+        _hasBits0 |= 512;
+        optionalSfixed64_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_sfixed64" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalSfixed64 {
+      get { return (_hasBits0 & 512) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_sfixed64" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalSfixed64() {
+      _hasBits0 &= ~512;
+    }
+
+    /// <summary>Field number for the "optional_float" field.</summary>
+    public const int OptionalFloatFieldNumber = 11;
+    private float optionalFloat_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public float OptionalFloat {
+      get { if ((_hasBits0 & 1024) != 0) { return optionalFloat_; } else { return 0F; } }
+      set {
+        _hasBits0 |= 1024;
+        optionalFloat_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_float" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalFloat {
+      get { return (_hasBits0 & 1024) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_float" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalFloat() {
+      _hasBits0 &= ~1024;
+    }
+
+    /// <summary>Field number for the "optional_double" field.</summary>
+    public const int OptionalDoubleFieldNumber = 12;
+    private double optionalDouble_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public double OptionalDouble {
+      get { if ((_hasBits0 & 2048) != 0) { return optionalDouble_; } else { return 0D; } }
+      set {
+        _hasBits0 |= 2048;
+        optionalDouble_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_double" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalDouble {
+      get { return (_hasBits0 & 2048) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_double" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalDouble() {
+      _hasBits0 &= ~2048;
+    }
+
+    /// <summary>Field number for the "optional_bool" field.</summary>
+    public const int OptionalBoolFieldNumber = 13;
+    private bool optionalBool_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool OptionalBool {
+      get { if ((_hasBits0 & 4096) != 0) { return optionalBool_; } else { return false; } }
+      set {
+        _hasBits0 |= 4096;
+        optionalBool_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_bool" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalBool {
+      get { return (_hasBits0 & 4096) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_bool" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalBool() {
+      _hasBits0 &= ~4096;
+    }
+
+    /// <summary>Field number for the "optional_string" field.</summary>
+    public const int OptionalStringFieldNumber = 14;
+    private string optionalString_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public string OptionalString {
+      get { return optionalString_ ?? ""; }
+      set {
+        optionalString_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
+      }
+    }
+    /// <summary>Gets whether the "optional_string" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalString {
+      get { return optionalString_ != null; }
+    }
+    /// <summary>Clears the value of the "optional_string" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalString() {
+      optionalString_ = null;
+    }
+
+    /// <summary>Field number for the "optional_bytes" field.</summary>
+    public const int OptionalBytesFieldNumber = 15;
+    private pb::ByteString optionalBytes_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public pb::ByteString OptionalBytes {
+      get { return optionalBytes_ ?? pb::ByteString.Empty; }
+      set {
+        optionalBytes_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
+      }
+    }
+    /// <summary>Gets whether the "optional_bytes" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalBytes {
+      get { return optionalBytes_ != null; }
+    }
+    /// <summary>Clears the value of the "optional_bytes" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalBytes() {
+      optionalBytes_ = null;
+    }
+
+    /// <summary>Field number for the "optional_cord" field.</summary>
+    public const int OptionalCordFieldNumber = 16;
+    private string optionalCord_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public string OptionalCord {
+      get { return optionalCord_ ?? ""; }
+      set {
+        optionalCord_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
+      }
+    }
+    /// <summary>Gets whether the "optional_cord" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalCord {
+      get { return optionalCord_ != null; }
+    }
+    /// <summary>Clears the value of the "optional_cord" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalCord() {
+      optionalCord_ = null;
+    }
+
+    /// <summary>Field number for the "optional_nested_message" field.</summary>
+    public const int OptionalNestedMessageFieldNumber = 18;
+    private global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage optionalNestedMessage_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage OptionalNestedMessage {
+      get { return optionalNestedMessage_; }
+      set {
+        optionalNestedMessage_ = value;
+      }
+    }
+
+    /// <summary>Field number for the "lazy_nested_message" field.</summary>
+    public const int LazyNestedMessageFieldNumber = 19;
+    private global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage lazyNestedMessage_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage LazyNestedMessage {
+      get { return lazyNestedMessage_; }
+      set {
+        lazyNestedMessage_ = value;
+      }
+    }
+
+    /// <summary>Field number for the "optional_nested_enum" field.</summary>
+    public const int OptionalNestedEnumFieldNumber = 21;
+    private global::ProtobufUnittest.TestProto3Optional.Types.NestedEnum optionalNestedEnum_;
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public global::ProtobufUnittest.TestProto3Optional.Types.NestedEnum OptionalNestedEnum {
+      get { if ((_hasBits0 & 8192) != 0) { return optionalNestedEnum_; } else { return global::ProtobufUnittest.TestProto3Optional.Types.NestedEnum.Unspecified; } }
+      set {
+        _hasBits0 |= 8192;
+        optionalNestedEnum_ = value;
+      }
+    }
+    /// <summary>Gets whether the "optional_nested_enum" field is set</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool HasOptionalNestedEnum {
+      get { return (_hasBits0 & 8192) != 0; }
+    }
+    /// <summary>Clears the value of the "optional_nested_enum" field</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void ClearOptionalNestedEnum() {
+      _hasBits0 &= ~8192;
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public override bool Equals(object other) {
+      return Equals(other as TestProto3Optional);
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public bool Equals(TestProto3Optional other) {
+      if (ReferenceEquals(other, null)) {
+        return false;
+      }
+      if (ReferenceEquals(other, this)) {
+        return true;
+      }
+      if (OptionalInt32 != other.OptionalInt32) return false;
+      if (OptionalInt64 != other.OptionalInt64) return false;
+      if (OptionalUint32 != other.OptionalUint32) return false;
+      if (OptionalUint64 != other.OptionalUint64) return false;
+      if (OptionalSint32 != other.OptionalSint32) return false;
+      if (OptionalSint64 != other.OptionalSint64) return false;
+      if (OptionalFixed32 != other.OptionalFixed32) return false;
+      if (OptionalFixed64 != other.OptionalFixed64) return false;
+      if (OptionalSfixed32 != other.OptionalSfixed32) return false;
+      if (OptionalSfixed64 != other.OptionalSfixed64) return false;
+      if (!pbc::ProtobufEqualityComparers.BitwiseSingleEqualityComparer.Equals(OptionalFloat, other.OptionalFloat)) return false;
+      if (!pbc::ProtobufEqualityComparers.BitwiseDoubleEqualityComparer.Equals(OptionalDouble, other.OptionalDouble)) return false;
+      if (OptionalBool != other.OptionalBool) return false;
+      if (OptionalString != other.OptionalString) return false;
+      if (OptionalBytes != other.OptionalBytes) return false;
+      if (OptionalCord != other.OptionalCord) return false;
+      if (!object.Equals(OptionalNestedMessage, other.OptionalNestedMessage)) return false;
+      if (!object.Equals(LazyNestedMessage, other.LazyNestedMessage)) return false;
+      if (OptionalNestedEnum != other.OptionalNestedEnum) return false;
+      return Equals(_unknownFields, other._unknownFields);
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public override int GetHashCode() {
+      int hash = 1;
+      if (HasOptionalInt32) hash ^= OptionalInt32.GetHashCode();
+      if (HasOptionalInt64) hash ^= OptionalInt64.GetHashCode();
+      if (HasOptionalUint32) hash ^= OptionalUint32.GetHashCode();
+      if (HasOptionalUint64) hash ^= OptionalUint64.GetHashCode();
+      if (HasOptionalSint32) hash ^= OptionalSint32.GetHashCode();
+      if (HasOptionalSint64) hash ^= OptionalSint64.GetHashCode();
+      if (HasOptionalFixed32) hash ^= OptionalFixed32.GetHashCode();
+      if (HasOptionalFixed64) hash ^= OptionalFixed64.GetHashCode();
+      if (HasOptionalSfixed32) hash ^= OptionalSfixed32.GetHashCode();
+      if (HasOptionalSfixed64) hash ^= OptionalSfixed64.GetHashCode();
+      if (HasOptionalFloat) hash ^= pbc::ProtobufEqualityComparers.BitwiseSingleEqualityComparer.GetHashCode(OptionalFloat);
+      if (HasOptionalDouble) hash ^= pbc::ProtobufEqualityComparers.BitwiseDoubleEqualityComparer.GetHashCode(OptionalDouble);
+      if (HasOptionalBool) hash ^= OptionalBool.GetHashCode();
+      if (HasOptionalString) hash ^= OptionalString.GetHashCode();
+      if (HasOptionalBytes) hash ^= OptionalBytes.GetHashCode();
+      if (HasOptionalCord) hash ^= OptionalCord.GetHashCode();
+      if (optionalNestedMessage_ != null) hash ^= OptionalNestedMessage.GetHashCode();
+      if (lazyNestedMessage_ != null) hash ^= LazyNestedMessage.GetHashCode();
+      if (HasOptionalNestedEnum) hash ^= OptionalNestedEnum.GetHashCode();
+      if (_unknownFields != null) {
+        hash ^= _unknownFields.GetHashCode();
+      }
+      return hash;
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public override string ToString() {
+      return pb::JsonFormatter.ToDiagnosticString(this);
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void WriteTo(pb::CodedOutputStream output) {
+      if (HasOptionalInt32) {
+        output.WriteRawTag(8);
+        output.WriteInt32(OptionalInt32);
+      }
+      if (HasOptionalInt64) {
+        output.WriteRawTag(16);
+        output.WriteInt64(OptionalInt64);
+      }
+      if (HasOptionalUint32) {
+        output.WriteRawTag(24);
+        output.WriteUInt32(OptionalUint32);
+      }
+      if (HasOptionalUint64) {
+        output.WriteRawTag(32);
+        output.WriteUInt64(OptionalUint64);
+      }
+      if (HasOptionalSint32) {
+        output.WriteRawTag(40);
+        output.WriteSInt32(OptionalSint32);
+      }
+      if (HasOptionalSint64) {
+        output.WriteRawTag(48);
+        output.WriteSInt64(OptionalSint64);
+      }
+      if (HasOptionalFixed32) {
+        output.WriteRawTag(61);
+        output.WriteFixed32(OptionalFixed32);
+      }
+      if (HasOptionalFixed64) {
+        output.WriteRawTag(65);
+        output.WriteFixed64(OptionalFixed64);
+      }
+      if (HasOptionalSfixed32) {
+        output.WriteRawTag(77);
+        output.WriteSFixed32(OptionalSfixed32);
+      }
+      if (HasOptionalSfixed64) {
+        output.WriteRawTag(81);
+        output.WriteSFixed64(OptionalSfixed64);
+      }
+      if (HasOptionalFloat) {
+        output.WriteRawTag(93);
+        output.WriteFloat(OptionalFloat);
+      }
+      if (HasOptionalDouble) {
+        output.WriteRawTag(97);
+        output.WriteDouble(OptionalDouble);
+      }
+      if (HasOptionalBool) {
+        output.WriteRawTag(104);
+        output.WriteBool(OptionalBool);
+      }
+      if (HasOptionalString) {
+        output.WriteRawTag(114);
+        output.WriteString(OptionalString);
+      }
+      if (HasOptionalBytes) {
+        output.WriteRawTag(122);
+        output.WriteBytes(OptionalBytes);
+      }
+      if (HasOptionalCord) {
+        output.WriteRawTag(130, 1);
+        output.WriteString(OptionalCord);
+      }
+      if (optionalNestedMessage_ != null) {
+        output.WriteRawTag(146, 1);
+        output.WriteMessage(OptionalNestedMessage);
+      }
+      if (lazyNestedMessage_ != null) {
+        output.WriteRawTag(154, 1);
+        output.WriteMessage(LazyNestedMessage);
+      }
+      if (HasOptionalNestedEnum) {
+        output.WriteRawTag(168, 1);
+        output.WriteEnum((int) OptionalNestedEnum);
+      }
+      if (_unknownFields != null) {
+        _unknownFields.WriteTo(output);
+      }
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public int CalculateSize() {
+      int size = 0;
+      if (HasOptionalInt32) {
+        size += 1 + pb::CodedOutputStream.ComputeInt32Size(OptionalInt32);
+      }
+      if (HasOptionalInt64) {
+        size += 1 + pb::CodedOutputStream.ComputeInt64Size(OptionalInt64);
+      }
+      if (HasOptionalUint32) {
+        size += 1 + pb::CodedOutputStream.ComputeUInt32Size(OptionalUint32);
+      }
+      if (HasOptionalUint64) {
+        size += 1 + pb::CodedOutputStream.ComputeUInt64Size(OptionalUint64);
+      }
+      if (HasOptionalSint32) {
+        size += 1 + pb::CodedOutputStream.ComputeSInt32Size(OptionalSint32);
+      }
+      if (HasOptionalSint64) {
+        size += 1 + pb::CodedOutputStream.ComputeSInt64Size(OptionalSint64);
+      }
+      if (HasOptionalFixed32) {
+        size += 1 + 4;
+      }
+      if (HasOptionalFixed64) {
+        size += 1 + 8;
+      }
+      if (HasOptionalSfixed32) {
+        size += 1 + 4;
+      }
+      if (HasOptionalSfixed64) {
+        size += 1 + 8;
+      }
+      if (HasOptionalFloat) {
+        size += 1 + 4;
+      }
+      if (HasOptionalDouble) {
+        size += 1 + 8;
+      }
+      if (HasOptionalBool) {
+        size += 1 + 1;
+      }
+      if (HasOptionalString) {
+        size += 1 + pb::CodedOutputStream.ComputeStringSize(OptionalString);
+      }
+      if (HasOptionalBytes) {
+        size += 1 + pb::CodedOutputStream.ComputeBytesSize(OptionalBytes);
+      }
+      if (HasOptionalCord) {
+        size += 2 + pb::CodedOutputStream.ComputeStringSize(OptionalCord);
+      }
+      if (optionalNestedMessage_ != null) {
+        size += 2 + pb::CodedOutputStream.ComputeMessageSize(OptionalNestedMessage);
+      }
+      if (lazyNestedMessage_ != null) {
+        size += 2 + pb::CodedOutputStream.ComputeMessageSize(LazyNestedMessage);
+      }
+      if (HasOptionalNestedEnum) {
+        size += 2 + pb::CodedOutputStream.ComputeEnumSize((int) OptionalNestedEnum);
+      }
+      if (_unknownFields != null) {
+        size += _unknownFields.CalculateSize();
+      }
+      return size;
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void MergeFrom(TestProto3Optional other) {
+      if (other == null) {
+        return;
+      }
+      if (other.HasOptionalInt32) {
+        OptionalInt32 = other.OptionalInt32;
+      }
+      if (other.HasOptionalInt64) {
+        OptionalInt64 = other.OptionalInt64;
+      }
+      if (other.HasOptionalUint32) {
+        OptionalUint32 = other.OptionalUint32;
+      }
+      if (other.HasOptionalUint64) {
+        OptionalUint64 = other.OptionalUint64;
+      }
+      if (other.HasOptionalSint32) {
+        OptionalSint32 = other.OptionalSint32;
+      }
+      if (other.HasOptionalSint64) {
+        OptionalSint64 = other.OptionalSint64;
+      }
+      if (other.HasOptionalFixed32) {
+        OptionalFixed32 = other.OptionalFixed32;
+      }
+      if (other.HasOptionalFixed64) {
+        OptionalFixed64 = other.OptionalFixed64;
+      }
+      if (other.HasOptionalSfixed32) {
+        OptionalSfixed32 = other.OptionalSfixed32;
+      }
+      if (other.HasOptionalSfixed64) {
+        OptionalSfixed64 = other.OptionalSfixed64;
+      }
+      if (other.HasOptionalFloat) {
+        OptionalFloat = other.OptionalFloat;
+      }
+      if (other.HasOptionalDouble) {
+        OptionalDouble = other.OptionalDouble;
+      }
+      if (other.HasOptionalBool) {
+        OptionalBool = other.OptionalBool;
+      }
+      if (other.HasOptionalString) {
+        OptionalString = other.OptionalString;
+      }
+      if (other.HasOptionalBytes) {
+        OptionalBytes = other.OptionalBytes;
+      }
+      if (other.HasOptionalCord) {
+        OptionalCord = other.OptionalCord;
+      }
+      if (other.optionalNestedMessage_ != null) {
+        if (optionalNestedMessage_ == null) {
+          OptionalNestedMessage = new global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage();
+        }
+        OptionalNestedMessage.MergeFrom(other.OptionalNestedMessage);
+      }
+      if (other.lazyNestedMessage_ != null) {
+        if (lazyNestedMessage_ == null) {
+          LazyNestedMessage = new global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage();
+        }
+        LazyNestedMessage.MergeFrom(other.LazyNestedMessage);
+      }
+      if (other.HasOptionalNestedEnum) {
+        OptionalNestedEnum = other.OptionalNestedEnum;
+      }
+      _unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields);
+    }
+
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public void MergeFrom(pb::CodedInputStream input) {
+      uint tag;
+      while ((tag = input.ReadTag()) != 0) {
+        switch(tag) {
+          default:
+            _unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, input);
+            break;
+          case 8: {
+            OptionalInt32 = input.ReadInt32();
+            break;
+          }
+          case 16: {
+            OptionalInt64 = input.ReadInt64();
+            break;
+          }
+          case 24: {
+            OptionalUint32 = input.ReadUInt32();
+            break;
+          }
+          case 32: {
+            OptionalUint64 = input.ReadUInt64();
+            break;
+          }
+          case 40: {
+            OptionalSint32 = input.ReadSInt32();
+            break;
+          }
+          case 48: {
+            OptionalSint64 = input.ReadSInt64();
+            break;
+          }
+          case 61: {
+            OptionalFixed32 = input.ReadFixed32();
+            break;
+          }
+          case 65: {
+            OptionalFixed64 = input.ReadFixed64();
+            break;
+          }
+          case 77: {
+            OptionalSfixed32 = input.ReadSFixed32();
+            break;
+          }
+          case 81: {
+            OptionalSfixed64 = input.ReadSFixed64();
+            break;
+          }
+          case 93: {
+            OptionalFloat = input.ReadFloat();
+            break;
+          }
+          case 97: {
+            OptionalDouble = input.ReadDouble();
+            break;
+          }
+          case 104: {
+            OptionalBool = input.ReadBool();
+            break;
+          }
+          case 114: {
+            OptionalString = input.ReadString();
+            break;
+          }
+          case 122: {
+            OptionalBytes = input.ReadBytes();
+            break;
+          }
+          case 130: {
+            OptionalCord = input.ReadString();
+            break;
+          }
+          case 146: {
+            if (optionalNestedMessage_ == null) {
+              OptionalNestedMessage = new global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage();
+            }
+            input.ReadMessage(OptionalNestedMessage);
+            break;
+          }
+          case 154: {
+            if (lazyNestedMessage_ == null) {
+              LazyNestedMessage = new global::ProtobufUnittest.TestProto3Optional.Types.NestedMessage();
+            }
+            input.ReadMessage(LazyNestedMessage);
+            break;
+          }
+          case 168: {
+            OptionalNestedEnum = (global::ProtobufUnittest.TestProto3Optional.Types.NestedEnum) input.ReadEnum();
+            break;
+          }
+        }
+      }
+    }
+
+    #region Nested types
+    /// <summary>Container for nested types declared in the TestProto3Optional message type.</summary>
+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+    public static partial class Types {
+      public enum NestedEnum {
+        [pbr::OriginalName("UNSPECIFIED")] Unspecified = 0,
+        [pbr::OriginalName("FOO")] Foo = 1,
+        [pbr::OriginalName("BAR")] Bar = 2,
+        [pbr::OriginalName("BAZ")] Baz = 3,
+        /// <summary>
+        /// Intentionally negative.
+        /// </summary>
+        [pbr::OriginalName("NEG")] Neg = -1,
+      }
+
+      public sealed partial class NestedMessage : pb::IMessage<NestedMessage> {
+        private static readonly pb::MessageParser<NestedMessage> _parser = new pb::MessageParser<NestedMessage>(() => new NestedMessage());
+        private pb::UnknownFieldSet _unknownFields;
+        private int _hasBits0;
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public static pb::MessageParser<NestedMessage> Parser { get { return _parser; } }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public static pbr::MessageDescriptor Descriptor {
+          get { return global::ProtobufUnittest.TestProto3Optional.Descriptor.NestedTypes[0]; }
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        pbr::MessageDescriptor pb::IMessage.Descriptor {
+          get { return Descriptor; }
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public NestedMessage() {
+          OnConstruction();
+        }
+
+        partial void OnConstruction();
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public NestedMessage(NestedMessage other) : this() {
+          _hasBits0 = other._hasBits0;
+          bb_ = other.bb_;
+          _unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields);
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public NestedMessage Clone() {
+          return new NestedMessage(this);
+        }
+
+        /// <summary>Field number for the "bb" field.</summary>
+        public const int BbFieldNumber = 1;
+        private int bb_;
+        /// <summary>
+        /// The field name "b" fails to compile in proto1 because it conflicts with
+        /// a local variable named "b" in one of the generated methods.  Doh.
+        /// This file needs to compile in proto1 to test backwards-compatibility.
+        /// </summary>
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public int Bb {
+          get { if ((_hasBits0 & 1) != 0) { return bb_; } else { return 0; } }
+          set {
+            _hasBits0 |= 1;
+            bb_ = value;
+          }
+        }
+        /// <summary>Gets whether the "bb" field is set</summary>
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public bool HasBb {
+          get { return (_hasBits0 & 1) != 0; }
+        }
+        /// <summary>Clears the value of the "bb" field</summary>
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public void ClearBb() {
+          _hasBits0 &= ~1;
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public override bool Equals(object other) {
+          return Equals(other as NestedMessage);
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public bool Equals(NestedMessage other) {
+          if (ReferenceEquals(other, null)) {
+            return false;
+          }
+          if (ReferenceEquals(other, this)) {
+            return true;
+          }
+          if (Bb != other.Bb) return false;
+          return Equals(_unknownFields, other._unknownFields);
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public override int GetHashCode() {
+          int hash = 1;
+          if (HasBb) hash ^= Bb.GetHashCode();
+          if (_unknownFields != null) {
+            hash ^= _unknownFields.GetHashCode();
+          }
+          return hash;
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public override string ToString() {
+          return pb::JsonFormatter.ToDiagnosticString(this);
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public void WriteTo(pb::CodedOutputStream output) {
+          if (HasBb) {
+            output.WriteRawTag(8);
+            output.WriteInt32(Bb);
+          }
+          if (_unknownFields != null) {
+            _unknownFields.WriteTo(output);
+          }
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public int CalculateSize() {
+          int size = 0;
+          if (HasBb) {
+            size += 1 + pb::CodedOutputStream.ComputeInt32Size(Bb);
+          }
+          if (_unknownFields != null) {
+            size += _unknownFields.CalculateSize();
+          }
+          return size;
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public void MergeFrom(NestedMessage other) {
+          if (other == null) {
+            return;
+          }
+          if (other.HasBb) {
+            Bb = other.Bb;
+          }
+          _unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields);
+        }
+
+        [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+        public void MergeFrom(pb::CodedInputStream input) {
+          uint tag;
+          while ((tag = input.ReadTag()) != 0) {
+            switch(tag) {
+              default:
+                _unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, input);
+                break;
+              case 8: {
+                Bb = input.ReadInt32();
+                break;
+              }
+            }
+          }
+        }
+
+      }
+
+    }
+    #endregion
+
+  }
+
+  #endregion
+
+}
+
+#endregion Designer generated code

二进制
csharp/src/Google.Protobuf.Test/testprotos.pb