Ejemplo n.º 1
0
        internal static void WriteObject(object value, int key, ProtoWriter writer, PrefixStyle style, int fieldNumber)
        {
            if (writer.model == null)
            {
                throw new InvalidOperationException("Cannot serialize sub-objects unless a model is provided");
            }
            if (writer.wireType != WireType.None) throw ProtoWriter.CreateException(writer);

            switch (style)
            {
                case PrefixStyle.Base128:
                    writer.wireType = WireType.String;
                    writer.fieldNumber = fieldNumber;
                    if (fieldNumber > 0) WriteHeaderCore(fieldNumber, WireType.String, writer);
                    break;
                case PrefixStyle.Fixed32:
                case PrefixStyle.Fixed32BigEndian:
                    writer.fieldNumber = 0;
                    writer.wireType = WireType.Fixed32;
                    break;
                default:
                    throw new ArgumentOutOfRangeException("style");
            }
            SubItemToken token = StartSubItem(value, writer, true);
            writer.model.Serialize(key, value, writer);
            EndSubItem(token, writer, style);
            
        }
Ejemplo n.º 2
0
        internal static void WriteObject(object value, int key, ProtoWriter writer, PrefixStyle style, int fieldNumber)
        {
#if FEAT_IKVM
            throw new NotSupportedException();
#else
            if (writer.model == null)
            {
                throw new InvalidOperationException("Cannot serialize sub-objects unless a model is provided");
            }
            if (writer.wireType != WireType.None) throw ProtoWriter.CreateException(writer);

            switch (style)
            {
                case PrefixStyle.Base128:
                    writer.wireType = WireType.String;
                    writer.fieldNumber = fieldNumber;
                    if (fieldNumber > 0) WriteHeaderCore(fieldNumber, WireType.String, writer);
                    break;
                case PrefixStyle.Fixed32:
                case PrefixStyle.Fixed32BigEndian:
                    writer.fieldNumber = 0;
                    writer.wireType = WireType.Fixed32;
                    break;
                default:
                    throw new ArgumentOutOfRangeException("style");
            }
            SubItemToken token = StartSubItem(value, writer, true);
            if (key < 0)
            {
                if (!writer.model.TrySerializeAuxiliaryType(writer, value.GetType(), DataFormat.Default, Serializer.ListItemTag, value, false))
                {
                    TypeModel.ThrowUnexpectedType(value.GetType());
                }
            }
            else
            {
                writer.model.Serialize(key, value, writer);
            }
            EndSubItem(token, writer, style);
#endif       
        }
Ejemplo n.º 3
0
 public static int ReadLengthPrefix(Stream source, bool expectHeader, PrefixStyle style, out int fieldNumber, out int bytesRead)
 {
     fieldNumber = 0;
     switch (style)
     {
     case PrefixStyle.None:
         bytesRead = 0;
         return 2147483647;
     case PrefixStyle.Base128:
     {
         bytesRead = 0;
         uint num2;
         int num;
         if (!expectHeader)
         {
             num = ProtoReader.TryReadUInt32Variant(source, out num2);
             bytesRead += num;
             return (int)((bytesRead >= 0) ? num2 : 4294967295u);
         }
         num = ProtoReader.TryReadUInt32Variant(source, out num2);
         bytesRead += num;
         if (num <= 0)
         {
             bytesRead = 0;
             return -1;
         }
         if ((num2 & 7u) != 2u)
         {
             throw new InvalidOperationException();
         }
         fieldNumber = (int)(num2 >> 3);
         num = ProtoReader.TryReadUInt32Variant(source, out num2);
         bytesRead += num;
         if (bytesRead == 0)
         {
             throw ProtoReader.EoF(null);
         }
         return (int)num2;
     }
     case PrefixStyle.Fixed32:
     {
         int num3 = source.ReadByte();
         if (num3 < 0)
         {
             bytesRead = 0;
             return -1;
         }
         bytesRead = 4;
         return num3 | ProtoReader.ReadByteOrThrow(source) << 8 | ProtoReader.ReadByteOrThrow(source) << 16 | ProtoReader.ReadByteOrThrow(source) << 24;
     }
     case PrefixStyle.Fixed32BigEndian:
     {
         int num4 = source.ReadByte();
         if (num4 < 0)
         {
             bytesRead = 0;
             return -1;
         }
         bytesRead = 4;
         return num4 << 24 | ProtoReader.ReadByteOrThrow(source) << 16 | ProtoReader.ReadByteOrThrow(source) << 8 | ProtoReader.ReadByteOrThrow(source);
     }
     default:
         throw new ArgumentOutOfRangeException("style");
     }
 }
        private static void EndSubItem(SubItemToken token, ProtoWriter writer, PrefixStyle style)
        {
            if (writer == null)
            {
                throw new ArgumentNullException("writer");
            }
            if (writer.wireType != WireType.None)
            {
                throw CreateException(writer);
            }
            int value = token.value;

            if (writer.depth <= 0)
            {
                throw CreateException(writer);
            }
            if (writer.depth-- > RecursionCheckDepth)
            {
                writer.PopRecursionStack();
            }
            writer.packedFieldNumber = 0; // ending the sub-item always wipes packed encoding
            if (value < 0)
            {                             // group - very simple append
                WriteHeaderCore(-value, WireType.EndGroup, writer);
                writer.wireType = WireType.None;
                return;
            }

            // so we're backfilling the length into an existing sequence
            int len;

            switch (style)
            {
            case PrefixStyle.Fixed32:
                len = (int)((writer.ioIndex - value) - 4);
                ProtoWriter.WriteInt32ToBuffer(len, writer.ioBuffer, value);
                break;

            case PrefixStyle.Fixed32BigEndian:
                len = (int)((writer.ioIndex - value) - 4);
                byte[] buffer = writer.ioBuffer;
                ProtoWriter.WriteInt32ToBuffer(len, buffer, value);
                // and swap the byte order
                byte b = buffer[value];
                buffer[value]     = buffer[value + 3];
                buffer[value + 3] = b;
                b = buffer[value + 1];
                buffer[value + 1] = buffer[value + 2];
                buffer[value + 2] = b;
                break;

            case PrefixStyle.Base128:
                // string - complicated because we only reserved one byte;
                // if the prefix turns out to need more than this then
                // we need to shuffle the existing data
                len = (int)((writer.ioIndex - value) - 1);
                int  offset = 0;
                uint tmp    = (uint)len;
                while ((tmp >>= 7) != 0)
                {
                    offset++;
                }
                if (offset == 0)
                {
                    writer.ioBuffer[value] = (byte)(len & 0x7F);
                }
                else
                {
                    DemandSpace(offset, writer);
                    byte[] blob = writer.ioBuffer;
                    Helpers.BlockCopy(blob, value + 1, blob, value + 1 + offset, len);
                    tmp = (uint)len;
                    do
                    {
                        blob[value++] = (byte)((tmp & 0x7F) | 0x80);
                    } while ((tmp >>= 7) != 0);
                    blob[value - 1]  = (byte)(blob[value - 1] & ~0x80);
                    writer.position += offset;
                    writer.ioIndex  += offset;
                }
                break;

            default:
                throw new ArgumentOutOfRangeException("style");
            }
            // and this object is no longer a blockage - also flush if sensible
            const int ADVISORY_FLUSH_SIZE = 1024;

            if (--writer.flushLock == 0 && writer.ioIndex >= ADVISORY_FLUSH_SIZE)
            {
                ProtoWriter.Flush(writer);
            }
        }
Ejemplo n.º 5
0
            /// <summary>
            /// Writes a protocol-buffer representation of the given instance to the supplied stream,
            /// with a length-prefix. This is useful for socket programming,
            /// as DeserializeWithLengthPrefix/MergeWithLengthPrefix can be used to read the single object back
            /// from an ongoing stream.
            /// </summary>
            /// <param name="instance">The existing instance to be serialized (cannot be null).</param>
            /// <param name="style">How to encode the length prefix.</param>
            /// <param name="destination">The destination stream to write to.</param>
            /// <param name="fieldNumber">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
            public static void SerializeWithLengthPrefix(Stream destination, object instance, PrefixStyle style, int fieldNumber)
            {
                RuntimeTypeModel model = RuntimeTypeModel.Default;

                model.SerializeWithLengthPrefix(destination, instance, model.MapType(instance.GetType()), style, fieldNumber);
            }
Ejemplo n.º 6
0
        /// <summary>
        /// Applies a protocol-buffer stream to an existing instance, using length-prefixed
        /// data - useful with network IO.
        /// </summary>
        /// <typeparam name="T">The type being merged.</typeparam>
        /// <param name="instance">The existing instance to be modified (can be null).</param>
        /// <param name="source">The binary stream to apply to the instance (cannot be null).</param>
        /// <param name="style">How to encode the length prefix.</param>
        /// <returns>The updated instance; this may be different to the instance argument if
        /// either the original instance was null, or the stream defines a known sub-type of the
        /// original instance.</returns>
        public static T MergeWithLengthPrefix <T>(Stream source, T instance, PrefixStyle style)
        {
            RuntimeTypeModel model = RuntimeTypeModel.Default;

            return((T)model.DeserializeWithLengthPrefix(source, instance, model.MapType(typeof(T)), style, 0));
        }
Ejemplo n.º 7
0
        /// <summary>
        /// Reads the length-prefix of a message from a stream without buffering additional data, allowing a fixed-length
        /// reader to be created.
        /// </summary>
        public static int ReadLengthPrefix(Stream source, bool expectHeader, PrefixStyle style, out int fieldNumber, out int bytesRead)
        {
            fieldNumber = 0;
            switch (style)
            {
                case PrefixStyle.None:
                    bytesRead = 0;
                    return int.MaxValue;
                case PrefixStyle.Base128:
                    uint val;
                    int tmpBytesRead;
                    bytesRead = 0;
                    if (expectHeader)
                    {                        
                        tmpBytesRead = ProtoReader.TryReadUInt32Variant(source, out val);
                        bytesRead += tmpBytesRead;
                        if (tmpBytesRead > 0)
                        {
                            if ((val & 7) != (uint)WireType.String)
                            { // got a header, but it isn't a string
                                throw new InvalidOperationException();
                            }
                            fieldNumber = (int)(val >> 3);
                            tmpBytesRead = ProtoReader.TryReadUInt32Variant(source, out val);
                            bytesRead += tmpBytesRead;
                            if (bytesRead == 0)
                            { // got a header, but no length
                                throw EoF(null);
                            }
                            return (int)val;
                        }
                        else
                        { // no header
                            bytesRead = 0;
                            return -1;
                        }
                    }
                    // check for a length
                    tmpBytesRead = ProtoReader.TryReadUInt32Variant(source, out val);
                    bytesRead += tmpBytesRead;
                    return bytesRead < 0 ? -1 : (int)val;

                case PrefixStyle.Fixed32:
                    {
                        int b = source.ReadByte();
                        if (b < 0)
                        {
                            bytesRead = 0;
                            return -1;
                        }
                        bytesRead = 4;
                        return b 
                             | (ReadByteOrThrow(source) << 8)
                             | (ReadByteOrThrow(source) << 16)
                             | (ReadByteOrThrow(source) << 24);
                    }
                case PrefixStyle.Fixed32BigEndian:
                    {
                        int b = source.ReadByte();
                        if (b < 0)
                        {
                            bytesRead = 0;
                            return -1;
                        }
                        bytesRead = 4;
                        return (b << 24)
                            | (ReadByteOrThrow(source) << 16)
                            | (ReadByteOrThrow(source) << 8)
                            | ReadByteOrThrow(source);
                    }
                default:
                    throw new ArgumentOutOfRangeException("style");
            }
        }
 /// <summary>
 /// Applies a protocol-buffer stream to an existing instance (or null), using length-prefixed
 /// data - useful with network IO.
 /// </summary>
 /// <param name="type">The type being merged.</param>
 /// <param name="value">The existing instance to be modified (can be null).</param>
 /// <param name="source">The binary stream to apply to the instance (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="expectedField">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
 /// <param name="resolver">Used to resolve types on a per-field basis.</param>
 /// <returns>The updated instance; this may be different to the instance argument if
 /// either the original instance was null, or the stream defines a known sub-type of the
 /// original instance.</returns>
 public object DeserializeWithLengthPrefix(Stream source, object value, Type type, PrefixStyle style, int expectedField, Serializer.TypeResolver resolver)
 {
     int bytesRead;
     return DeserializeWithLengthPrefix(source, value, type, style, expectedField, resolver, out bytesRead);
 }
Ejemplo n.º 9
0
 /// <summary>
 /// Writes a protocol-buffer representation of the given instance to the supplied stream,
 /// with a length-prefix. This is useful for socket programming,
 /// as DeserializeWithLengthPrefix/MergeWithLengthPrefix can be used to read the single object back
 /// from an ongoing stream.
 /// </summary>
 /// <param name="instance">The existing instance to be serialized (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="destination">The destination stream to write to.</param>
 /// <param name="fieldNumber">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
 public static void SerializeWithLengthPrefix(Stream destination, object instance, PrefixStyle style, int fieldNumber)
 {
     if (instance is null)
     {
         throw new ArgumentNullException(nameof(instance));
     }
     RuntimeTypeModel.Default.SerializeWithLengthPrefix(destination, instance, instance.GetType(), style, fieldNumber);
 }
Ejemplo n.º 10
0
 /// <summary>Indicates the number of bytes expected for the next message.</summary>
 /// <param name="buffer">The buffer containing the data to investigate for a length.</param>
 /// <param name="index">The offset of the first byte to read from the buffer.</param>
 /// <param name="count">The number of bytes to read from the buffer.</param>
 /// <param name="style">The algorithm used to encode the length.</param>
 /// <param name="length">The length of the message, if it could be identified.</param>
 /// <returns>True if a length could be obtained, false otherwise.</returns>
 public static bool TryReadLengthPrefix(byte[] buffer, int index, int count, PrefixStyle style, out int length)
 {
     using Stream source = new MemoryStream(buffer, index, count);
     return(TryReadLengthPrefix(source, style, out length));
 }
Ejemplo n.º 11
0
 /// <summary>Indicates the number of bytes expected for the next message.</summary>
 /// <param name="source">The stream containing the data to investigate for a length.</param>
 /// <param name="style">The algorithm used to encode the length.</param>
 /// <param name="length">The length of the message, if it could be identified.</param>
 /// <returns>True if a length could be obtained, false otherwise.</returns>
 public static bool TryReadLengthPrefix(Stream source, PrefixStyle style, out int length)
 {
     length = ProtoReader.ReadLengthPrefix(source, false, style, out int _, out int bytesRead);
     return(bytesRead > 0);
 }
Ejemplo n.º 12
0
 /// <summary>
 /// Applies a protocol-buffer stream to an existing instance, using length-prefixed
 /// data - useful with network IO.
 /// </summary>
 /// <typeparam name="T">The type being merged.</typeparam>
 /// <param name="instance">The existing instance to be modified (can be null).</param>
 /// <param name="source">The binary stream to apply to the instance (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <returns>The updated instance; this may be different to the instance argument if
 /// either the original instance was null, or the stream defines a known sub-type of the
 /// original instance.</returns>
 public static T MergeWithLengthPrefix <[DynamicallyAccessedMembers(DynamicAccess.ContractType)] T>(Stream source, T instance, PrefixStyle style)
 {
     return((T)RuntimeTypeModel.Default.DeserializeWithLengthPrefix(source, instance, typeof(T), style, 0));
 }
Ejemplo n.º 13
0
 /// <summary>
 /// Creates a new instance from a protocol-buffer stream that has a length-prefix
 /// on data (to assist with network IO).
 /// </summary>
 /// <typeparam name="T">The type to be created.</typeparam>
 /// <param name="source">The binary stream to apply to the new instance (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="fieldNumber">The expected tag of the item (only used with base-128 prefix style).</param>
 /// <returns>A new, initialized instance.</returns>
 public static T DeserializeWithLengthPrefix <[DynamicallyAccessedMembers(DynamicAccess.ContractType)] T>(Stream source, PrefixStyle style, int fieldNumber)
 {
     return((T)RuntimeTypeModel.Default.DeserializeWithLengthPrefix(source, null, typeof(T), style, fieldNumber));
 }
Ejemplo n.º 14
0
 /// <summary>
 /// Creates a new instance from a protocol-buffer stream that has a length-prefix
 /// on data (to assist with network IO).
 /// </summary>
 /// <typeparam name="T">The type to be created.</typeparam>
 /// <param name="source">The binary stream to apply to the new instance (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <returns>A new, initialized instance.</returns>
 public static T DeserializeWithLengthPrefix <[DynamicallyAccessedMembers(DynamicAccess.ContractType)] T>(Stream source, PrefixStyle style)
 {
     return(DeserializeWithLengthPrefix <T>(source, style, 0));
 }
Ejemplo n.º 15
0
 /// <summary>
 /// Reads a sequence of consecutive length-prefixed items from a stream, using
 /// either base-128 or fixed-length prefixes. Base-128 prefixes with a tag
 /// are directly comparable to serializing multiple items in succession
 /// (use the <see cref="ListItemTag"/> tag to emulate the implicit behavior
 /// when serializing a list/array). When a tag is
 /// specified, any records with different tags are silently omitted. The
 /// tag is ignored. The tag is ignored for fixed-length prefixes.
 /// </summary>
 /// <typeparam name="T">The type of object to deserialize.</typeparam>
 /// <param name="source">The binary stream containing the serialized records.</param>
 /// <param name="style">The prefix style used in the data.</param>
 /// <param name="fieldNumber">The tag of records to return (if non-positive, then no tag is
 /// expected and all records are returned).</param>
 /// <returns>The sequence of deserialized objects.</returns>
 public static IEnumerable <T> DeserializeItems <[DynamicallyAccessedMembers(DynamicAccess.ContractType)] T>(Stream source, PrefixStyle style, int fieldNumber)
 {
     return(RuntimeTypeModel.Default.DeserializeItems <T>(source, style, fieldNumber));
 }
Ejemplo n.º 16
0
 /// <summary>
 /// Writes a protocol-buffer representation of the given instance to the supplied stream.
 /// </summary>
 /// <param name="instance">The existing instance to be serialized (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="destination">The destination stream to write to.</param>
 /// <param name="tag">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
 public static void SerializeWithLengthPrefix(Stream destination, object instance, PrefixStyle style, int tag)
 {
     if (destination == null) throw new ArgumentNullException("destination");
     if (instance == null) return; // nothing to do
     foreach (MethodInfo method in typeof(Serializer).GetMethods(
         BindingFlags.Static | BindingFlags.Public))
     {
         ParameterInfo[] p;
         if (method.Name == "SerializeWithLengthPrefix" && method.IsGenericMethod)
         {
             MethodInfo genericMethod = method.MakeGenericMethod(instance.GetType());
             if((p = genericMethod.GetParameters()).Length == 4
                 && p[0].ParameterType == typeof(Stream)
                 && p[2].ParameterType == typeof(PrefixStyle)
                 && p[3].ParameterType == typeof(int))
             {
                 genericMethod.Invoke(
                    null, new object[] { destination, instance, style, tag });
                 return;
             }
         }
     }
     throw new ProtoException("Unable to resolve SerializeWithLengthPrefix method");
 }
Ejemplo n.º 17
0
        public static IExtensible ReadProtobufMessage(this BinaryReader reader, Type T, PrefixStyle style)
        {
            var type        = typeof(ProtoBuf.Serializer);
            var deserialize = type.GetMethod("DeserializeWithLengthPrefix", new Type[] {
                typeof(Stream),
                typeof(PrefixStyle)
            });

            deserialize = deserialize.MakeGenericMethod(T);

            return((IExtensible)deserialize.Invoke(null, new object[] { reader.BaseStream, style }));
        }
Ejemplo n.º 18
0
 public static T ReadProtobufMessage <T>(this BinaryReader reader, PrefixStyle style)
 {
     return(ProtoBuf.Serializer.DeserializeWithLengthPrefix <T>(reader.BaseStream, style));
 }
 /// <summary>
 /// Writes a protocol-buffer representation of the given instance to the supplied stream,
 /// with a length-prefix. This is useful for socket programming,
 /// as DeserializeWithLengthPrefix can be used to read the single object back
 /// from an ongoing stream.
 /// </summary>
 /// <param name="type">The type being serialized.</param>
 /// <param name="value">The existing instance to be serialized (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="dest">The destination stream to write to.</param>
 /// <param name="fieldNumber">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
 public void SerializeWithLengthPrefix(Stream dest, object value, Type type, PrefixStyle style, int fieldNumber)
 {
     if (type == null)
     {
         if(value == null) throw new ArgumentNullException("value");
         type = value.GetType();
     }
     int key = GetKey(ref type);
     using (ProtoWriter writer = new ProtoWriter(dest, this))
     {
         switch (style)
         {
             case PrefixStyle.None:
                 Serialize(key, value, writer);
                 break;
             case PrefixStyle.Base128:
             case PrefixStyle.Fixed32:
             case PrefixStyle.Fixed32BigEndian:
                 ProtoWriter.WriteObject(value, key, writer, style, fieldNumber);
                 break;
             default:
                 throw new ArgumentOutOfRangeException("style");
         }
         writer.Close();
     }
 }
Ejemplo n.º 20
0
        public static IProtobufQueryable <T> AsQueryable <T>(this RuntimeTypeModel model, Stream source, PrefixStyle prefix = PrefixStyle.Base128)
        {
            var options = QueryableOptions.GetDefault();

            options.PrefixStyle = prefix;

            return(model.AsQueryable <T>(source, options));
        }
 /// <summary>
 /// Writes a protocol-buffer representation of the given instance to the supplied stream,
 /// with a length-prefix. This is useful for socket programming,
 /// as DeserializeWithLengthPrefix/MergeWithLengthPrefix can be used to read the single object back
 /// from an ongoing stream.
 /// </summary>
 /// <param name="instance">The existing instance to be serialized (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="destination">The destination stream to write to.</param>
 /// <param name="fieldNumber">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
 public static void SerializeWithLengthPrefix(Stream destination, object instance, PrefixStyle style, int fieldNumber)
 {
     throw new NotImplementedException();//TODO: NotImplementedException
 }
Ejemplo n.º 22
0
 private protected override SubItemToken ImplStartLengthPrefixedSubItem(ref State state, object instance, PrefixStyle style)
 {
     WireType = WireType.None;
     return(new SubItemToken(_position64));
 }
Ejemplo n.º 23
0
        public static void SerializeWithLengthPrefix <T>(Stream destination, T instance, PrefixStyle style, int fieldNumber)
        {
            RuntimeTypeModel @default = RuntimeTypeModel.Default;

            @default.SerializeWithLengthPrefix(destination, instance, @default.MapType(typeof(T)), style, fieldNumber);
        }
Ejemplo n.º 24
0
            private protected override void ImplEndLengthPrefixedSubItem(ref State state, SubItemToken token, PrefixStyle style)
            {
                var len = _position64 - token.value64;
                int bytes;

                switch (style)
                {
                case PrefixStyle.Fixed32BigEndian:
                case PrefixStyle.Fixed32:
                    bytes = 4;
                    break;

                case PrefixStyle.Base128:
                    bytes = ImplWriteVarint64(ref state, (ulong)len);
                    break;

                default:
                    state.ThrowInvalidSerializationOperation();
                    goto case PrefixStyle.None;

                case PrefixStyle.None:
                    bytes = 0;
                    break;
                }
                Advance(bytes);
            }
Ejemplo n.º 25
0
 /// <summary>
 /// Writes a protocol-buffer representation of the given instance to the supplied stream,
 /// with a length-prefix. This is useful for socket programming,
 /// as DeserializeWithLengthPrefix/MergeWithLengthPrefix can be used to read the single object back
 /// from an ongoing stream.
 /// </summary>
 /// <typeparam name="T">The type being serialized.</typeparam>
 /// <param name="instance">The existing instance to be serialized (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="destination">The destination stream to write to.</param>
 public static void SerializeWithLengthPrefix <T>(Stream destination, T instance, PrefixStyle style)
 {
     SerializeWithLengthPrefix <T>(destination, instance, style, 0);
 }
Ejemplo n.º 26
0
            protected internal override void WriteMessage <T>(ref State state, T value, ISerializer <T> serializer, PrefixStyle style, bool recursionCheck)
            {
                if (serializer == null)
                {
                    serializer = TypeModel.GetSerializer <T>(Model);
                }
                var len = Measure <T>(this, value, serializer);

                AdvanceSubMessage(ref state, len, style);
            }
Ejemplo n.º 27
0
 /// <summary>
 /// Applies a protocol-buffer stream to an existing instance (or null), using length-prefixed
 /// data - useful with network IO.
 /// </summary>
 /// <param name="value">The existing instance to be modified (can be null).</param>
 /// <param name="source">The binary stream to apply to the instance (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="resolver">Used to resolve types on a per-field basis.</param>
 /// <returns>The updated instance; this may be different to the instance argument if
 /// either the original instance was null, or the stream defines a known sub-type of the
 /// original instance.</returns>
 public static bool TryDeserializeWithLengthPrefix(Stream source, PrefixStyle style, TypeResolver resolver, out object value)
 {
     value = RuntimeTypeModel.Default.DeserializeWithLengthPrefix(source, null, null, style, 0, resolver);
     return(value != null);
 }
Ejemplo n.º 28
0
        public static int ReadLengthPrefix(Stream source, bool expectHeader, PrefixStyle style, out int fieldNumber)
        {
            int num;

            return(ReadLengthPrefix(source, expectHeader, style, out fieldNumber, out num));
        }
Ejemplo n.º 29
0
 public static int ReadLengthPrefix(Stream source, bool expectHeader, PrefixStyle style, out int fieldNumber)
 {
     int num;
     return ProtoReader.ReadLengthPrefix(source, expectHeader, style, out fieldNumber, out num);
 }
Ejemplo n.º 30
0
        public static int ReadLengthPrefix(Stream source, bool expectHeader, PrefixStyle style, out int fieldNumber, out int bytesRead)
        {
            fieldNumber = 0;
            switch (style)
            {
            case PrefixStyle.None:
                bytesRead = 0;
                return(2147483647);

            case PrefixStyle.Base128:
            {
                bytesRead = 0;
                uint num2;
                int  num3;
                if (expectHeader)
                {
                    num3       = TryReadUInt32Variant(source, out num2);
                    bytesRead += num3;
                    if (num3 > 0)
                    {
                        if ((num2 & 7) != 2)
                        {
                            throw new InvalidOperationException();
                        }
                        fieldNumber = (int)(num2 >> 3);
                        num3        = TryReadUInt32Variant(source, out num2);
                        bytesRead  += num3;
                        if (bytesRead == 0)
                        {
                            throw EoF(null);
                        }
                        return((int)num2);
                    }
                    bytesRead = 0;
                    return(-1);
                }
                num3       = TryReadUInt32Variant(source, out num2);
                bytesRead += num3;
                if (bytesRead >= 0)
                {
                    return((int)num2);
                }
                return(-1);
            }

            case PrefixStyle.Fixed32:
            {
                int num4 = source.ReadByte();
                if (num4 < 0)
                {
                    bytesRead = 0;
                    return(-1);
                }
                bytesRead = 4;
                return(num4 | ReadByteOrThrow(source) << 8 | ReadByteOrThrow(source) << 16 | ReadByteOrThrow(source) << 24);
            }

            case PrefixStyle.Fixed32BigEndian:
            {
                int num = source.ReadByte();
                if (num < 0)
                {
                    bytesRead = 0;
                    return(-1);
                }
                bytesRead = 4;
                return(num << 24 | ReadByteOrThrow(source) << 16 | ReadByteOrThrow(source) << 8 | ReadByteOrThrow(source));
            }

            default:
                throw new ArgumentOutOfRangeException("style");
            }
        }
Ejemplo n.º 31
0
 /// <summary>
 /// Reads a sequence of consecutive length-prefixed items from a stream, using
 /// either base-128 or fixed-length prefixes. Base-128 prefixes with a tag
 /// are directly comparable to serializing multiple items in succession
 /// (use the <see cref="ListItemTag"/> tag to emulate the implicit behavior
 /// when serializing a list/array). When a tag is
 /// specified, any records with different tags are silently omitted. The
 /// tag is ignored. The tag is ignores for fixed-length prefixes.
 /// </summary>
 /// <typeparam name="T">The type of object to deserialize.</typeparam>
 /// <param name="source">The binary stream containing the serialized records.</param>
 /// <param name="style">The prefix style used in the data.</param>
 /// <param name="fieldNumber">The tag of records to return (if non-positive, then no tag is
 /// expected and all records are returned).</param>
 /// <returns>The sequence of deserialized objects.</returns>
 public static IEnumerable <T> DeserializeItems <T>(Stream source, PrefixStyle style, int fieldNumber)
 {
     return(RuntimeTypeModel.Default.DeserializeItems <T>(source, style, fieldNumber));
 }
Ejemplo n.º 32
0
            /// <summary>
            /// Writes a protocol-buffer representation of the given instance to the supplied stream,
            /// with a length-prefix. This is useful for socket programming,
            /// as DeserializeWithLengthPrefix/MergeWithLengthPrefix can be used to read the single object back
            /// from an ongoing stream.
            /// </summary>
            /// <param name="instance">The existing instance to be serialized (cannot be null).</param>
            /// <param name="style">How to encode the length prefix.</param>
            /// <param name="destination">The destination stream to write to.</param>
            /// <param name="fieldNumber">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
            public static void SerializeWithLengthPrefix(Stream destination, object instance, PrefixStyle style, int fieldNumber)
            {
                if (instance == null)
                {
                    throw new ArgumentNullException("instance");
                }
                RuntimeTypeModel model = RuntimeTypeModel.Default;

                model.SerializeWithLengthPrefix(destination, instance, model.MapType(instance.GetType()), style, fieldNumber);
            }
Ejemplo n.º 33
0
            /// <summary>
            /// Deserialize object of unknown types from in input stream.
            /// </summary>
            /// <param name="source">The input stream.</param>
            /// <param name="style">The prefix style used to encode the lengths.</param>
            /// <param name="typeReader">The caller must provide a mechanism to resolve a Type from
            /// the tags encountered in the stream. If the delegate returns null, then the instance
            /// is skipped - otherwise, the object is deserialized according to type.</param>
            /// <param name="item">The deserialized instance, or null if the stream terminated.</param>
            /// <returns>True if an object was idenfified; false if the stream terminated. Note
            /// that unexpected types are skipped.</returns>
            public static bool TryDeserializeWithLengthPrefix(Stream source, PrefixStyle style,
                Getter<int,Type> typeReader, out object item)
            {
                uint len;
                Type itemType = null;
                Getter<int, bool> processField = null;
                if(typeReader != null) processField  = delegate(int checkTag)
                {
                    itemType = typeReader(checkTag);
                    return itemType != null;
                };
                if(!Serializer.TryReadPrefixLength(source, style, 1, out len, processField))
                {
                    item = null;
                    return false;
                }

                if (len == uint.MaxValue)
                {
                    item = NonGeneric.Deserialize(itemType, source);
                }
                else
                {
                    using (SubStream subStream = new SubStream(source, len, false))
                    {
                        item = NonGeneric.Deserialize(itemType, subStream);
                    }
                }
                return true;
            }
Ejemplo n.º 34
0
 private bool TryDeserializeWithLengthPrefix(Stream source, PrefixStyle style, Serializer.TypeResolver resolver, out object value)
 {
     value = _model.DeserializeWithLengthPrefix(source, null, typeof(TDeserialized), style, 0, resolver);
     return(value != null);
 }
 /// <summary>
 /// Applies a protocol-buffer stream to an existing instance (or null), using length-prefixed
 /// data - useful with network IO.
 /// </summary>
 /// <param name="type">The type being merged.</param>
 /// <param name="value">The existing instance to be modified (can be null).</param>
 /// <param name="source">The binary stream to apply to the instance (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="fieldNumber">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
 /// <returns>The updated instance; this may be different to the instance argument if
 /// either the original instance was null, or the stream defines a known sub-type of the
 /// original instance.</returns>
 public object DeserializeWithLengthPrefix(Stream source, object value, Type type, PrefixStyle style, int fieldNumber)
 {
     int bytesRead;
     return DeserializeWithLengthPrefix(source, value, type, style, fieldNumber, null, out bytesRead);
 }
Ejemplo n.º 36
0
 public static void SerializeToStreamWithLength <T>(Stream stream, T obj, PrefixStyle style)
 {
     Serializer.SerializeWithLengthPrefix(stream, obj, style);
 }
        /// <summary>
        /// Applies a protocol-buffer stream to an existing instance (or null), using length-prefixed
        /// data - useful with network IO.
        /// </summary>
        /// <param name="type">The type being merged.</param>
        /// <param name="value">The existing instance to be modified (can be null).</param>
        /// <param name="source">The binary stream to apply to the instance (cannot be null).</param>
        /// <param name="style">How to encode the length prefix.</param>
        /// <param name="expectedField">The tag used as a prefix to each record (only used with base-128 style prefixes).</param>
        /// <param name="resolver">Used to resolve types on a per-field basis.</param>
        /// <param name="bytesRead">Returns the number of bytes consumed by this operation (includes length-prefix overheads and any skipped data).</param>
        /// <returns>The updated instance; this may be different to the instance argument if
        /// either the original instance was null, or the stream defines a known sub-type of the
        /// original instance.</returns>
        public object DeserializeWithLengthPrefix(Stream source, object value, Type type, PrefixStyle style, int expectedField, Serializer.TypeResolver resolver, out int bytesRead)
        {
            bool skip;
            int len;
            int tmpBytesRead;
            bytesRead = 0;
            do
            {
                int actualField;
                bool expectPrefix = expectedField > 0 || resolver != null;
                len = ProtoReader.ReadLengthPrefix(source, expectPrefix, style, out actualField, out tmpBytesRead);
                bytesRead += tmpBytesRead;
                if (len < 0) return value;

                if (expectedField == 0 && type == null && resolver != null)
                {
                    type = resolver(actualField);
                    skip = type == null;
                }
                else { skip = expectedField != actualField; }

                if (skip)
                {
                    if (len == int.MaxValue) throw new InvalidOperationException();
                    ProtoReader.Seek(source, len, null);
                    bytesRead += len;
                }
            } while (skip);

            int key = GetKey(ref type);
            if (key < 0) throw new InvalidOperationException();
            using (ProtoReader reader = new ProtoReader(source, this, len))
            {
                object result = Deserialize(key, value, reader);
                bytesRead += reader.Position;
                return result;
            }

        }
Ejemplo n.º 38
0
            private protected override SubItemToken ImplStartLengthPrefixedSubItem(ref State state, object instance, PrefixStyle style)
            {
                switch (WireType)
                {
                case WireType.String:
                    WireType = WireType.None;
                    DemandSpace(32, this, ref state);     // make some space in anticipation...
                    flushLock++;
                    Advance(1);
                    return(new SubItemToken((long)(ioIndex++)));    // leave 1 space (optimistic) for length

                case WireType.Fixed32:
                    DemandSpace(32, this, ref state);     // make some space in anticipation...
                    flushLock++;
                    SubItemToken token = new SubItemToken((long)ioIndex);
                    IncrementedAndReset(4, this);     // leave 4 space (rigid) for length
                    return(token);

                default:
                    state.ThrowInvalidSerializationOperation();
                    return(default);
                }
            }
Ejemplo n.º 39
0
 /// <summary>
 /// Reads the length-prefix of a message from a stream without buffering additional data, allowing a fixed-length
 /// reader to be created.
 /// </summary>
 public static int ReadLengthPrefix(Stream source, bool expectHeader, PrefixStyle style, out int fieldNumber)
 {
     int bytesRead;
     return ReadLengthPrefix(source, expectHeader, style, out fieldNumber, out bytesRead);
 }
Ejemplo n.º 40
0
            private protected override void ImplEndLengthPrefixedSubItem(ref State state, SubItemToken token, PrefixStyle style)
            {
                // so we're backfilling the length into an existing sequence
                int len;
                int value = (int)token.value64;

                switch (style)
                {
                case PrefixStyle.Fixed32:
                    len = (int)(ioIndex - value - 4);
                    WriteUInt32ToBuffer((uint)len, ioBuffer, value);
                    break;

                case PrefixStyle.Fixed32BigEndian:
                    len = (int)(ioIndex - value - 4);
                    byte[] buffer = ioBuffer;
                    WriteUInt32ToBuffer((uint)len, buffer, value);
                    // and swap the byte order
                    byte b = buffer[value];
                    buffer[value]     = buffer[value + 3];
                    buffer[value + 3] = b;
                    b = buffer[value + 1];
                    buffer[value + 1] = buffer[value + 2];
                    buffer[value + 2] = b;
                    break;

                case PrefixStyle.Base128:
                    // string - complicated because we only reserved one byte;
                    // if the prefix turns out to need more than this then
                    // we need to shuffle the existing data
                    len = (int)(ioIndex - value - 1);
                    int  offset = 0;
                    uint tmp    = (uint)len;
                    while ((tmp >>= 7) != 0)
                    {
                        offset++;
                    }
                    if (offset == 0)
                    {
                        ioBuffer[value] = (byte)(len & 0x7F);
                    }
                    else
                    {
                        DemandSpace(offset, this, ref state);
                        byte[] blob = ioBuffer;
                        Buffer.BlockCopy(blob, value + 1, blob, value + 1 + offset, len);
                        tmp = (uint)len;
                        do
                        {
                            blob[value++] = (byte)((tmp & 0x7F) | 0x80);
                        } while ((tmp >>= 7) != 0);
                        blob[value - 1] = (byte)(blob[value - 1] & ~0x80);
                        Advance(offset);
                        ioIndex += offset;
                    }
                    break;

                default:
                    ThrowHelper.ThrowArgumentOutOfRangeException(nameof(style));
                    break;
                }
                // and this object is no longer a blockage - also flush if sensible
                const int ADVISORY_FLUSH_SIZE = 1024;

                if (--flushLock == 0 && ioIndex >= ADVISORY_FLUSH_SIZE)
                {
                    state.Flush();
                }
            }
Ejemplo n.º 41
0
 private static void EndSubItem(SubItemToken token, ProtoWriter writer, PrefixStyle style)
 {
     if (writer == null)
     {
         throw new ArgumentNullException("writer");
     }
     if (writer.wireType != WireType.None)
     {
         throw ProtoWriter.CreateException(writer);
     }
     int value = token.value;
     if (writer.depth <= 0)
     {
         throw ProtoWriter.CreateException(writer);
     }
     if (writer.depth-- > 25)
     {
         writer.PopRecursionStack();
     }
     writer.packedFieldNumber = 0;
     if (value < 0)
     {
         ProtoWriter.WriteHeaderCore(-value, WireType.EndGroup, writer);
         writer.wireType = WireType.None;
         return;
     }
     switch (style)
     {
     case PrefixStyle.Base128:
     {
         int num = writer.ioIndex - value - 1;
         int num2 = 0;
         uint num3 = (uint)num;
         while ((num3 >>= 7) != 0u)
         {
             num2++;
         }
         if (num2 == 0)
         {
             writer.ioBuffer[value] = (byte)(num & 127);
         }
         else
         {
             ProtoWriter.DemandSpace(num2, writer);
             byte[] array = writer.ioBuffer;
             Helpers.BlockCopy(array, value + 1, array, value + 1 + num2, num);
             num3 = (uint)num;
             do
             {
                 array[value++] = (byte)((num3 & 127u) | 128u);
             }
             while ((num3 >>= 7) != 0u);
             array[value - 1] = (byte)((int)array[value - 1] & -129);
             writer.position += num2;
             writer.ioIndex += num2;
         }
         break;
     }
     case PrefixStyle.Fixed32:
     {
         int num = writer.ioIndex - value - 4;
         ProtoWriter.WriteInt32ToBuffer(num, writer.ioBuffer, value);
         break;
     }
     case PrefixStyle.Fixed32BigEndian:
     {
         int num = writer.ioIndex - value - 4;
         byte[] array2 = writer.ioBuffer;
         ProtoWriter.WriteInt32ToBuffer(num, array2, value);
         byte b = array2[value];
         array2[value] = array2[value + 3];
         array2[value + 3] = b;
         b = array2[value + 1];
         array2[value + 1] = array2[value + 2];
         array2[value + 2] = b;
         break;
     }
     default:
         throw new ArgumentOutOfRangeException("style");
     }
     if (--writer.flushLock == 0 && writer.ioIndex >= 1024)
     {
         ProtoWriter.Flush(writer);
     }
 }
Ejemplo n.º 42
0
 /// <summary>
 /// Creates a new instance from a protocol-buffer stream that has a length-prefix
 /// on data (to assist with network IO).
 /// </summary>
 /// <typeparam name="T">The type to be created.</typeparam>
 /// <param name="source">The binary stream to apply to the new instance (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <returns>A new, initialized instance.</returns>
 public static T DeserializeWithLengthPrefix <T>(Stream source, PrefixStyle style)
 {
     return(DeserializeWithLengthPrefix <T>(source, style, 0));
 }
 /// <summary>
 /// Applies a protocol-buffer stream to an existing instance (or null), using length-prefixed
 /// data - useful with network IO.
 /// </summary>
 /// <param name="value">The existing instance to be modified (can be null).</param>
 /// <param name="source">The binary stream to apply to the instance (cannot be null).</param>
 /// <param name="style">How to encode the length prefix.</param>
 /// <param name="resolver">Used to resolve types on a per-field basis.</param>
 /// <returns>The updated instance; this may be different to the instance argument if
 /// either the original instance was null, or the stream defines a known sub-type of the
 /// original instance.</returns>
 public static bool TryDeserializeWithLengthPrefix(Stream source, PrefixStyle style, TypeResolver resolver, out object value)
 {
     throw new NotImplementedException();//TODO: NotImplementedException
 }
Ejemplo n.º 44
0
        /// <summary>
        /// Creates a new instance from a protocol-buffer stream that has a length-prefix
        /// on data (to assist with network IO).
        /// </summary>
        /// <typeparam name="T">The type to be created.</typeparam>
        /// <param name="source">The binary stream to apply to the new instance (cannot be null).</param>
        /// <param name="style">How to encode the length prefix.</param>
        /// <param name="fieldNumber">The expected tag of the item (only used with base-128 prefix style).</param>
        /// <returns>A new, initialized instance.</returns>
        public static T DeserializeWithLengthPrefix <T>(Stream source, PrefixStyle style, int fieldNumber)
        {
            RuntimeTypeModel model = RuntimeTypeModel.Default;

            return((T)model.DeserializeWithLengthPrefix(source, null, model.MapType(typeof(T)), style, fieldNumber));
        }
Ejemplo n.º 45
0
        private static void EndSubItem(SubItemToken token, ProtoWriter writer, PrefixStyle style)
        {
            if (writer.wireType != WireType.None) { throw CreateException(writer); }
            int value = token.value;
            if (writer.depth <= 0) throw CreateException(writer);
            if (writer.depth-- > RecursionCheckDepth)
            {
                writer.PopRecursionStack();
            }
            writer.packedFieldNumber = 0; // ending the sub-item always wipes packed encoding
            if (value < 0)
            {   // group - very simple append
                WriteHeaderCore(-value, WireType.EndGroup, writer);
                writer.wireType = WireType.None;
                return;
            }

            // so we're backfilling the length into an existing sequence
            int len;
            switch(style)
            {
                case PrefixStyle.Fixed32:
                    len = (int)((writer.ioIndex - value) - 4);
                    ProtoWriter.WriteInt32ToBuffer(len, writer.ioBuffer, value);
                    break;
                case PrefixStyle.Fixed32BigEndian:
                    len = (int)((writer.ioIndex - value) - 4);
                    byte[] buffer = writer.ioBuffer;
                    ProtoWriter.WriteInt32ToBuffer(len, buffer, value);
                    // and swap the byte order
                    byte b = buffer[value];
                    buffer[value] = buffer[value + 3];
                    buffer[value + 3] = b;
                    b = buffer[value + 1];
                    buffer[value + 1] = buffer[value + 2];
                    buffer[value + 2] = b;
                    break;
                case PrefixStyle.Base128:
                    // string - complicated because we only reserved one byte;
                    // if the prefix turns out to need more than this then
                    // we need to shuffle the existing data
                    len = (int)((writer.ioIndex - value) - 1);
                    int offset = 0;
                    uint tmp = (uint)len;
                    while ((tmp >>= 7) != 0) offset++;
                    if (offset == 0)
                    {
                        writer.ioBuffer[value] = (byte)(len & 0x7F);
                    }
                    else
                    {
                        DemandSpace(offset, writer);
                        byte[] blob = writer.ioBuffer;
                        Helpers.BlockCopy(blob, value + 1, blob, value + 1 + offset, len);
                        tmp = (uint)len;
                        do
                        {
                            blob[value++] = (byte)((tmp & 0x7F) | 0x80);
                        } while ((tmp >>= 7) != 0);
                        blob[value - 1] = (byte)(blob[value - 1] & ~0x80);
                        writer.position += offset;
                        writer.ioIndex += offset;
                    }
                    break;
                default:
                    throw new ArgumentOutOfRangeException("style");
            }
            // and this object is no longer a blockage
            writer.flushLock--;
        }
Ejemplo n.º 46
0
 public T DeserializeWithLengthPrefix <T>(Stream stream, PrefixStyle prefixStyle)
 {
     return(Serializer.DeserializeWithLengthPrefix <T>(stream, prefixStyle));
 }