Beispiel #1
0
 public ArrayDecorator(TypeModel model, IProtoSerializer tail, int fieldNumber, bool writePacked, WireType packedWireType, Type arrayType, bool overwriteList, bool supportNull) : base(tail)
 {
     this.itemType = arrayType.GetElementType();
     if (!supportNull)
     {
         Helpers.GetUnderlyingType(this.itemType);
     }
     if ((writePacked || (packedWireType != WireType.None)) && (fieldNumber <= 0))
     {
         throw new ArgumentOutOfRangeException("fieldNumber");
     }
     if (!ListDecorator.CanPack(packedWireType))
     {
         if (writePacked)
         {
             throw new InvalidOperationException("Only simple data-types can use packed encoding");
         }
         packedWireType = WireType.None;
     }
     this.fieldNumber    = fieldNumber;
     this.packedWireType = packedWireType;
     if (writePacked)
     {
         this.options = (byte)(this.options | 1);
     }
     if (overwriteList)
     {
         this.options = (byte)(this.options | 2);
     }
     if (supportNull)
     {
         this.options = (byte)(this.options | 4);
     }
     this.arrayType = arrayType;
 }
Beispiel #2
0
 public TupleSerializer(RuntimeTypeModel model, ConstructorInfo ctor, MemberInfo[] members)
 {
     if (ctor == null)
     {
         throw new ArgumentNullException("ctor");
     }
     if (members == null)
     {
         throw new ArgumentNullException("members");
     }
     this.ctor    = ctor;
     this.members = members;
     this.tails   = new IProtoSerializer[members.Length];
     ParameterInfo[] parameters = ctor.GetParameters();
     for (int i = 0; i < members.Length; i++)
     {
         WireType         type;
         IProtoSerializer serializer2;
         Type             parameterType = parameters[i].ParameterType;
         Type             itemType      = null;
         Type             defaultType   = null;
         MetaType.ResolveListTypes(model, parameterType, ref itemType, ref defaultType);
         Type type5       = (itemType == null) ? parameterType : itemType;
         bool asReference = false;
         if (model.FindOrAddAuto(type5, false, true, false) >= 0)
         {
             asReference = model[type5].AsReferenceDefault;
         }
         IProtoSerializer tail = ValueMember.TryGetCoreSerializer(model, DataFormat.Default, type5, out type, asReference, false, false, true);
         if (tail == null)
         {
             throw new InvalidOperationException("No serializer defined for type: " + type5.FullName);
         }
         tail = new TagDecorator(i + 1, type, false, tail);
         if (itemType == null)
         {
             serializer2 = tail;
         }
         else if (parameterType.IsArray)
         {
             serializer2 = new ArrayDecorator(model, tail, i + 1, false, type, parameterType, false, false);
         }
         else
         {
             serializer2 = new ListDecorator(model, parameterType, defaultType, tail, i + 1, false, type, true, false, false);
         }
         this.tails[i] = serializer2;
     }
 }
Beispiel #3
0
        protected override void EmitRead(CompilerContext ctx, Local valueFrom)
        {
            Type type         = ctx.MapType(typeof(List <>)).MakeGenericType(new Type[] { this.itemType });
            Type expectedType = this.ExpectedType;

            using (Local local = this.AppendToCollection ? ctx.GetLocalWithValue(expectedType, valueFrom) : null)
            {
                using (Local local2 = new Local(ctx, expectedType))
                {
                    using (Local local3 = new Local(ctx, type))
                    {
                        ctx.EmitCtor(type);
                        ctx.StoreValue(local3);
                        ListDecorator.EmitReadList(ctx, local3, base.Tail, type.GetMethod("Add"), this.packedWireType, false);
                        using (Local local4 = this.AppendToCollection ? new Local(ctx, ctx.MapType(typeof(int))) : null)
                        {
                            Type[] types = new Type[] { ctx.MapType(typeof(Array)), ctx.MapType(typeof(int)) };
                            if (this.AppendToCollection)
                            {
                                ctx.LoadLength(local, true);
                                ctx.CopyValue();
                                ctx.StoreValue(local4);
                                ctx.LoadAddress(local3, type);
                                ctx.LoadValue(type.GetProperty("Count"));
                                ctx.Add();
                                ctx.CreateArray(this.itemType, null);
                                ctx.StoreValue(local2);
                                ctx.LoadValue(local4);
                                CodeLabel label = ctx.DefineLabel();
                                ctx.BranchIfFalse(label, true);
                                ctx.LoadValue(local);
                                ctx.LoadValue(local2);
                                ctx.LoadValue(0);
                                ctx.EmitCall(expectedType.GetMethod("CopyTo", types));
                                ctx.MarkLabel(label);
                                ctx.LoadValue(local3);
                                ctx.LoadValue(local2);
                                ctx.LoadValue(local4);
                            }
                            else
                            {
                                ctx.LoadAddress(local3, type);
                                ctx.LoadValue(type.GetProperty("Count"));
                                ctx.CreateArray(this.itemType, null);
                                ctx.StoreValue(local2);
                                ctx.LoadAddress(local3, type);
                                ctx.LoadValue(local2);
                                ctx.LoadValue(0);
                            }
                            types[0] = expectedType;
                            MethodInfo method = type.GetMethod("CopyTo", types);
                            if (method == null)
                            {
                                types[1] = ctx.MapType(typeof(Array));
                                method   = type.GetMethod("CopyTo", types);
                            }
                            ctx.EmitCall(method);
                        }
                        ctx.LoadValue(local2);
                    }
                }
            }
        }