private ulong ReadRawVarint64()
        {
            int   shift  = 0;
            ulong result = 0;

            while (shift < 64)
            {
                byte b = ReadByteFromStream();
                result |= (ulong)(b & 0x7F) << shift;
                if ((b & 0x80) == 0)
                {
                    return(result);
                }
                shift += 7;
            }

            throw InvalidProtocolBufferException.MalformedVarint();
        }
        private static FieldSetting <T> CreateArray <InternalT>(int fieldNum, WireType wireType, Func <T, IEnumerable <InternalT> > valueGetter, Action <T, InternalT> oneValueSetter,
                                                                Action <T, BasicDeserializer> readActionWithoutTag, Func <T, bool> hasValueFunc,
                                                                Action <BasicSerializer, InternalT> oneValueWriter, Func <BasicDeserializer, InternalT> oneValueReader,
                                                                bool canReadPacked)
        {
            CheckFieldNum(fieldNum);
            return(new FieldSetting <T>(fieldNum, WireFormat.MakeTag(fieldNum, wireType),

                                        (value, serializer, rt) =>
            {
                foreach (var item in valueGetter(value))
                {
                    serializer.WriteRawTag(rt);
                    oneValueWriter(serializer, item);
                }
                ;
            },

                                        readActionWithoutTag,
                                        hasValueFunc,
                                        canReadPacked ? WireFormat.MakeTag(fieldNum, WireType.LengthDelimited) : 0,
                                        canReadPacked ? (value, serializer) =>
            {
                var len = serializer.ReadLength();
                var positionLimit = serializer.stream.Position + len;

                while (serializer.stream.Position < positionLimit)
                {
                    oneValueSetter(value, oneValueReader(serializer));
                }

                if (serializer.stream.Position > positionLimit)
                {
                    throw InvalidProtocolBufferException.AllowableFieldLengthWasExceeded();
                }
            } : (Action <T, BasicDeserializer>)null));
        }
        private uint ReadRawVarint32(bool zeroIfEndOfStream = false)
        {
            int tmp;

            if (zeroIfEndOfStream)
            {
                tmp = stream.ReadByte();

                if (tmp == -1)
                {
                    return(0);
                }
            }
            else
            {
                tmp = ReadByteFromStream();
            }

            if (tmp < 128)
            {
                return((uint)tmp);
            }

            int result = tmp & 0x7f;

            if ((tmp = ReadByteFromStream()) < 128)
            {
                result |= tmp << 7;
            }
            else
            {
                result |= (tmp & 0x7f) << 7;
                if ((tmp = ReadByteFromStream()) < 128)
                {
                    result |= tmp << 14;
                }
                else
                {
                    result |= (tmp & 0x7f) << 14;
                    if ((tmp = ReadByteFromStream()) < 128)
                    {
                        result |= tmp << 21;
                    }
                    else
                    {
                        result |= (tmp & 0x7f) << 21;
                        result |= (tmp = ReadByteFromStream()) << 28;
                        if (tmp >= 128)
                        {
                            // Discard upper 32 bits
                            for (int i = 0; i < 5; i++)
                            {
                                if (ReadByteFromStream() < 128)
                                {
                                    return((uint)result);
                                }
                            }

                            throw InvalidProtocolBufferException.MalformedVarint();
                        }
                    }
                }
            }
            return((uint)result);
        }
        public void SkipField(WireType wireType)
        {
            switch (wireType)
            {
            case WireType.Varint:
                int tmp;
                int cnt = 0;
                while ((tmp = ReadByteFromStream()) >= 128)
                {
                    cnt++;

                    if (cnt == 10)
                    {
                        throw InvalidProtocolBufferException.MalformedVarint();
                    }
                }

                break;

            case WireType.Fixed64:
                ReadFromStream(buffForSeek, 0, 8);

                break;

            case WireType.LengthDelimited:
                var len = ReadLength();
                if (len <= buffForSeek.Length)
                {
                    ReadFromStream(buffForSeek, 0, len);
                }
                else
                {
                    ReadFromStream(new byte[len], 0, len);
                }

                break;

            case WireType.StartGroup:
                recursionDepth++;
                uint     tag;
                WireType wt;
                do
                {
                    tag = ReadTag();
                    if (tag == 0)
                    {
                        throw InvalidProtocolBufferException.TruncatedMessage();
                    }

                    wt = WireFormat.GetTagWireType(tag);
                    SkipField(wt);
                } while (wt != WireType.EndGroup);
                recursionDepth--;

                break;

            case WireType.EndGroup:
                break;

            case WireType.Fixed32:
                ReadFromStream(buffForSeek, 0, 4);
                break;

            default:
                throw InvalidProtocolBufferException.UnknownWireType();
                break;
            }
        }
Example #5
0
        private void Initialize()
        {
            // create write action
            if (useHasValue)
            {
                if (getterFieldNumsForSerialization != null)
                {
                    writeAction = (value, serializer) =>
                    {
                        var settings = getterFieldNumsForSerialization(value).Select(x => fieldSettings[x]).OrderBy(x => x.FieldNum).ToArray();
                        foreach (var s in settings)
                        {
                            if (s.HasValueFunc == null || s.HasValueFunc(value))
                            {
                                s.WriteAction(value, serializer, s.RawTag);
                            }
                        }
                    };
                }
                else
                {
                    writeAction = (value, serializer) =>
                    {
                        foreach (var s in fieldSettings.Values)
                        {
                            if (s.HasValueFunc == null || s.HasValueFunc(value))
                            {
                                s.WriteAction(value, serializer, s.RawTag);
                            }
                        }
                    };
                }
            }
            else
            {
                if (getterFieldNumsForSerialization != null)
                {
                    writeAction = (value, serializer) =>
                    {
                        var settings = getterFieldNumsForSerialization(value).Select(x => fieldSettings[x]).OrderBy(x => x.FieldNum).ToArray();
                        foreach (var s in settings)
                        {
                            s.WriteAction(value, serializer, s.RawTag);
                        }
                    };
                }
                else
                {
                    writeAction = (value, serializer) =>
                    {
                        foreach (var s in fieldSettings.Values)
                        {
                            s.WriteAction(value, serializer, s.RawTag);
                        }
                    };
                }
            }

            // create read actions
            if (actionOnMessageRead != null)
            {
                readAction = deserializer =>
                {
                    T           value         = new T();
                    List <int>  readFieldNums = new List <int>();
                    List <uint> unknownTags   = new List <uint>();
                    uint        tag;
                    while ((tag = deserializer.ReadTag()) > 0)
                    {
                        var fnum = WireFormat.GetTagFieldNumber(tag);

                        Action <T, BasicDeserializer> ra;
                        if (readActionsByTag.TryGetValue(tag, out ra))
                        {
                            ra(value, deserializer);
                            readFieldNums.Add(fnum);
                        }
                        else
                        {
                            deserializer.SkipField(WireFormat.GetTagWireType(tag));
                            unknownTags.Add(tag);
                        }
                    }

                    actionOnMessageRead(value, new MessageReadData(readFieldNums, unknownTags));

                    return(value);
                };

                lenLimitedReadAction = (deserializer, lenght) =>
                {
                    T           value         = new T();
                    List <int>  readFieldNums = new List <int>();
                    List <uint> unknownTags   = new List <uint>();
                    uint        tag;

                    long limitPos = deserializer.stream.Position + lenght;

                    while (deserializer.stream.Position < limitPos)
                    {
                        tag = deserializer.ReadTag();
                        var fnum = WireFormat.GetTagFieldNumber(tag);

                        Action <T, BasicDeserializer> ra;
                        if (readActionsByTag.TryGetValue(tag, out ra))
                        {
                            ra(value, deserializer);
                            readFieldNums.Add(fnum);
                        }
                        else
                        {
                            deserializer.SkipField(WireFormat.GetTagWireType(tag));
                            unknownTags.Add(tag);
                        }
                    }

                    if (deserializer.stream.Position > limitPos)
                    {
                        throw InvalidProtocolBufferException.AllowableMessageLengthWasExceeded();
                    }

                    actionOnMessageRead(value, new MessageReadData(readFieldNums, unknownTags));

                    return(value);
                };
            }
            else
            {
                readAction = deserializer =>
                {
                    T    value = new T();
                    uint tag;
                    while ((tag = deserializer.ReadTag()) > 0)
                    {
                        Action <T, BasicDeserializer> ra;
                        if (readActionsByTag.TryGetValue(tag, out ra))
                        {
                            ra(value, deserializer);
                        }
                        else
                        {
                            deserializer.SkipField(WireFormat.GetTagWireType(tag));
                        }
                    }

                    return(value);
                };

                lenLimitedReadAction = (deserializer, lenght) =>
                {
                    T    value = new T();
                    uint tag;
                    long limitPos = deserializer.stream.Position + lenght;
                    while (deserializer.stream.Position < limitPos)
                    {
                        tag = deserializer.ReadTag();

                        Action <T, BasicDeserializer> ra;
                        if (readActionsByTag.TryGetValue(tag, out ra))
                        {
                            ra(value, deserializer);
                        }
                        else
                        {
                            deserializer.SkipField(WireFormat.GetTagWireType(tag));
                        }
                    }

                    if (deserializer.stream.Position > limitPos)
                    {
                        throw InvalidProtocolBufferException.AllowableMessageLengthWasExceeded();
                    }

                    return(value);
                };
            }

            initialized = true;
        }