Added recursion limits to AbstractReader.cs
diff --git a/src/ProtocolBuffers.Test/TestProtos/UnitTestXmlSerializerTestProtoFile.cs b/src/ProtocolBuffers.Test/TestProtos/UnitTestXmlSerializerTestProtoFile.cs
index 441ea65..c050766 100644
--- a/src/ProtocolBuffers.Test/TestProtos/UnitTestXmlSerializerTestProtoFile.cs
+++ b/src/ProtocolBuffers.Test/TestProtos/UnitTestXmlSerializerTestProtoFile.cs
@@ -35,6 +35,8 @@
     internal static pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlChild, global::Google.ProtocolBuffers.TestProtos.TestXmlChild.Builder> internal__static_protobuf_unittest_extra_TestXmlChild__FieldAccessorTable;

     internal static pbd::MessageDescriptor internal__static_protobuf_unittest_extra_TestXmlNoFields__Descriptor;

     internal static pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlNoFields, global::Google.ProtocolBuffers.TestProtos.TestXmlNoFields.Builder> internal__static_protobuf_unittest_extra_TestXmlNoFields__FieldAccessorTable;

+    internal static pbd::MessageDescriptor internal__static_protobuf_unittest_extra_TestXmlRescursive__Descriptor;

+    internal static pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive, global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.Builder> internal__static_protobuf_unittest_extra_TestXmlRescursive__FieldAccessorTable;

     internal static pbd::MessageDescriptor internal__static_protobuf_unittest_extra_TestXmlMessage__Descriptor;

     internal static pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlMessage, global::Google.ProtocolBuffers.TestProtos.TestXmlMessage.Builder> internal__static_protobuf_unittest_extra_TestXmlMessage__FieldAccessorTable;

     internal static pbd::MessageDescriptor internal__static_protobuf_unittest_extra_TestXmlMessage_Children__Descriptor;

@@ -54,25 +56,27 @@
           "YnVmX3VuaXR0ZXN0X2V4dHJhGiRnb29nbGUvcHJvdG9idWYvY3NoYXJwX29w" + 

           "dGlvbnMucHJvdG8iVQoMVGVzdFhtbENoaWxkEjUKB29wdGlvbnMYAyADKA4y" + 

           "JC5wcm90b2J1Zl91bml0dGVzdF9leHRyYS5FbnVtT3B0aW9ucxIOCgZiaW5h" + 

-          "cnkYBCABKAwiEQoPVGVzdFhtbE5vRmllbGRzIrcCCg5UZXN0WG1sTWVzc2Fn" + 

-          "ZRIOCgZudW1iZXIYBiABKAMSDwoHbnVtYmVycxgCIAMoBRIMCgR0ZXh0GAMg" + 

-          "ASgJEhIKCXRleHRsaW5lcxi8BSADKAkSDQoFdmFsaWQYBSABKAgSNAoFY2hp" + 

-          "bGQYASABKAsyJS5wcm90b2J1Zl91bml0dGVzdF9leHRyYS5UZXN0WG1sQ2hp" + 

-          "bGQSQwoIY2hpbGRyZW4YkQMgAygKMjAucHJvdG9idWZfdW5pdHRlc3RfZXh0" + 

-          "cmEuVGVzdFhtbE1lc3NhZ2UuQ2hpbGRyZW4aUQoIQ2hpbGRyZW4SNQoHb3B0" + 

-          "aW9ucxgDIAMoDjIkLnByb3RvYnVmX3VuaXR0ZXN0X2V4dHJhLkVudW1PcHRp" + 

-          "b25zEg4KBmJpbmFyeRgEIAEoDCoFCGQQyAEiIgoQVGVzdFhtbEV4dGVuc2lv" + 

-          "bhIOCgZudW1iZXIYASACKAUqKgoLRW51bU9wdGlvbnMSBwoDT05FEAASBwoD" + 

-          "VFdPEAESCQoFVEhSRUUQAjplCg5leHRlbnNpb25fZW51bRInLnByb3RvYnVm" + 

-          "X3VuaXR0ZXN0X2V4dHJhLlRlc3RYbWxNZXNzYWdlGGUgASgOMiQucHJvdG9i" + 

-          "dWZfdW5pdHRlc3RfZXh0cmEuRW51bU9wdGlvbnM6PwoOZXh0ZW5zaW9uX3Rl" + 

-          "eHQSJy5wcm90b2J1Zl91bml0dGVzdF9leHRyYS5UZXN0WG1sTWVzc2FnZRhm" + 

-          "IAEoCTpFChBleHRlbnNpb25fbnVtYmVyEicucHJvdG9idWZfdW5pdHRlc3Rf" + 

-          "ZXh0cmEuVGVzdFhtbE1lc3NhZ2UYZyADKAVCAhABOm4KEWV4dGVuc2lvbl9t" + 

-          "ZXNzYWdlEicucHJvdG9idWZfdW5pdHRlc3RfZXh0cmEuVGVzdFhtbE1lc3Nh" + 

-          "Z2UYxwEgASgLMikucHJvdG9idWZfdW5pdHRlc3RfZXh0cmEuVGVzdFhtbEV4" + 

-          "dGVuc2lvbkJMSAHCPkcKIUdvb2dsZS5Qcm90b2NvbEJ1ZmZlcnMuVGVzdFBy" + 

-          "b3RvcxIiVW5pdFRlc3RYbWxTZXJpYWxpemVyVGVzdFByb3RvRmlsZQ==");

+          "cnkYBCABKAwiEQoPVGVzdFhtbE5vRmllbGRzIk4KEVRlc3RYbWxSZXNjdXJz" + 

+          "aXZlEjkKBWNoaWxkGAEgASgLMioucHJvdG9idWZfdW5pdHRlc3RfZXh0cmEu" + 

+          "VGVzdFhtbFJlc2N1cnNpdmUitwIKDlRlc3RYbWxNZXNzYWdlEg4KBm51bWJl" + 

+          "chgGIAEoAxIPCgdudW1iZXJzGAIgAygFEgwKBHRleHQYAyABKAkSEgoJdGV4" + 

+          "dGxpbmVzGLwFIAMoCRINCgV2YWxpZBgFIAEoCBI0CgVjaGlsZBgBIAEoCzIl" + 

+          "LnByb3RvYnVmX3VuaXR0ZXN0X2V4dHJhLlRlc3RYbWxDaGlsZBJDCghjaGls" + 

+          "ZHJlbhiRAyADKAoyMC5wcm90b2J1Zl91bml0dGVzdF9leHRyYS5UZXN0WG1s" + 

+          "TWVzc2FnZS5DaGlsZHJlbhpRCghDaGlsZHJlbhI1CgdvcHRpb25zGAMgAygO" + 

+          "MiQucHJvdG9idWZfdW5pdHRlc3RfZXh0cmEuRW51bU9wdGlvbnMSDgoGYmlu" + 

+          "YXJ5GAQgASgMKgUIZBDIASIiChBUZXN0WG1sRXh0ZW5zaW9uEg4KBm51bWJl" + 

+          "chgBIAIoBSoqCgtFbnVtT3B0aW9ucxIHCgNPTkUQABIHCgNUV08QARIJCgVU" + 

+          "SFJFRRACOmUKDmV4dGVuc2lvbl9lbnVtEicucHJvdG9idWZfdW5pdHRlc3Rf" + 

+          "ZXh0cmEuVGVzdFhtbE1lc3NhZ2UYZSABKA4yJC5wcm90b2J1Zl91bml0dGVz" + 

+          "dF9leHRyYS5FbnVtT3B0aW9uczo/Cg5leHRlbnNpb25fdGV4dBInLnByb3Rv" + 

+          "YnVmX3VuaXR0ZXN0X2V4dHJhLlRlc3RYbWxNZXNzYWdlGGYgASgJOkUKEGV4" + 

+          "dGVuc2lvbl9udW1iZXISJy5wcm90b2J1Zl91bml0dGVzdF9leHRyYS5UZXN0" + 

+          "WG1sTWVzc2FnZRhnIAMoBUICEAE6bgoRZXh0ZW5zaW9uX21lc3NhZ2USJy5w" + 

+          "cm90b2J1Zl91bml0dGVzdF9leHRyYS5UZXN0WG1sTWVzc2FnZRjHASABKAsy" + 

+          "KS5wcm90b2J1Zl91bml0dGVzdF9leHRyYS5UZXN0WG1sRXh0ZW5zaW9uQkxI" + 

+          "AcI+RwohR29vZ2xlLlByb3RvY29sQnVmZmVycy5UZXN0UHJvdG9zEiJVbml0" + 

+          "VGVzdFhtbFNlcmlhbGl6ZXJUZXN0UHJvdG9GaWxl");

       pbd::FileDescriptor.InternalDescriptorAssigner assigner = delegate(pbd::FileDescriptor root) {

         descriptor = root;

         internal__static_protobuf_unittest_extra_TestXmlChild__Descriptor = Descriptor.MessageTypes[0];

@@ -83,7 +87,11 @@
         internal__static_protobuf_unittest_extra_TestXmlNoFields__FieldAccessorTable = 

             new pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlNoFields, global::Google.ProtocolBuffers.TestProtos.TestXmlNoFields.Builder>(internal__static_protobuf_unittest_extra_TestXmlNoFields__Descriptor,

                 new string[] { });

-        internal__static_protobuf_unittest_extra_TestXmlMessage__Descriptor = Descriptor.MessageTypes[2];

+        internal__static_protobuf_unittest_extra_TestXmlRescursive__Descriptor = Descriptor.MessageTypes[2];

+        internal__static_protobuf_unittest_extra_TestXmlRescursive__FieldAccessorTable = 

+            new pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive, global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.Builder>(internal__static_protobuf_unittest_extra_TestXmlRescursive__Descriptor,

+                new string[] { "Child", });

+        internal__static_protobuf_unittest_extra_TestXmlMessage__Descriptor = Descriptor.MessageTypes[3];

         internal__static_protobuf_unittest_extra_TestXmlMessage__FieldAccessorTable = 

             new pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlMessage, global::Google.ProtocolBuffers.TestProtos.TestXmlMessage.Builder>(internal__static_protobuf_unittest_extra_TestXmlMessage__Descriptor,

                 new string[] { "Number", "Numbers", "Text", "Textlines", "Valid", "Child", "Children", });

@@ -91,7 +99,7 @@
         internal__static_protobuf_unittest_extra_TestXmlMessage_Children__FieldAccessorTable = 

             new pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlMessage.Types.Children, global::Google.ProtocolBuffers.TestProtos.TestXmlMessage.Types.Children.Builder>(internal__static_protobuf_unittest_extra_TestXmlMessage_Children__Descriptor,

                 new string[] { "Options", "Binary", });

-        internal__static_protobuf_unittest_extra_TestXmlExtension__Descriptor = Descriptor.MessageTypes[3];

+        internal__static_protobuf_unittest_extra_TestXmlExtension__Descriptor = Descriptor.MessageTypes[4];

         internal__static_protobuf_unittest_extra_TestXmlExtension__FieldAccessorTable = 

             new pb::FieldAccess.FieldAccessorTable<global::Google.ProtocolBuffers.TestProtos.TestXmlExtension, global::Google.ProtocolBuffers.TestProtos.TestXmlExtension.Builder>(internal__static_protobuf_unittest_extra_TestXmlExtension__Descriptor,

                 new string[] { "Number", });

@@ -634,6 +642,268 @@
   [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]

   [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]

   [global::System.CodeDom.Compiler.GeneratedCodeAttribute("ProtoGen", "2.3.0.277")]

+  public sealed partial class TestXmlRescursive : pb::GeneratedMessage<TestXmlRescursive, TestXmlRescursive.Builder> {

+    private static readonly TestXmlRescursive defaultInstance = new Builder().BuildPartial();

+    private static readonly string[] _testXmlRescursiveFieldNames = new string[] { "child" };

+    private static readonly uint[] _testXmlRescursiveFieldTags = new uint[] { 10 };

+    public static TestXmlRescursive DefaultInstance {

+      get { return defaultInstance; }

+    }

+    

+    public override TestXmlRescursive DefaultInstanceForType {

+      get { return defaultInstance; }

+    }

+    

+    protected override TestXmlRescursive ThisMessage {

+      get { return this; }

+    }

+    

+    public static pbd::MessageDescriptor Descriptor {

+      get { return global::Google.ProtocolBuffers.TestProtos.UnitTestXmlSerializerTestProtoFile.internal__static_protobuf_unittest_extra_TestXmlRescursive__Descriptor; }

+    }

+    

+    protected override pb::FieldAccess.FieldAccessorTable<TestXmlRescursive, TestXmlRescursive.Builder> InternalFieldAccessors {

+      get { return global::Google.ProtocolBuffers.TestProtos.UnitTestXmlSerializerTestProtoFile.internal__static_protobuf_unittest_extra_TestXmlRescursive__FieldAccessorTable; }

+    }

+    

+    public const int ChildFieldNumber = 1;

+    private bool hasChild;

+    private global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive child_ = global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.DefaultInstance;

+    public bool HasChild {

+      get { return hasChild; }

+    }

+    public global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive Child {

+      get { return child_; }

+    }

+    

+    public override bool IsInitialized {

+      get {

+        return true;

+      }

+    }

+    

+    public override void WriteTo(pb::ICodedOutputStream output) {

+      int size = SerializedSize;

+      string[] field_names = _testXmlRescursiveFieldNames;

+      if (hasChild) {

+        output.WriteMessage(1, field_names[0], Child);

+      }

+      UnknownFields.WriteTo(output);

+    }

+    

+    private int memoizedSerializedSize = -1;

+    public override int SerializedSize {

+      get {

+        int size = memoizedSerializedSize;

+        if (size != -1) return size;

+        

+        size = 0;

+        if (hasChild) {

+          size += pb::CodedOutputStream.ComputeMessageSize(1, Child);

+        }

+        size += UnknownFields.SerializedSize;

+        memoizedSerializedSize = size;

+        return size;

+      }

+    }

+    

+    public static TestXmlRescursive ParseFrom(pb::ByteString data) {

+      return ((Builder) CreateBuilder().MergeFrom(data)).BuildParsed();

+    }

+    public static TestXmlRescursive ParseFrom(pb::ByteString data, pb::ExtensionRegistry extensionRegistry) {

+      return ((Builder) CreateBuilder().MergeFrom(data, extensionRegistry)).BuildParsed();

+    }

+    public static TestXmlRescursive ParseFrom(byte[] data) {

+      return ((Builder) CreateBuilder().MergeFrom(data)).BuildParsed();

+    }

+    public static TestXmlRescursive ParseFrom(byte[] data, pb::ExtensionRegistry extensionRegistry) {

+      return ((Builder) CreateBuilder().MergeFrom(data, extensionRegistry)).BuildParsed();

+    }

+    public static TestXmlRescursive ParseFrom(global::System.IO.Stream input) {

+      return ((Builder) CreateBuilder().MergeFrom(input)).BuildParsed();

+    }

+    public static TestXmlRescursive ParseFrom(global::System.IO.Stream input, pb::ExtensionRegistry extensionRegistry) {

+      return ((Builder) CreateBuilder().MergeFrom(input, extensionRegistry)).BuildParsed();

+    }

+    public static TestXmlRescursive ParseDelimitedFrom(global::System.IO.Stream input) {

+      return CreateBuilder().MergeDelimitedFrom(input).BuildParsed();

+    }

+    public static TestXmlRescursive ParseDelimitedFrom(global::System.IO.Stream input, pb::ExtensionRegistry extensionRegistry) {

+      return CreateBuilder().MergeDelimitedFrom(input, extensionRegistry).BuildParsed();

+    }

+    public static TestXmlRescursive ParseFrom(pb::ICodedInputStream input) {

+      return ((Builder) CreateBuilder().MergeFrom(input)).BuildParsed();

+    }

+    public static TestXmlRescursive ParseFrom(pb::ICodedInputStream input, pb::ExtensionRegistry extensionRegistry) {

+      return ((Builder) CreateBuilder().MergeFrom(input, extensionRegistry)).BuildParsed();

+    }

+    public static Builder CreateBuilder() { return new Builder(); }

+    public override Builder ToBuilder() { return CreateBuilder(this); }

+    public override Builder CreateBuilderForType() { return new Builder(); }

+    public static Builder CreateBuilder(TestXmlRescursive prototype) {

+      return (Builder) new Builder().MergeFrom(prototype);

+    }

+    

+    [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]

+    [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]

+    [global::System.CodeDom.Compiler.GeneratedCodeAttribute("ProtoGen", "2.3.0.277")]

+    public sealed partial class Builder : pb::GeneratedBuilder<TestXmlRescursive, Builder> {

+      protected override Builder ThisBuilder {

+        get { return this; }

+      }

+      public Builder() {}

+      

+      TestXmlRescursive result = new TestXmlRescursive();

+      

+      protected override TestXmlRescursive MessageBeingBuilt {

+        get { return result; }

+      }

+      

+      public override Builder Clear() {

+        result = new TestXmlRescursive();

+        return this;

+      }

+      

+      public override Builder Clone() {

+        return new Builder().MergeFrom(result);

+      }

+      

+      public override pbd::MessageDescriptor DescriptorForType {

+        get { return global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.Descriptor; }

+      }

+      

+      public override TestXmlRescursive DefaultInstanceForType {

+        get { return global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.DefaultInstance; }

+      }

+      

+      public override TestXmlRescursive BuildPartial() {

+        if (result == null) {

+          throw new global::System.InvalidOperationException("build() has already been called on this Builder");

+        }

+        TestXmlRescursive returnMe = result;

+        result = null;

+        return returnMe;

+      }

+      

+      public override Builder MergeFrom(pb::IMessage other) {

+        if (other is TestXmlRescursive) {

+          return MergeFrom((TestXmlRescursive) other);

+        } else {

+          base.MergeFrom(other);

+          return this;

+        }

+      }

+      

+      public override Builder MergeFrom(TestXmlRescursive other) {

+        if (other == global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.DefaultInstance) return this;

+        if (other.HasChild) {

+          MergeChild(other.Child);

+        }

+        this.MergeUnknownFields(other.UnknownFields);

+        return this;

+      }

+      

+      public override Builder MergeFrom(pb::ICodedInputStream input) {

+        return MergeFrom(input, pb::ExtensionRegistry.Empty);

+      }

+      

+      public override Builder MergeFrom(pb::ICodedInputStream input, pb::ExtensionRegistry extensionRegistry) {

+        pb::UnknownFieldSet.Builder unknownFields = null;

+        uint tag;

+        string field_name;

+        while (input.ReadTag(out tag, out field_name)) {

+          if(tag == 0 && field_name != null) {

+            int field_ordinal = global::System.Array.BinarySearch(_testXmlRescursiveFieldNames, field_name, global::System.StringComparer.Ordinal);

+            if(field_ordinal >= 0)

+              tag = _testXmlRescursiveFieldTags[field_ordinal];

+            else {

+              if (unknownFields == null) {

+                unknownFields = pb::UnknownFieldSet.CreateBuilder(this.UnknownFields);

+              }

+              ParseUnknownField(input, unknownFields, extensionRegistry, tag, field_name);

+              continue;

+            }

+          }

+          switch (tag) {

+            case 0: {

+              throw pb::InvalidProtocolBufferException.InvalidTag();

+            }

+            default: {

+              if (pb::WireFormat.IsEndGroupTag(tag)) {

+                if (unknownFields != null) {

+                  this.UnknownFields = unknownFields.Build();

+                }

+                return this;

+              }

+              if (unknownFields == null) {

+                unknownFields = pb::UnknownFieldSet.CreateBuilder(this.UnknownFields);

+              }

+              ParseUnknownField(input, unknownFields, extensionRegistry, tag, field_name);

+              break;

+            }

+            case 10: {

+              global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.Builder subBuilder = global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.CreateBuilder();

+              if (result.hasChild) {

+                subBuilder.MergeFrom(Child);

+              }

+              input.ReadMessage(subBuilder, extensionRegistry);

+              Child = subBuilder.BuildPartial();

+              break;

+            }

+          }

+        }

+        

+        if (unknownFields != null) {

+          this.UnknownFields = unknownFields.Build();

+        }

+        return this;

+      }

+      

+      

+      public bool HasChild {

+       get { return result.hasChild; }

+      }

+      public global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive Child {

+        get { return result.Child; }

+        set { SetChild(value); }

+      }

+      public Builder SetChild(global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive value) {

+        pb::ThrowHelper.ThrowIfNull(value, "value");

+        result.hasChild = true;

+        result.child_ = value;

+        return this;

+      }

+      public Builder SetChild(global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.Builder builderForValue) {

+        pb::ThrowHelper.ThrowIfNull(builderForValue, "builderForValue");

+        result.hasChild = true;

+        result.child_ = builderForValue.Build();

+        return this;

+      }

+      public Builder MergeChild(global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive value) {

+        pb::ThrowHelper.ThrowIfNull(value, "value");

+        if (result.hasChild &&

+            result.child_ != global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.DefaultInstance) {

+            result.child_ = global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.CreateBuilder(result.child_).MergeFrom(value).BuildPartial();

+        } else {

+          result.child_ = value;

+        }

+        result.hasChild = true;

+        return this;

+      }

+      public Builder ClearChild() {

+        result.hasChild = false;

+        result.child_ = global::Google.ProtocolBuffers.TestProtos.TestXmlRescursive.DefaultInstance;

+        return this;

+      }

+    }

+    static TestXmlRescursive() {

+      object.ReferenceEquals(global::Google.ProtocolBuffers.TestProtos.UnitTestXmlSerializerTestProtoFile.Descriptor, null);

+    }

+  }

+  

+  [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]

+  [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]

+  [global::System.CodeDom.Compiler.GeneratedCodeAttribute("ProtoGen", "2.3.0.277")]

   public sealed partial class TestXmlMessage : pb::ExtendableMessage<TestXmlMessage, TestXmlMessage.Builder> {

     private static readonly TestXmlMessage defaultInstance = new Builder().BuildPartial();

     private static readonly string[] _testXmlMessageFieldNames = new string[] { "child", "children", "number", "numbers", "text", "textlines", "valid" };