Пример #1
0
            /// <summary>
            /// Like <see cref="MergeFrom(ICodedInputStream, ExtensionRegistry, IBuilder)" />
            /// but parses a single field.
            /// </summary>
            /// <param name="input">The input to read the field from</param>
            /// <param name="extensionRegistry">Registry to use when an extension field is encountered</param>
            /// <param name="builder">Builder to merge field into, if it's a known field</param>
            /// <param name="tag">The tag, which should already have been read from the input</param>
            /// <returns>true unless the tag is an end-group tag</returns>
            internal bool MergeFieldFrom(ICodedInputStream input,
                                         ExtensionRegistry extensionRegistry, IBuilder builder, uint tag,
                                         string fieldName)
            {
                if (tag == 0 && fieldName != null)
                {
                    FieldDescriptor fieldByName = builder.DescriptorForType.FindFieldByName(fieldName);
                    if (fieldByName != null)
                    {
                        tag = WireFormat.MakeTag(fieldByName);
                    }
                    else
                    {
                        ExtensionInfo extension = extensionRegistry.FindByName(builder.DescriptorForType, fieldName);
                        if (extension != null)
                        {
                            tag = WireFormat.MakeTag(extension.Descriptor);
                        }
                    }
                }

                MessageDescriptor type = builder.DescriptorForType;

                if (type.Options.MessageSetWireFormat && tag == WireFormat.MessageSetTag.ItemStart)
                {
                    MergeMessageSetExtensionFromCodedStream(input, extensionRegistry, builder);
                    return(true);
                }

                WireFormat.WireType wireType = WireFormat.GetTagWireType(tag);
                int fieldNumber = WireFormat.GetTagFieldNumber(tag);

                FieldDescriptor field;
                IMessageLite    defaultFieldInstance = null;

                if (type.IsExtensionNumber(fieldNumber))
                {
                    ExtensionInfo extension = extensionRegistry[type, fieldNumber];
                    if (extension == null)
                    {
                        field = null;
                    }
                    else
                    {
                        field = extension.Descriptor;
                        defaultFieldInstance = extension.DefaultInstance;
                    }
                }
                else
                {
                    field = type.FindFieldByNumber(fieldNumber);
                }

                // Unknown field or wrong wire type. Skip.
                if (field == null)
                {
                    return(MergeFieldFrom(tag, input));
                }
                if (wireType != WireFormat.GetWireType(field))
                {
                    WireFormat.WireType expectedType = WireFormat.GetWireType(field.FieldType);
                    if (wireType == expectedType)
                    {
                        //Allowed as of 2.3, this is unpacked data for a packed array
                    }
                    else if (field.IsRepeated && wireType == WireFormat.WireType.LengthDelimited &&
                             (expectedType == WireFormat.WireType.Varint || expectedType == WireFormat.WireType.Fixed32 ||
                              expectedType == WireFormat.WireType.Fixed64))
                    {
                        //Allowed as of 2.3, this is packed data for an unpacked array
                    }
                    else
                    {
                        return(MergeFieldFrom(tag, input));
                    }
                }

                switch (field.FieldType)
                {
                case FieldType.Group:
                case FieldType.Message:
                {
                    IBuilderLite subBuilder = (defaultFieldInstance != null)
                                                          ? defaultFieldInstance.WeakCreateBuilderForType()
                                                          : builder.CreateBuilderForField(field);
                    if (!field.IsRepeated)
                    {
                        subBuilder.WeakMergeFrom((IMessageLite)builder[field]);
                        if (field.FieldType == FieldType.Group)
                        {
                            input.ReadGroup(field.FieldNumber, subBuilder, extensionRegistry);
                        }
                        else
                        {
                            input.ReadMessage(subBuilder, extensionRegistry);
                        }
                        builder[field] = subBuilder.WeakBuild();
                    }
                    else
                    {
                        List <IMessageLite> list = new List <IMessageLite>();
                        if (field.FieldType == FieldType.Group)
                        {
                            input.ReadGroupArray(tag, fieldName, list, subBuilder.WeakDefaultInstanceForType,
                                                 extensionRegistry);
                        }
                        else
                        {
                            input.ReadMessageArray(tag, fieldName, list, subBuilder.WeakDefaultInstanceForType,
                                                   extensionRegistry);
                        }

                        foreach (IMessageLite m in list)
                        {
                            builder.WeakAddRepeatedField(field, m);
                        }
                        return(true);
                    }
                    break;
                }

                case FieldType.Enum:
                {
                    if (!field.IsRepeated)
                    {
                        object    unknown;
                        IEnumLite value = null;
                        if (input.ReadEnum(ref value, out unknown, field.EnumType))
                        {
                            builder[field] = value;
                        }
                        else if (unknown is int)
                        {
                            MergeVarintField(fieldNumber, (ulong)(int)unknown);
                        }
                    }
                    else
                    {
                        ICollection <object> unknown;
                        List <IEnumLite>     list = new List <IEnumLite>();
                        input.ReadEnumArray(tag, fieldName, list, out unknown, field.EnumType);

                        foreach (IEnumLite en in list)
                        {
                            builder.WeakAddRepeatedField(field, en);
                        }

                        if (unknown != null)
                        {
                            foreach (object oval in unknown)
                            {
                                if (oval is int)
                                {
                                    MergeVarintField(fieldNumber, (ulong)(int)oval);
                                }
                            }
                        }
                    }
                    break;
                }

                default:
                {
                    if (!field.IsRepeated)
                    {
                        object value = null;
                        if (input.ReadPrimitiveField(field.FieldType, ref value))
                        {
                            builder[field] = value;
                        }
                    }
                    else
                    {
                        List <object> list = new List <object>();
                        input.ReadPrimitiveArray(field.FieldType, tag, fieldName, list);
                        foreach (object oval in list)
                        {
                            builder.WeakAddRepeatedField(field, oval);
                        }
                    }
                    break;
                }
                }
                return(true);
            }
        protected override bool ParseUnknownField(ICodedInputStream input, ExtensionRegistry extensionRegistry, uint tag, string fieldName)
        {
            TMessage messageBeingBuilt = this.MessageBeingBuilt;
            FieldSet extensions        = messageBeingBuilt.Extensions;

            WireFormat.WireType tagWireType = WireFormat.GetTagWireType(tag);
            int tagFieldNumber = WireFormat.GetTagFieldNumber(tag);
            IGeneratedExtensionLite generatedExtensionLite = extensionRegistry[this.DefaultInstanceForType, tagFieldNumber];

            if (generatedExtensionLite == null)
            {
                return(input.SkipField());
            }
            IFieldDescriptorLite descriptor = generatedExtensionLite.Descriptor;

            if (descriptor == null)
            {
                return(input.SkipField());
            }
            WireFormat.WireType wireType = descriptor.IsPacked ? WireFormat.WireType.LengthDelimited : WireFormat.GetWireType(descriptor.FieldType);
            if (tagWireType != wireType)
            {
                wireType = WireFormat.GetWireType(descriptor.FieldType);
                if (tagWireType != wireType && (!descriptor.IsRepeated || tagWireType != WireFormat.WireType.LengthDelimited || (wireType != WireFormat.WireType.Varint && wireType != WireFormat.WireType.Fixed32 && wireType != WireFormat.WireType.Fixed64)))
                {
                    return(input.SkipField());
                }
            }
            if (!descriptor.IsRepeated && tagWireType != WireFormat.GetWireType(descriptor.FieldType))
            {
                return(input.SkipField());
            }
            FieldType fieldType = descriptor.FieldType;

            switch (fieldType)
            {
            case FieldType.Group:
            case FieldType.Message:
            {
                if (descriptor.IsRepeated)
                {
                    List <IMessageLite> list = new List <IMessageLite>();
                    if (descriptor.FieldType == FieldType.Group)
                    {
                        input.ReadGroupArray <IMessageLite>(tag, fieldName, list, generatedExtensionLite.MessageDefaultInstance, extensionRegistry);
                    }
                    else
                    {
                        input.ReadMessageArray <IMessageLite>(tag, fieldName, list, generatedExtensionLite.MessageDefaultInstance, extensionRegistry);
                    }
                    using (List <IMessageLite> .Enumerator enumerator = list.GetEnumerator())
                    {
                        while (enumerator.MoveNext())
                        {
                            IMessageLite current = enumerator.Current;
                            extensions.AddRepeatedField(descriptor, current);
                        }
                    }
                    return(true);
                }
                IMessageLite messageLite = extensions[generatedExtensionLite.Descriptor] as IMessageLite;
                IBuilderLite builderLite = (messageLite ?? generatedExtensionLite.MessageDefaultInstance).WeakToBuilder();
                if (descriptor.FieldType == FieldType.Group)
                {
                    input.ReadGroup(descriptor.FieldNumber, builderLite, extensionRegistry);
                }
                else
                {
                    input.ReadMessage(builderLite, extensionRegistry);
                }
                extensions[descriptor] = builderLite.WeakBuild();
                break;
            }

            default:
                if (fieldType == FieldType.Enum)
                {
                    if (!descriptor.IsRepeated)
                    {
                        IEnumLite value = null;
                        object    obj;
                        if (input.ReadEnum(ref value, out obj, descriptor.EnumType))
                        {
                            extensions[descriptor] = value;
                            break;
                        }
                        break;
                    }
                    else
                    {
                        List <IEnumLite>     list2 = new List <IEnumLite>();
                        ICollection <object> collection;
                        input.ReadEnumArray(tag, fieldName, list2, out collection, descriptor.EnumType);
                        using (List <IEnumLite> .Enumerator enumerator2 = list2.GetEnumerator())
                        {
                            while (enumerator2.MoveNext())
                            {
                                IEnumLite current2 = enumerator2.Current;
                                extensions.AddRepeatedField(descriptor, current2);
                            }
                            break;
                        }
                    }
                }
                if (!descriptor.IsRepeated)
                {
                    object value2 = null;
                    if (input.ReadPrimitiveField(descriptor.FieldType, ref value2))
                    {
                        extensions[descriptor] = value2;
                    }
                }
                else
                {
                    List <object> list3 = new List <object>();
                    input.ReadPrimitiveArray(descriptor.FieldType, tag, fieldName, list3);
                    using (List <object> .Enumerator enumerator3 = list3.GetEnumerator())
                    {
                        while (enumerator3.MoveNext())
                        {
                            object current3 = enumerator3.Current;
                            extensions.AddRepeatedField(descriptor, current3);
                        }
                    }
                }
                break;
            }
            return(true);
        }
        protected override bool ParseUnknownField(ICodedInputStream input,
                                                  ExtensionRegistry extensionRegistry, uint tag, string fieldName)
        {
            FieldSet extensions = MessageBeingBuilt.Extensions;

            WireFormat.WireType wireType = WireFormat.GetTagWireType(tag);
            int fieldNumber = WireFormat.GetTagFieldNumber(tag);
            IGeneratedExtensionLite extension = extensionRegistry[DefaultInstanceForType, fieldNumber];

            if (extension == null) //unknown field
            {
                return(input.SkipField());
            }

            IFieldDescriptorLite field = extension.Descriptor;


            // Unknown field or wrong wire type. Skip.
            if (field == null)
            {
                return(input.SkipField());
            }
            WireFormat.WireType expectedType = field.IsPacked
                                                   ? WireFormat.WireType.LengthDelimited
                                                   : WireFormat.GetWireType(field.FieldType);
            if (wireType != expectedType)
            {
                expectedType = WireFormat.GetWireType(field.FieldType);
                if (wireType == expectedType)
                {
                    //Allowed as of 2.3, this is unpacked data for a packed array
                }
                else if (field.IsRepeated && wireType == WireFormat.WireType.LengthDelimited &&
                         (expectedType == WireFormat.WireType.Varint || expectedType == WireFormat.WireType.Fixed32 ||
                          expectedType == WireFormat.WireType.Fixed64))
                {
                    //Allowed as of 2.3, this is packed data for an unpacked array
                }
                else
                {
                    return(input.SkipField());
                }
            }
            if (!field.IsRepeated && wireType != WireFormat.GetWireType(field.FieldType)) //invalid wire type
            {
                return(input.SkipField());
            }

            switch (field.FieldType)
            {
            case FieldType.Group:
            case FieldType.Message:
            {
                if (!field.IsRepeated)
                {
                    IMessageLite message    = extensions[extension.Descriptor] as IMessageLite;
                    IBuilderLite subBuilder = (message ?? extension.MessageDefaultInstance).WeakToBuilder();

                    if (field.FieldType == FieldType.Group)
                    {
                        input.ReadGroup(field.FieldNumber, subBuilder, extensionRegistry);
                    }
                    else
                    {
                        input.ReadMessage(subBuilder, extensionRegistry);
                    }

                    extensions[field] = subBuilder.WeakBuild();
                }
                else
                {
                    List <IMessageLite> list = new List <IMessageLite>();
                    if (field.FieldType == FieldType.Group)
                    {
                        input.ReadGroupArray(tag, fieldName, list, extension.MessageDefaultInstance,
                                             extensionRegistry);
                    }
                    else
                    {
                        input.ReadMessageArray(tag, fieldName, list, extension.MessageDefaultInstance,
                                               extensionRegistry);
                    }

                    foreach (IMessageLite m in list)
                    {
                        extensions.AddRepeatedField(field, m);
                    }
                    return(true);
                }
                break;
            }

            case FieldType.Enum:
            {
                if (!field.IsRepeated)
                {
                    object    unknown;
                    IEnumLite value = null;
                    if (input.ReadEnum(ref value, out unknown, field.EnumType))
                    {
                        extensions[field] = value;
                    }
                }
                else
                {
                    ICollection <object> unknown;
                    List <IEnumLite>     list = new List <IEnumLite>();
                    input.ReadEnumArray(tag, fieldName, list, out unknown, field.EnumType);

                    foreach (IEnumLite en in list)
                    {
                        extensions.AddRepeatedField(field, en);
                    }
                }
                break;
            }

            default:
            {
                if (!field.IsRepeated)
                {
                    object value = null;
                    if (input.ReadPrimitiveField(field.FieldType, ref value))
                    {
                        extensions[field] = value;
                    }
                }
                else
                {
                    List <object> list = new List <object>();
                    input.ReadPrimitiveArray(field.FieldType, tag, fieldName, list);
                    foreach (object oval in list)
                    {
                        extensions.AddRepeatedField(field, oval);
                    }
                }
                break;
            }
            }

            return(true);
        }
Пример #4
0
            /// <summary>
            /// Like <see cref="MergeFrom(ICodedInputStream, ExtensionRegistry, IBuilder)" />
            /// but parses a single field.
            /// </summary>
            /// <param name="input">The input to read the field from</param>
            /// <param name="extensionRegistry">Registry to use when an extension field is encountered</param>
            /// <param name="builder">Builder to merge field into, if it's a known field</param>
            /// <param name="tag">The tag, which should already have been read from the input</param>
            /// <returns>true unless the tag is an end-group tag</returns>
            internal bool MergeFieldFrom(ICodedInputStream input,
                                         ExtensionRegistry extensionRegistry, IBuilder builder, uint tag,
                                         string fieldName)
            {
                if (tag == 0 && fieldName != null)
                {
                    FieldDescriptor fieldByName = builder.DescriptorForType.FindFieldByName(fieldName);
                    if (fieldByName != null)
                    {
                        tag = WireFormat.MakeTag(fieldByName);
                    }
                    else
                    {
                        ExtensionInfo extension = extensionRegistry.FindByName(builder.DescriptorForType, fieldName);
                        if (extension != null)
                        {
                            tag = WireFormat.MakeTag(extension.Descriptor);
                        }
                    }
                }

                MessageDescriptor type = builder.DescriptorForType;
                if (type.Options.MessageSetWireFormat && tag == WireFormat.MessageSetTag.ItemStart)
                {
                    MergeMessageSetExtensionFromCodedStream(input, extensionRegistry, builder);
                    return true;
                }

                WireFormat.WireType wireType = WireFormat.GetTagWireType(tag);
                int fieldNumber = WireFormat.GetTagFieldNumber(tag);

                FieldDescriptor field;
                IMessageLite defaultFieldInstance = null;

                if (type.IsExtensionNumber(fieldNumber))
                {
                    ExtensionInfo extension = extensionRegistry[type, fieldNumber];
                    if (extension == null)
                    {
                        field = null;
                    }
                    else
                    {
                        field = extension.Descriptor;
                        defaultFieldInstance = extension.DefaultInstance;
                    }
                }
                else
                {
                    field = type.FindFieldByNumber(fieldNumber);
                }

                // Unknown field or wrong wire type. Skip.
                if (field == null)
                {
                    return MergeFieldFrom(tag, input);
                }
                if (wireType != WireFormat.GetWireType(field))
                {
                    WireFormat.WireType expectedType = WireFormat.GetWireType(field.FieldType);
                    if (wireType == expectedType)
                    {
                        //Allowed as of 2.3, this is unpacked data for a packed array
                    }
                    else if (field.IsRepeated && wireType == WireFormat.WireType.LengthDelimited &&
                             (expectedType == WireFormat.WireType.Varint || expectedType == WireFormat.WireType.Fixed32 ||
                              expectedType == WireFormat.WireType.Fixed64))
                    {
                        //Allowed as of 2.3, this is packed data for an unpacked array
                    }
                    else
                    {
                        return MergeFieldFrom(tag, input);
                    }
                }

                switch (field.FieldType)
                {
                    case FieldType.Group:
                    case FieldType.Message:
                        {
                            IBuilderLite subBuilder = (defaultFieldInstance != null)
                                                          ? defaultFieldInstance.WeakCreateBuilderForType()
                                                          : builder.CreateBuilderForField(field);
                            if (!field.IsRepeated)
                            {
                                subBuilder.WeakMergeFrom((IMessageLite) builder[field]);
                                if (field.FieldType == FieldType.Group)
                                {
                                    input.ReadGroup(field.FieldNumber, subBuilder, extensionRegistry);
                                }
                                else
                                {
                                    input.ReadMessage(subBuilder, extensionRegistry);
                                }
                                builder[field] = subBuilder.WeakBuild();
                            }
                            else
                            {
                                List<IMessageLite> list = new List<IMessageLite>();
                                if (field.FieldType == FieldType.Group)
                                {
                                    input.ReadGroupArray(tag, fieldName, list, subBuilder.WeakDefaultInstanceForType,
                                                         extensionRegistry);
                                }
                                else
                                {
                                    input.ReadMessageArray(tag, fieldName, list, subBuilder.WeakDefaultInstanceForType,
                                                           extensionRegistry);
                                }

                                foreach (IMessageLite m in list)
                                {
                                    builder.WeakAddRepeatedField(field, m);
                                }
                                return true;
                            }
                            break;
                        }
                    case FieldType.Enum:
                        {
                            if (!field.IsRepeated)
                            {
                                object unknown;
                                IEnumLite value = null;
                                if (input.ReadEnum(ref value, out unknown, field.EnumType))
                                {
                                    builder[field] = value;
                                }
                                else if (unknown is int)
                                {
                                    MergeVarintField(fieldNumber, (ulong) (int) unknown);
                                }
                            }
                            else
                            {
                                ICollection<object> unknown;
                                List<IEnumLite> list = new List<IEnumLite>();
                                input.ReadEnumArray(tag, fieldName, list, out unknown, field.EnumType);

                                foreach (IEnumLite en in list)
                                {
                                    builder.WeakAddRepeatedField(field, en);
                                }

                                if (unknown != null)
                                {
                                    foreach (object oval in unknown)
                                    {
                                        if (oval is int)
                                        {
                                            MergeVarintField(fieldNumber, (ulong) (int) oval);
                                        }
                                    }
                                }
                            }
                            break;
                        }
                    default:
                        {
                            if (!field.IsRepeated)
                            {
                                object value = null;
                                if (input.ReadPrimitiveField(field.FieldType, ref value))
                                {
                                    builder[field] = value;
                                }
                            }
                            else
                            {
                                List<object> list = new List<object>();
                                input.ReadPrimitiveArray(field.FieldType, tag, fieldName, list);
                                foreach (object oval in list)
                                {
                                    builder.WeakAddRepeatedField(field, oval);
                                }
                            }
                            break;
                        }
                }
                return true;
            }