Esempio n. 1
0
        public void EmitEncode(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var arrayIsNotNullLabel  = il.DefineLabel();
            var arrayIsNotEmptylabel = il.DefineLabel();
            var endOfSubmethodLabel  = il.DefineLabel();

            emitLoad(il);                                               // if (value)
            il.Brtrue(arrayIsNotNullLabel);                             //     goto arrayIsNotNullLabel

            // Array is null branch
            il.Ldloc(context.DataPointerVar);                           // *(int*) data = -1
            il.Ldc_I4(-1);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            il.Br(endOfSubmethodLabel);                                 // goto endOfSubmethodLabel

            il.MarkLabel(arrayIsNotNullLabel);
            emitLoad(il);                                               // if (value.Length)
            il.Ldlen();                                                 //     goto arrayIsNotEmptylabel
            il.Conv_I4();
            il.Brtrue(arrayIsNotEmptylabel);

            // Array is empty branch
            il.Ldloc(context.DataPointerVar);                           // *(int*) data = 0
            il.Ldc_I4(0);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            il.Br(endOfSubmethodLabel);                                 // goto endOfSubmethodLabel

            // Array is not empty branch
            il.MarkLabel(arrayIsNotEmptylabel);
            var lengthVar = context.GetSharedVariable <int>("length");   // var length = value.Length

            emitLoad(il);
            il.Ldlen();
            il.Conv_I4();
            il.Stloc(lengthVar);
            var sizeVar = context.GetSharedVariable <int>("sizeInBytes");// var sizeInBytes = length * sizeOfStruct

            il.Ldloc(lengthVar);
            il.Ldc_I4(sizeOfStruct);
            il.Mul();
            il.Stloc(sizeVar);
            il.Ldloc(context.DataPointerVar);                           // *(int*) data = length
            il.Ldloc(lengthVar);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            var pointerVar = il.PinArray(typeOfStruct, emitLoad);       // var pinned arrayPointer = pin(value)

            il.Ldloc(context.DataPointerVar);                           // cpblk(data, (byte*)arrayPointer, sizeInBytes)
            il.Ldloc(pointerVar);
            il.Conv_I();
            il.Ldloc(sizeVar);
            il.Cpblk();
            il.UnpinArray(pointerVar);                                  // unpin(arrayPointer)
            il.IncreasePointer(context.DataPointerVar, sizeVar);        // data += sizeInBytes
            il.MarkLabel(endOfSubmethodLabel);
        }
Esempio n. 2
0
        private void EmitProcessDirect(IEmittingContext emittingContext, ProxyMethodParameterCodec[] responseParameterCodecs, Type retvalType)
        {
            bool hasRetval = retvalType != typeof(void);
            var  il        = emittingContext.IL;

            il.Callvirt(OutgoingRequestProcessorMethods.Process);                // stack_0 = stack_0.Process(stack_1, stack_2, stack_3, stack_4, stack_5)

            if (responseParameterCodecs.Any() || hasRetval)
            {
                EmitPrepareToDecode(emittingContext);

                foreach (var codec in responseParameterCodecs)
                {
                    codec.EmitDecodeAndStore(emittingContext);                      // arg_i = Decode(data, remainingBytes, false)
                }
                if (hasRetval)
                {
                    var retvalCodec = new ProxyMethodRetvalCodec(retvalType);
                    retvalCodec.EmitDecode(emittingContext);                        // stack_0 = Decode(data, remainingBytes, false)
                }
            }
            else
            {
                il.Pop();                                                           // pop(stack_0)
            }
        }
Esempio n. 3
0
        public void EmitCalculateSize(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var contractIsNotNullLabel = il.DefineLabel();
            var endOfSubmethodLabel    = il.DefineLabel();

            if (CanBeNull)
            {
                emitLoad(il);                                                   // if (value)
                il.Brtrue(contractIsNotNullLabel);                              //     goto contractIsNotNullLabel

                il.Ldc_I4(sizeof(int));                                         // stack_0 = sizeof(int)
                il.Br(endOfSubmethodLabel);                                     // goto endOfSubmethodLabel

                il.MarkLabel(contractIsNotNullLabel);                           // label contractIsNotNullLabel
            }

            il.Ldc_I4(fixedPartOfSize);                                         // stack_0 = fixedPartOfSize
            foreach (var memberInfo in memberInfos.Skip(numFixedProperties))    // foreach (member)
            {
                var memberVar = il.DeclareLocal(                                //     stack_0 += sizeof member
                    GetMemberType(memberInfo.Member));
                EmitLoadMember(il, emitLoad, memberInfo.Member);
                il.Stloc(memberVar);
                memberInfo.Codec.EmitCalculateSize(context, memberVar);
                il.Add();
            }
            il.MarkLabel(endOfSubmethodLabel);                                  // label endOfSubmethodLabel
        }
Esempio n. 4
0
 public void EmitCalculateSize(IEmittingContext context, Action<MyILGenerator> emitLoad)
 {
     var il = context.IL;
     context.EmitLoadManualCodecFor(type);
     emitLoad(il);
     il.Callvirt(ManualCodecMethods.CalculateSize(type));
 }
Esempio n. 5
0
        public void EmitEncode(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;
            var valueIsNotNullLabel = il.DefineLabel();
            var endOfMethodLabel    = il.DefineLabel();

            var elemVar = il.DeclareLocal(elementType);                     // TElement elem

            emitLoad(il);                                                   // if (value)
            il.Brtrue(valueIsNotNullLabel);                                 //     goto valueIsNotNullLabel

            // value is null branch
            il.Ldloc(context.DataPointerVar);                               // *(int*) data = -1
            il.Ldc_I4(-1);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));        // data += sizeof(int)
            il.Br(endOfMethodLabel);                                        // goto endOfMethodLabel

            // value is not null branch
            il.MarkLabel(valueIsNotNullLabel);                              // label valueIsNotNullLabel
            il.Ldloc(context.DataPointerVar);                               // *(int*) data = (int)value.Count
            EmitLoadCount(il, emitLoad);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));        // data += sizeof(int)
            using (var loop = il.EmitForeachLoop(elementType, emitLoad))    // foreach (current in value)
            {
                loop.LoadCurrent();                                         //     elem = current
                il.Stloc(elemVar);
                elementCodec.EmitEncode(context, elemVar);                  //     encode(data, elem)
            }
            il.MarkLabel(endOfMethodLabel);                                 // label endOfMethodLabel
        }
Esempio n. 6
0
        public void EmitEncode(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var valueIsNotNullLabel = il.DefineLabel();
            var endOfSubmethodLabel = il.DefineLabel();

            if (CanBeNull)
            {
                emitLoad(il);                                               // if (value)
                il.Brtrue(valueIsNotNullLabel);                             //     goto valueIsNotNullLabel

                il.Ldloc(context.DataPointerVar);                           // *(int*) data = 0
                il.Ldc_I4(0);
                il.Stind_I4();
                il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
                il.Br(endOfSubmethodLabel);                                 // goto endOfSubmethodLabel

                il.MarkLabel(valueIsNotNullLabel);                          // goto valueIsNotNullLabel
                il.Ldloc(context.DataPointerVar);                           // *(int*) data = 1
                il.Ldc_I4(1);
                il.Stind_I4();
                il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            }

            foreach (var memberInfo in memberInfos)                         // foreach (member)
            {
                var memberVar = il.DeclareLocal(                            //     encode(value.member)
                    GetMemberType(memberInfo.Member));
                EmitLoadMember(il, emitLoad, memberInfo.Member);
                il.Stloc(memberVar);
                memberInfo.Codec.EmitEncode(context, memberVar);
            }
            il.MarkLabel(endOfSubmethodLabel);                              // label endOfSubmethodLabel
        }
Esempio n. 7
0
        private static void EmitProcessAndEncodeDirect(IEmittingContext emittingContext, HandlerParameterCodec[] responseParameterCodecs, Type retvalType)
        {
            var il = emittingContext.IL;

            EmitEncodeDirect(emittingContext, responseParameterCodecs, retvalType);
            il.Call(TaskMethods.FromResult(typeof(byte[])));
        }
        public void EmitCalculateSize(IEmittingContext context, Action<MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var arrayIsNotNullLabel = il.DefineLabel();
            var endOfSubmethodLabel = il.DefineLabel();

            emitLoad(il);                               // if (value)
            il.Brtrue(arrayIsNotNullLabel);             //     goto arrayIsNotNullLabel

            // Array is null branch
            il.Ldc_I4(sizeof(int));                     // stack_0 = sizeof(int)
            il.Br(endOfSubmethodLabel);                 // goto endOfSubmethodLabel

            // String is not null branch
            il.MarkLabel(arrayIsNotNullLabel);
            emitLoad(il);                               // stack_0 = value.Length * sizeOfStruct + sizeof(int)
            il.Ldlen();
            il.Conv_I4();
            il.Ldc_I4(sizeOfStruct);
            il.Mul();
            il.Ldc_I4(sizeof(int));
            il.Add();
            il.MarkLabel(endOfSubmethodLabel);
        }
Esempio n. 9
0
 protected override void EmitDecodeAndStore(IEmittingContext context, LocalBuilder collectionVar, Action emitLoadIndex, bool doNotCheckBounds)
 {
     var il = context.IL;
     il.Ldloc(collectionVar);
     ElementCodec.EmitDecode(context, doNotCheckBounds);
     il.Callvirt(addMethod);
 }
Esempio n. 10
0
        public void EmitCalculateSize(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var arrayIsNotNullLabel = il.DefineLabel();
            var endOfSubmethodLabel = il.DefineLabel();

            emitLoad(il);                               // if (value)
            il.Brtrue(arrayIsNotNullLabel);             //     goto arrayIsNotNullLabel

            // Array is null branch
            il.Ldc_I4(sizeof(int));                     // stack_0 = sizeof(int)
            il.Br(endOfSubmethodLabel);                 // goto endOfSubmethodLabel

            // String is not null branch
            il.MarkLabel(arrayIsNotNullLabel);
            emitLoad(il);                               // stack_0 = value.Length * sizeOfStruct + sizeof(int)
            il.Ldlen();
            il.Conv_I4();
            il.Ldc_I4(sizeOfStruct);
            il.Mul();
            il.Ldc_I4(sizeof(int));
            il.Add();
            il.MarkLabel(endOfSubmethodLabel);
        }
Esempio n. 11
0
        public void EmitCalculateSize(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var endOfSubmethodLabel = il.DefineLabel();

            if (canBeNull)
            {
                var stringIsNotNullLabel = il.DefineLabel();

                emitLoad(il);                               // if (value)
                il.Brtrue(stringIsNotNullLabel);            //     goto stringIsNotNullLabel

                // String is null branch
                il.Ldc_I4(sizeof(int));                     // stack_0 = sizeof(int)
                il.Br(endOfSubmethodLabel);                 // goto endOfSubmethodLabel

                // String is not null branch
                il.MarkLabel(stringIsNotNullLabel);         // label stringIsNotNullLabel
            }

            EmitLoadAsString(il, emitLoad);                 // stack_0 = (FormatToString(value).Length << 1) + sizeof(int)
            il.Call(GetLength);
            il.Ldc_I4(1);
            il.Shl();
            il.Ldc_I4(sizeof(int));
            il.Add();
            il.MarkLabel(endOfSubmethodLabel);              // label endOfSubmethodLabel
        }
Esempio n. 12
0
        public void EmitCalculateSize(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;
            var valueIsNullOrEmptyLabel = il.DefineLabel();
            var valueHasElementsLabel   = il.DefineLabel();
            var endOfMethodLabel        = il.DefineLabel();

            var elemVar = il.DeclareLocal(elementType);                     // T elem

            emitLoad(il);                                                   // if (!value)
            il.Brfalse(valueIsNullOrEmptyLabel);                            //     goto valueIsNullOrEmptyLabel

            EmitLoadCount(il, emitLoad);                                    // if ((int)value.Length)
            il.Brtrue(valueHasElementsLabel);                               //     goto valueHasElementsLabel

            il.MarkLabel(valueIsNullOrEmptyLabel);                          // label valueIsNullOrEmptyLabel
            il.Ldc_I4(sizeof(int));                                         // stack_0 = sizeof(int)
            il.Br(endOfMethodLabel);                                        // goto endOfMethodLabel

            il.MarkLabel(valueHasElementsLabel);                            // label valueHasElementsLabel
            il.Ldc_I4(sizeof(int));                                         // sum = sizeof(int)
            using (var loop = il.EmitForeachLoop(elementType, emitLoad))    // foreach (current in value)
            {
                loop.LoadCurrent();                                         //     elem = current
                il.Stloc(elemVar);
                elementCodec.EmitCalculateSize(context, elemVar);           //     stack_1 = CalculateSize(elem)
                il.Add();                                                   //     stack_0 = stack_0 + stack_1
            }
            il.MarkLabel(endOfMethodLabel);                                 // label endOfMethodLabel
        }
Esempio n. 13
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;

            var endOfSubmethodLabel = il.DefineLabel();

            if (!doNotCheckBounds)
            {
                var canReadSizeLabel = il.DefineLabel();
                il.Ldloc(context.RemainingBytesVar);                          // if (remainingBytes >= sizeof(int))
                il.Ldc_I4(sizeof(int));                                       //     goto canReadSizeLabel
                il.Bge(canReadSizeLabel);
                il.ThrowUnexpectedEndException();                             // throw new InvalidDataException("...")
                il.MarkLabel(canReadSizeLabel);                               // label canReadSizeLabel
            }
            il.Ldloc(context.DataPointerVar);                                 // stack_0 = *(int*) data
            il.Ldind_I4();
            var tempInteger = context.GetSharedVariable <int>("tempInteger"); // var tempInteger = stack_0

            il.Stloc(tempInteger);
            il.IncreasePointer(context.DataPointerVar, sizeof(int));        // data += sizeof(int)
            il.DecreaseInteger(context.RemainingBytesVar, sizeof(int));     // remainingBytes -= sizeof(int)

            if (canBeNull)
            {
                var strIsNotNullLabel = il.DefineLabel();

                il.Ldloc(tempInteger);                                      // if (tempInteger != -1)
                il.Ldc_I4(-1);                                              //     goto strIsNotNullLabel
                il.Bne_Un(strIsNotNullLabel);

                // String is null branch
                il.Ldnull();                                                // stack_0 = null
                il.Br(endOfSubmethodLabel);                                 // goto endOfSubmethodLabel

                // String is not null branch
                il.MarkLabel(strIsNotNullLabel);                            // label strIsNotNullLabel
            }

            if (!doNotCheckBounds)
            {
                var canReadDataLabel = il.DefineLabel();
                il.Ldloc(context.RemainingBytesVar);                        // if (remainingBytes >= tempInteger)
                il.Ldloc(tempInteger);                                      //     goto canReadDataLabel
                il.Bge(canReadDataLabel);
                il.ThrowUnexpectedEndException();                           // throw new InvalidDataException("...")
                il.MarkLabel(canReadDataLabel);                             // label canReadDataLabel
            }
            il.Ldloc(context.DataPointerVar);                               // stack_0 = data
            il.Ldc_I4(0);                                                   // stack_1 = 0
            il.Ldloc(tempInteger);                                          // stack_2 = tempInteger >> 1
            il.Ldc_I4(1);
            il.Shr();
            il.Newobj(NewString);                                           // stack_0 = new string(stack_0, stack_1, stack_2)
            EmitParseFromString(il);                                        // stack_0 = Parse(stack_0)
            il.IncreasePointer(context.DataPointerVar, tempInteger);        // data += tempInteger
            il.DecreaseInteger(context.RemainingBytesVar, tempInteger);     // remainingBytes -= tempInteger
            il.MarkLabel(endOfSubmethodLabel);                              // label endOfSubmethodLabel
        }
Esempio n. 14
0
        public void EmitEncode(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var strIsNotNullLabel   = il.DefineLabel();
            var endOfSubmethodLabel = il.DefineLabel();

            if (canBeNull)
            {
                emitLoad(il);                                                       // if (val) goto strIsNotNullLabel
                il.Brtrue(strIsNotNullLabel);

                // String is null branch
                il.Ldloc(context.DataPointerVar);                                   // *(int*) data = -1
                il.Ldc_I4(-1);
                il.Stind_I4();
                il.IncreasePointer(context.DataPointerVar, sizeof(int));            // data += sizeof(int)
                il.Br(endOfSubmethodLabel);                                         // goto endOfEncodeLabel

                // String is not null branch
                il.MarkLabel(strIsNotNullLabel);                                    // label strIsNotNullLabel
            }

            var stringValueVar = context.GetSharedVariable <string>("stringValue");  // var stringValue = FormatToString(value)

            EmitLoadAsString(il, emitLoad);
            il.Stloc(stringValueVar);

            var tempIntegerVar = context.GetSharedVariable <int>("tempInteger");     // var tempInteger = stringValue.Length << 1

            il.Ldloc(stringValueVar);
            il.Call(GetLength);
            il.Ldc_I4(1);
            il.Shl();
            il.Stloc(tempIntegerVar);
            il.Ldloc(context.DataPointerVar);                                       // *(int*)data = tempInteger
            il.Ldloc(tempIntegerVar);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));                // data += sizeof(int)
            var pinnedString = il.DeclareLocal(typeof(string), true);               // var pinned pinnedString = stringValue

            il.Ldloc(stringValueVar);
            il.Stloc(pinnedString);
            il.Ldloc(pinnedString);                                                     // stack_0 = (byte*)pinnedString
            il.Conv_I();
            il.Call(GetOffsetToStringData);                                             // stack_0 = stack_0 +
            il.Add();                                                                   //     RuntimeHelpers.OffsetToStringData
            var charPointer = context.GetSharedVariable(typeof(char *), "charPointer"); // charPointer = stack_0

            il.Stloc(charPointer);
            il.Ldloc(context.DataPointerVar);                                       // cpblk(data, charPointer, tempInteger)
            il.Ldloc(charPointer);
            il.Ldloc(tempIntegerVar);
            il.Cpblk();
            il.Ldnull();                                                            // pinnedString = null
            il.Stloc(pinnedString);
            il.IncreasePointer(context.DataPointerVar, tempIntegerVar);             // data += tempInteger
            il.MarkLabel(endOfSubmethodLabel);                                      // label endOfSubmethodLabel
        }
Esempio n. 15
0
        public void EmitCalculateSize(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            context.EmitLoadManualCodecFor(type);
            emitLoad(il);
            il.Callvirt(ManualCodecMethods.CalculateSize(type));
        }
Esempio n. 16
0
        protected override void EmitDecodeAndStore(IEmittingContext context, LocalBuilder collectionVar, Action emitLoadIndex, bool doNotCheckBounds)
        {
            var il = context.IL;

            il.Ldloc(collectionVar);
            ElementCodec.EmitDecode(context, doNotCheckBounds);
            il.Callvirt(addMethod);
        }
Esempio n. 17
0
        public void EmitEncode(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            context.EmitLoadManualCodecFor(type);
            il.Ldloca(context.DataPointerVar);
            emitLoad(il);
            il.Callvirt(ManualCodecMethods.Encode(type));
        }
Esempio n. 18
0
 public HandlerParameterCodec(IEmittingContext emittingContext, MethodParameterDescription description)
 {
     this.emittingContext = emittingContext;
     type = description.Type;
     way = description.Way;
     codec = new IndirectCodec(type);
     if (IsResponseParameter)
         local = emittingContext.IL.DeclareLocal(type);
 }
 protected override void EmitDecodeAndStore(IEmittingContext context, LocalBuilder collectionVar, Action emitLoadIndex, bool doNotCheckBounds)
 {
     var il = context.IL;
     il.Ldloc(collectionVar);
     emitLoadIndex();
     il.Ldelema(ElementType);
     ElementCodec.EmitDecode(context, doNotCheckBounds);
     il.Stobj(ElementType);
 }
Esempio n. 20
0
        public void EmitEncode(IEmittingContext context, Action <MyILGenerator> emitLoad)
        {
            var il = context.IL;

            il.Ldloc(context.DataPointerVar);                           // *(T*) data = val
            emitLoad(il);
            il.Stobj(type);
            il.IncreasePointer(context.DataPointerVar, sizeInBytes);   // data += sizeInBytes
        }
 public void EmitDecodeAndStore(IEmittingContext emittingContext)
 {
     var il = emittingContext.IL;
     il.Ldarg(argIndex);
     codec.EmitDecode(emittingContext, false);
     if (type.IsValueType)
         il.Stobj(type);
     else
         il.Stind_Ref();
 }
Esempio n. 22
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;

            context.EmitLoadManualCodecFor(type);
            il.Ldloca(context.DataPointerVar);
            il.Ldloca(context.RemainingBytesVar);
            il.Ldc_I4(0);
            il.Callvirt(ManualCodecMethods.Decode(type));
        }
Esempio n. 23
0
        protected override void EmitDecodeAndStore(IEmittingContext context, LocalBuilder collectionVar, Action emitLoadIndex, bool doNotCheckBounds)
        {
            var il = context.IL;

            il.Ldloc(collectionVar);
            emitLoadIndex();
            il.Ldelema(ElementType);
            ElementCodec.EmitDecode(context, doNotCheckBounds);
            il.Stobj(ElementType);
        }
Esempio n. 24
0
 public HandlerParameterCodec(IEmittingContext emittingContext, MethodParameterDescription description)
 {
     this.emittingContext = emittingContext;
     type  = description.Type;
     way   = description.Way;
     codec = new IndirectCodec(type);
     if (IsResponseParameter)
     {
         local = emittingContext.IL.DeclareLocal(type);
     }
 }
Esempio n. 25
0
        private static void EmitPrepareToDecode(IEmittingContext emittingContext)
        {
            var il = emittingContext.IL;
            var responseDataArrayVar = il.DeclareLocal(typeof(byte[]));

            il.Stloc(responseDataArrayVar);                                     // dataArray = stack_0
            il.Ldloc(responseDataArrayVar);                                     // remainingBytes = dataArray.Length
            il.Ldlen();
            il.Stloc(emittingContext.RemainingBytesVar);
            var pinnedVar = il.PinArray(typeof(byte), responseDataArrayVar);    // var pinned dataPointer = pin(dataArray)

            il.Ldloc(pinnedVar);                                                // data = dataPointer
            il.Stloc(emittingContext.DataPointerVar);
        }
        public void EmitDecodeAndStore(IEmittingContext emittingContext)
        {
            var il = emittingContext.IL;

            il.Ldarg(argIndex);
            codec.EmitDecode(emittingContext, false);
            if (type.IsValueType)
            {
                il.Stobj(type);
            }
            else
            {
                il.Stind_Ref();
            }
        }
Esempio n. 27
0
        private static void EmitEncodeDirect(IEmittingContext emittingContext, HandlerParameterCodec[] responseParameterCodecs, Type retvalType)
        {
            var  il        = emittingContext.IL;
            bool hasRetval = retvalType != typeof(void);

            if (hasRetval || responseParameterCodecs.Any())
            {
                HandlerRetvalCodec retvalCodec = null;

                if (hasRetval)
                {
                    retvalCodec = new HandlerRetvalCodec(emittingContext, retvalType);
                    retvalCodec.EmitStore();                                                // var ret = stack_0
                    retvalCodec.EmitCalculateSize();                                        // stack_0 = calculateSize(ret)
                }

                bool hasSizeOnStack = hasRetval;
                foreach (var codec in responseParameterCodecs)
                {
                    codec.EmitCalculateSize();                                              // stack_0 += calculateSize(param_i)
                    EmitAddIf(il, ref hasSizeOnStack);
                }

                var dataArrayVar = il.DeclareLocal(typeof(byte[]));                         // var dataArray = new byte[size of retval]
                il.Newarr(typeof(byte));
                il.Stloc(dataArrayVar);

                var pinnedVar = il.PinArray(typeof(byte), dataArrayVar);                    // var pinned dataPointer = pin(dataArrayVar)
                il.Ldloc(pinnedVar);                                                        // data = dataPointer
                il.Stloc(emittingContext.DataPointerVar);

                foreach (var codec in responseParameterCodecs)
                {
                    codec.EmitEncode();                                                     // encode(data, param_i)
                }
                if (hasRetval)
                {
                    retvalCodec.EmitEncode();                                               // encode(data, ret)
                }
                il.Ldloc(dataArrayVar);                                                     // stack_0 = dataArray
            }
            else
            {
                il.Ldc_I4(0);                                                               // stack_0 = new byte[0]
                il.Newarr(typeof(byte));
            }
        }
Esempio n. 28
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;
            var valueIsNotNullLabel = il.DefineLabel();
            var endOfMethodLabel    = il.DefineLabel();

            var resultVar = il.DeclareLocal(type);                      // TCollection result

            if (!doNotCheckBounds)
            {
                var canReadLengthLabel = il.DefineLabel();
                il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeof(int))
                il.Ldc_I4(sizeof(int));                                 //     goto canReadLengthLabel
                il.Bge(canReadLengthLabel);
                il.ThrowUnexpectedEndException();                       // throw new InvalidDataException("...")
                il.MarkLabel(canReadLengthLabel);                       // label canReadLengthLabel
            }

            var lengthVar = il.DeclareLocal(typeof(int));               // var length = *(int*) data

            il.Ldloc(context.DataPointerVar);
            il.Ldind_I4();
            il.Stloc(lengthVar);
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            il.DecreaseInteger(context.RemainingBytesVar, sizeof(int)); // remainingBytes -= sizeof(int)
            il.Ldloc(lengthVar);                                        // if (length != -1)
            il.Ldc_I4(-1);                                              //     goto valueIsNotNullLabel
            il.Bne_Un(valueIsNotNullLabel);

            il.Ldnull();                                                // stack_0 = null
            il.Br(endOfMethodLabel);                                    // goto endOfMethodLabel

            il.MarkLabel(valueIsNotNullLabel);                          // label valueIsNotNullLabel
            EmitCreateCollection(il, lengthVar);                        // result = new TCollection()
            il.Stloc(resultVar);

            using (var loop = il.EmitForLoop(lengthVar))                // for (int i = 0; i < length; i++)
            {                                                           //     result.Add(decode(data, remainingBytes))
                EmitDecodeAndStore(context, resultVar,
                                   loop.LoadIndex, doNotCheckBounds);
            }

            il.Ldloc(resultVar);                                        // stack_0 = result
            il.MarkLabel(endOfMethodLabel);                             // label endOfMethodLabel
        }
Esempio n. 29
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;

            if (!doNotCheckBounds)
            {
                var everythingsAllrightLabel = il.DefineLabel();
                il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeInBytes)
                il.Ldc_I4(sizeInBytes);                                 //     goto everythingsAllrightLabel
                il.Bge(everythingsAllrightLabel);
                il.ThrowUnexpectedEndException();                       // throw new InvalidDataException("...")
                il.MarkLabel(everythingsAllrightLabel);                 // label everythingsAllrightLabel
            }
            il.Ldloc(context.DataPointerVar);                           // stack_0 = *(T*) data
            il.Ldobj(type);
            il.IncreasePointer(context.DataPointerVar, sizeInBytes);    // data += sizeInBytes
            il.DecreaseInteger(context.RemainingBytesVar, sizeInBytes); // remainingBytes -= sizeInBytes
        }
Esempio n. 30
0
 public void EmitDecode(IEmittingContext emittingContext)
 {
     codec.EmitDecode(emittingContext, false);
 }
 public void EmitCalculateSize(IEmittingContext emittingContext)
 {
     typeCodec.EmitCalculateSize(emittingContext, Loaders.TypeOf(type));
 }
Esempio n. 32
0
 protected abstract void EmitDecodeAndStore(IEmittingContext context, LocalBuilder collectionVar, Action emitLoadIndex, bool doNotCheckBounds);
Esempio n. 33
0
 public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
 {
     var il = context.IL;
     if (!doNotCheckBounds)
     {
         var everythingsAllrightLabel = il.DefineLabel();
         il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeInBytes)
         il.Ldc_I4(sizeInBytes);                                 //     goto everythingsAllrightLabel
         il.Bge(everythingsAllrightLabel);
         il.ThrowUnexpectedEndException();                       // throw new InvalidDataException("...")
         il.MarkLabel(everythingsAllrightLabel);                 // label everythingsAllrightLabel
     }
     il.Ldloc(context.DataPointerVar);                           // stack_0 = *(T*) data
     il.Ldobj(type);
     il.IncreasePointer(context.DataPointerVar, sizeInBytes);    // data += sizeInBytes
     il.DecreaseInteger(context.RemainingBytesVar, sizeInBytes); // remainingBytes -= sizeInBytes
 }
Esempio n. 34
0
        public void EmitEncode(IEmittingContext context, Action<MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var arrayIsNotNullLabel = il.DefineLabel();
            var arrayIsNotEmptylabel = il.DefineLabel();
            var endOfSubmethodLabel = il.DefineLabel();

            emitLoad(il);                                               // if (value)
            il.Brtrue(arrayIsNotNullLabel);                             //     goto arrayIsNotNullLabel

            // Array is null branch
            il.Ldloc(context.DataPointerVar);                           // *(int*) data = -1
            il.Ldc_I4(-1);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            il.Br(endOfSubmethodLabel);                                 // goto endOfSubmethodLabel

            il.MarkLabel(arrayIsNotNullLabel);
            emitLoad(il);                                               // if (value.Length)
            il.Ldlen();                                                 //     goto arrayIsNotEmptylabel
            il.Conv_I4();
            il.Brtrue(arrayIsNotEmptylabel);

            // Array is empty branch
            il.Ldloc(context.DataPointerVar);                           // *(int*) data = 0
            il.Ldc_I4(0);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            il.Br(endOfSubmethodLabel);                                 // goto endOfSubmethodLabel

            // Array is not empty branch
            il.MarkLabel(arrayIsNotEmptylabel);
            var lengthVar = context.GetSharedVariable<int>("length");   // var length = value.Length
            emitLoad(il);
            il.Ldlen();
            il.Conv_I4();
            il.Stloc(lengthVar);
            var sizeVar = context.GetSharedVariable<int>("sizeInBytes");// var sizeInBytes = length * sizeOfStruct
            il.Ldloc(lengthVar);
            il.Ldc_I4(sizeOfStruct);
            il.Mul();
            il.Stloc(sizeVar);
            il.Ldloc(context.DataPointerVar);                           // *(int*) data = length
            il.Ldloc(lengthVar);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            var pointerVar = il.PinArray(typeOfStruct, emitLoad);       // var pinned arrayPointer = pin(value)
            il.Ldloc(context.DataPointerVar);                           // cpblk(data, (byte*)arrayPointer, sizeInBytes)
            il.Ldloc(pointerVar);
            il.Conv_I();
            il.Ldloc(sizeVar);
            il.Cpblk();
            il.UnpinArray(pointerVar);                                  // unpin(arrayPointer)
            il.IncreasePointer(context.DataPointerVar, sizeVar);        // data += sizeInBytes
            il.MarkLabel(endOfSubmethodLabel);
        }
Esempio n. 35
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;
            var valueIsNotNullLabel = il.DefineLabel();
            var endOfMethodLabel = il.DefineLabel();

            var resultVar = il.DeclareLocal(type);                      // TCollection result

            if (!doNotCheckBounds)
            {
                var canReadLengthLabel = il.DefineLabel();
                il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeof(int))
                il.Ldc_I4(sizeof(int));                                 //     goto canReadLengthLabel
                il.Bge(canReadLengthLabel);
                il.ThrowUnexpectedEndException();                       // throw new InvalidDataException("...")
                il.MarkLabel(canReadLengthLabel);                       // label canReadLengthLabel
            }

            var lengthVar = il.DeclareLocal(typeof(int));               // var length = *(int*) data
            il.Ldloc(context.DataPointerVar);
            il.Ldind_I4();
            il.Stloc(lengthVar);
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            il.DecreaseInteger(context.RemainingBytesVar, sizeof(int)); // remainingBytes -= sizeof(int)
            il.Ldloc(lengthVar);                                        // if (length != -1)
            il.Ldc_I4(-1);                                              //     goto valueIsNotNullLabel
            il.Bne_Un(valueIsNotNullLabel);

            il.Ldnull();                                                // stack_0 = null
            il.Br(endOfMethodLabel);                                    // goto endOfMethodLabel

            il.MarkLabel(valueIsNotNullLabel);                          // label valueIsNotNullLabel
            EmitCreateCollection(il, lengthVar);                        // result = new TCollection()
            il.Stloc(resultVar);

            using (var loop = il.EmitForLoop(lengthVar))                // for (int i = 0; i < length; i++)
            {                                                           //     result.Add(decode(data, remainingBytes))
                EmitDecodeAndStore(context, resultVar,
                                   loop.LoadIndex, doNotCheckBounds);
            }

            il.Ldloc(resultVar);                                        // stack_0 = result
            il.MarkLabel(endOfMethodLabel);                             // label endOfMethodLabel
        }
 public static void EmitEncode(this IEmittingCodec codec, IEmittingContext context, Action<MyILGenerator> emitLoadParent, MethodInfo propertyGetter)
 {
     codec.EmitEncode(context, il => { emitLoadParent(il); il.Call(propertyGetter); });
 }
Esempio n. 37
0
        private static void EmitProcessAndEncodeAsyncVoid(IEmittingContext emittingContext)
        {
            var il = emittingContext.IL;

            il.Call(ToEmptyByteArrayTaskMethod);
        }
 public static void EmitEncode(this IEmittingCodec codec, IEmittingContext context, int argIndex)
 {
     codec.EmitEncode(context, il => il.Ldarg(argIndex));
 }
 public static void EmitEncode(this IEmittingCodec codec, IEmittingContext context, LocalBuilder localVar)
 {
     codec.EmitEncode(context, il => il.Ldloc(localVar));
 }
Esempio n. 40
0
 private static void EmitProcessAndEncodeDirect(IEmittingContext emittingContext, HandlerParameterCodec[] responseParameterCodecs, Type retvalType)
 {
     var il = emittingContext.IL;
     EmitEncodeDirect(emittingContext, responseParameterCodecs, retvalType);
     il.Call(TaskMethods.FromResult(typeof(byte[])));
 }
Esempio n. 41
0
        private static void EmitProcessAndEncodeAsyncWithRetval(HandlerClassBuildingContext classContext, IEmittingContext emittingContext, Type pureRetvalType)
        {
            var encodeDeferredMethod = CreateEncodeDeferredMethod(classContext, pureRetvalType);
            var continueWithMethod = TaskMethods.ContinueWith(pureRetvalType, typeof(byte[]));

            var il = emittingContext.IL;
            il.Ldarg(0);
            il.Ldftn(encodeDeferredMethod);
            il.Newobj(FuncMethods.Constructor(typeof(Task<>).MakeGenericType(pureRetvalType), typeof(byte[])));
            il.Callvirt(continueWithMethod);
        }
Esempio n. 42
0
        public void EmitCalculateSize(IEmittingContext context, Action<MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var endOfSubmethodLabel = il.DefineLabel();

            if (canBeNull)
            {
                var stringIsNotNullLabel = il.DefineLabel();

                emitLoad(il);                               // if (value)
                il.Brtrue(stringIsNotNullLabel);            //     goto stringIsNotNullLabel

                // String is null branch
                il.Ldc_I4(sizeof(int));                     // stack_0 = sizeof(int)
                il.Br(endOfSubmethodLabel);                 // goto endOfSubmethodLabel

                // String is not null branch
                il.MarkLabel(stringIsNotNullLabel);         // label stringIsNotNullLabel
            }

            EmitLoadAsString(il, emitLoad);                 // stack_0 = (FormatToString(value).Length << 1) + sizeof(int)
            il.Call(GetLength);
            il.Ldc_I4(1);
            il.Shl();
            il.Ldc_I4(sizeof(int));
            il.Add();
            il.MarkLabel(endOfSubmethodLabel);              // label endOfSubmethodLabel
        }
 public void EmitEncode(IEmittingContext emittingContext)
 {
     typeCodec.EmitEncode(emittingContext, Loaders.TypeOf(type));
 }
 public static void EmitEncodeIndirect(this IEmittingCodec codec, IEmittingContext context, int argIndex, Type type)
 {
     codec.EmitEncode(context, il => { il.Ldarg(argIndex); il.Ldobj(type); });
 }
Esempio n. 45
0
 public HandlerRetvalCodec(IEmittingContext emittingContext, Type type)
 {
     this.emittingContext = emittingContext;
     codec = new IndirectCodec(type);
     local = emittingContext.IL.DeclareLocal(type);
 }
Esempio n. 46
0
        public void EmitEncode(IEmittingContext context, Action<MyILGenerator> emitLoad)
        {
            var il = context.IL;

            var strIsNotNullLabel = il.DefineLabel();
            var endOfSubmethodLabel = il.DefineLabel();

            if (canBeNull)
            {
                emitLoad(il);                                                       // if (val) goto strIsNotNullLabel
                il.Brtrue(strIsNotNullLabel);

                // String is null branch
                il.Ldloc(context.DataPointerVar);                                   // *(int*) data = -1
                il.Ldc_I4(-1);
                il.Stind_I4();
                il.IncreasePointer(context.DataPointerVar, sizeof(int));            // data += sizeof(int)
                il.Br(endOfSubmethodLabel);                                         // goto endOfEncodeLabel

                // String is not null branch
                il.MarkLabel(strIsNotNullLabel);                                    // label strIsNotNullLabel
            }

            var stringValueVar = context.GetSharedVariable<string>("stringValue");  // var stringValue = FormatToString(value)
            EmitLoadAsString(il, emitLoad);
            il.Stloc(stringValueVar);

            var tempIntegerVar = context.GetSharedVariable<int>("tempInteger");     // var tempInteger = stringValue.Length << 1
            il.Ldloc(stringValueVar);
            il.Call(GetLength);
            il.Ldc_I4(1);
            il.Shl();
            il.Stloc(tempIntegerVar);
            il.Ldloc(context.DataPointerVar);                                       // *(int*)data = tempInteger
            il.Ldloc(tempIntegerVar);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));                // data += sizeof(int)
            var pinnedString = il.DeclareLocal(typeof(string), true);               // var pinned pinnedString = stringValue
            il.Ldloc(stringValueVar);
            il.Stloc(pinnedString);
            il.Ldloc(pinnedString);                                                 // stack_0 = (byte*)pinnedString
            il.Conv_I();
            il.Call(GetOffsetToStringData);                                         // stack_0 = stack_0 +
            il.Add();                                                               //     RuntimeHelpers.OffsetToStringData
            var charPointer = context.GetSharedVariable(typeof(char*), "charPointer");// charPointer = stack_0
            il.Stloc(charPointer);
            il.Ldloc(context.DataPointerVar);                                       // cpblk(data, charPointer, tempInteger)
            il.Ldloc(charPointer);
            il.Ldloc(tempIntegerVar);
            il.Cpblk();
            il.Ldnull();                                                            // pinnedString = null
            il.Stloc(pinnedString);
            il.IncreasePointer(context.DataPointerVar, tempIntegerVar);             // data += tempInteger
            il.MarkLabel(endOfSubmethodLabel);                                      // label endOfSubmethodLabel
        }
Esempio n. 47
0
        private static void EmitProcessAndEncodeAsyncWithRetval(HandlerClassBuildingContext classContext, IEmittingContext emittingContext, Type pureRetvalType)
        {
            var encodeDeferredMethod = CreateEncodeDeferredMethod(classContext, pureRetvalType);
            var continueWithMethod   = TaskMethods.ContinueWith(pureRetvalType, typeof(byte[]));

            var il = emittingContext.IL;

            il.Ldarg(0);
            il.Ldftn(encodeDeferredMethod);
            il.Newobj(FuncMethods.Constructor(typeof(Task <>).MakeGenericType(pureRetvalType), typeof(byte[])));
            il.Callvirt(continueWithMethod);
        }
 public void EmitCalculateSize(IEmittingContext emittingContext)
 {
     codec.EmitCalculateSize(emittingContext, emitLoad);
 }
Esempio n. 49
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;

            var enoughBytesForLengthLabel = il.DefineLabel();
            var enoughBytesForDataLabel = il.DefineLabel();
            var lengthIsMinusOneLabel = il.DefineLabel();
            var lengthIsZeroLabel = il.DefineLabel();
            var labelGroup = new[] {lengthIsMinusOneLabel, lengthIsZeroLabel};
            var lengthIsPositiveLabel = il.DefineLabel();
            var endOfMethodLabel = il.DefineLabel();

            if (!doNotCheckBounds)
            {
                il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeof(int))
                il.Ldc_I4(sizeof(int));                                 //     goto enoughBytesForLengthLabel
                il.Bge(enoughBytesForLengthLabel);

                // not enough bytes for length
                il.ThrowUnexpectedEndException();                       // throw new InvalidDataException(...)
            }

            // enough bytes for length
            il.MarkLabel(enoughBytesForLengthLabel);
            var lengthVar = context.GetSharedVariable<int>("length");    // var length = *(int*)data
            il.Ldloc(context.DataPointerVar);
            il.Ldind_I4();
            il.Stloc(lengthVar);
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            il.DecreaseInteger(context.RemainingBytesVar, sizeof(int)); // remainingBytes -= sizeof(int)
            il.Ldloc(lengthVar);                                        // switch(length + 1)
            il.Ldc_I4(1);                                               //     case 0:  goto lengthIsMinusOneLabel
            il.Add();                                                   //     case 1:  goto lengthIsZeroLabel
            il.Switch(labelGroup);                                      //     default: goto lengthIsPositiveLabel
            il.Br(lengthIsPositiveLabel);

            // length is -1
            il.MarkLabel(lengthIsMinusOneLabel);
            il.Ldnull();                                                // stack_0 = null
            il.Br(endOfMethodLabel);                                    // goto endOfMethodLabel

            // length is 0
            il.MarkLabel(lengthIsZeroLabel);
            il.Ldc_I4(0);                                               // stack_0 = new T[0]
            il.Newarr(typeOfStruct);
            il.Br(endOfMethodLabel);                                    // goto endOfMethodLabel

            // length is positive
            il.MarkLabel(lengthIsPositiveLabel);
            var sizeVar = context.GetSharedVariable<int>("sizeInBytes");// var sizeInBytes = length * sizeOfStruct
            il.Ldloc(lengthVar);
            il.Ldc_I4(sizeOfStruct);
            il.Mul();
            il.Stloc(sizeVar);

            if (!doNotCheckBounds)
            {
                il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeInBytes)
                il.Ldloc(sizeVar);                                      //     goto enoughBytesForDataLabel
                il.Bge(enoughBytesForDataLabel);

                // not enough bytes for data
                il.ThrowUnexpectedEndException();                       // throw new InvalidDataException(...)
            }

            // enough bytes for data
            il.MarkLabel(enoughBytesForDataLabel);
            var resultVar = context.GetSharedVariable(                   // var result = new T[length]
                typeOfStruct.MakeArrayType(), "arrayOf");
            il.Ldloc(lengthVar);
            il.Newarr(typeOfStruct);
            il.Stloc(resultVar);
            var pointerVar = il.PinArray(typeOfStruct, resultVar); // var pinned arrayPointer = pin(value)
            il.Ldloc(pointerVar);                         // cpblk((byte*)arrayPointer, data, sizeInBytes)
            il.Conv_I();
            il.Ldloc(context.DataPointerVar);
            il.Ldloc(sizeVar);
            il.Cpblk();
            il.UnpinArray(pointerVar);                                // unpin(arrayPointer)
            il.IncreasePointer(context.DataPointerVar, sizeVar);       // data += size
            il.DecreaseInteger(context.RemainingBytesVar, sizeVar);    // remainingBytes -= size
            il.Ldloc(resultVar);                          // stack_0 = result
            il.MarkLabel(endOfMethodLabel);
        }
Esempio n. 50
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;

            var resultIsNotNullLabel = il.DefineLabel();
            var endOfSubmethodLabel  = il.DefineLabel();

            if (CanBeNull)
            {
                if (!doNotCheckBounds)
                {
                    var canReadFlagLabel = il.DefineLabel();
                    il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeof(int))
                    il.Ldc_I4(sizeof(int));                                 //     goto canReadFlagLabel
                    il.Bge(canReadFlagLabel);
                    il.ThrowUnexpectedEndException();                       // throw new InvalidDataException("...")
                    il.MarkLabel(canReadFlagLabel);                         // label canReadFlagLabel
                }

                var flagVar = il.DeclareLocal(typeof(int));

                il.Ldloc(context.DataPointerVar);                           // flag = *(int*) data
                il.Ldind_I4();
                il.Stloc(flagVar);
                il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
                il.DecreaseInteger(context.RemainingBytesVar, sizeof(int)); // remainingBytes -= sizeof(int)

                il.Ldloc(flagVar);                                          // if (flag)
                il.Brtrue(resultIsNotNullLabel);                            //     goto resultIsNotNullLabel

                il.Ldnull();                                                // stack_0 = null
                il.Br(endOfSubmethodLabel);                                 // goto endOfSubmethodLabel

                il.MarkLabel(resultIsNotNullLabel);                         // label resultIsNotNullLabel
            }

            var thisVar = il.DeclareLocal(type);

            if (CanBeNull)
            {
                il.Ldtoken(type);                                           // stack_0 = (T)FormatterServices.GetUninitializedObject(typeof(T))
                il.Call(GetTypeFromHandleMethod);
                il.Call(GetUninitializedObject);
                il.Castclass(type);
                il.Stloc(thisVar);
            }
            else
            {
                il.Ldloca(thisVar);
                il.Initobj(type);
            }

            foreach (var memberInfo in memberInfos)                         // foreach (member)
            {
                if (CanBeNull)                                              //     stack_0.member = decode()
                {
                    il.Ldloc(thisVar);
                }
                else
                {
                    il.Ldloca(thisVar);
                }
                memberInfo.Codec.EmitDecode(context, doNotCheckBounds);
                EmitSetMember(il, memberInfo.Member);
            }

            il.Ldloc(thisVar);
            il.MarkLabel(endOfSubmethodLabel);                              // label endOfSubmethodLabel
        }
Esempio n. 51
0
        public void EmitEncode(IEmittingContext context, Action<MyILGenerator> emitLoad)
        {
            var il = context.IL;
            var valueIsNotNullLabel = il.DefineLabel();
            var endOfMethodLabel = il.DefineLabel();

            var elemVar = il.DeclareLocal(elementType);                     // TElement elem

            emitLoad(il);                                                   // if (value)
            il.Brtrue(valueIsNotNullLabel);                                 //     goto valueIsNotNullLabel

            // value is null branch
            il.Ldloc(context.DataPointerVar);                               // *(int*) data = -1
            il.Ldc_I4(-1);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));        // data += sizeof(int)
            il.Br(endOfMethodLabel);                                        // goto endOfMethodLabel

            // value is not null branch
            il.MarkLabel(valueIsNotNullLabel);                              // label valueIsNotNullLabel
            il.Ldloc(context.DataPointerVar);                               // *(int*) data = (int)value.Count
            EmitLoadCount(il, emitLoad);
            il.Stind_I4();
            il.IncreasePointer(context.DataPointerVar, sizeof(int));        // data += sizeof(int)
            using (var loop = il.EmitForeachLoop(elementType, emitLoad))    // foreach (current in value)
            {
                loop.LoadCurrent();                                         //     elem = current
                il.Stloc(elemVar);
                elementCodec.EmitEncode(context, elemVar);                  //     encode(data, elem)
            }
            il.MarkLabel(endOfMethodLabel);                                 // label endOfMethodLabel
        }
Esempio n. 52
0
 public void EmitEncode(IEmittingContext context, Action<MyILGenerator> emitLoad)
 {
     var il = context.IL;
     context.EmitLoadManualCodecFor(type);
     il.Ldloca(context.DataPointerVar);
     emitLoad(il);
     il.Callvirt(ManualCodecMethods.Encode(type));
 }
Esempio n. 53
0
        public void EmitCalculateSize(IEmittingContext context, Action<MyILGenerator> emitLoad)
        {
            var il = context.IL;
            var valueIsNullOrEmptyLabel = il.DefineLabel();
            var valueHasElementsLabel = il.DefineLabel();
            var endOfMethodLabel = il.DefineLabel();

            var elemVar = il.DeclareLocal(elementType);                     // T elem

            emitLoad(il);                                                   // if (!value)
            il.Brfalse(valueIsNullOrEmptyLabel);                            //     goto valueIsNullOrEmptyLabel

            EmitLoadCount(il, emitLoad);                                    // if ((int)value.Length)
            il.Brtrue(valueHasElementsLabel);                               //     goto valueHasElementsLabel

            il.MarkLabel(valueIsNullOrEmptyLabel);                          // label valueIsNullOrEmptyLabel
            il.Ldc_I4(sizeof(int));                                         // stack_0 = sizeof(int)
            il.Br(endOfMethodLabel);                                        // goto endOfMethodLabel

            il.MarkLabel(valueHasElementsLabel);                            // label valueHasElementsLabel
            il.Ldc_I4(sizeof(int));                                         // sum = sizeof(int)
            using (var loop = il.EmitForeachLoop(elementType, emitLoad))    // foreach (current in value)
            {
                loop.LoadCurrent();                                         //     elem = current
                il.Stloc(elemVar);
                elementCodec.EmitCalculateSize(context, elemVar);           //     stack_1 = CalculateSize(elem)
                il.Add();                                                   //     stack_0 = stack_0 + stack_1
            }
            il.MarkLabel(endOfMethodLabel);                                 // label endOfMethodLabel
        }
Esempio n. 54
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;

            var endOfSubmethodLabel = il.DefineLabel();

            if (!doNotCheckBounds)
            {
                var canReadSizeLabel = il.DefineLabel();
                il.Ldloc(context.RemainingBytesVar);                        // if (remainingBytes >= sizeof(int))
                il.Ldc_I4(sizeof(int));                                     //     goto canReadSizeLabel
                il.Bge(canReadSizeLabel);
                il.ThrowUnexpectedEndException();                           // throw new InvalidDataException("...")
                il.MarkLabel(canReadSizeLabel);                             // label canReadSizeLabel
            }
            il.Ldloc(context.DataPointerVar);                               // stack_0 = *(int*) data
            il.Ldind_I4();
            var tempInteger = context.GetSharedVariable<int>("tempInteger");// var tempInteger = stack_0
            il.Stloc(tempInteger);
            il.IncreasePointer(context.DataPointerVar, sizeof(int));        // data += sizeof(int)
            il.DecreaseInteger(context.RemainingBytesVar, sizeof(int));     // remainingBytes -= sizeof(int)

            if (canBeNull)
            {
                var strIsNotNullLabel = il.DefineLabel();

                il.Ldloc(tempInteger);                                      // if (tempInteger != -1)
                il.Ldc_I4(-1);                                              //     goto strIsNotNullLabel
                il.Bne_Un(strIsNotNullLabel);

                // String is null branch
                il.Ldnull();                                                // stack_0 = null
                il.Br(endOfSubmethodLabel);                                 // goto endOfSubmethodLabel

                // String is not null branch
                il.MarkLabel(strIsNotNullLabel);                            // label strIsNotNullLabel
            }

            if (!doNotCheckBounds)
            {
                var canReadDataLabel = il.DefineLabel();
                il.Ldloc(context.RemainingBytesVar);                        // if (remainingBytes >= tempInteger)
                il.Ldloc(tempInteger);                                      //     goto canReadDataLabel
                il.Bge(canReadDataLabel);
                il.ThrowUnexpectedEndException();                           // throw new InvalidDataException("...")
                il.MarkLabel(canReadDataLabel);                             // label canReadDataLabel
            }
            il.Ldloc(context.DataPointerVar);                               // stack_0 = data
            il.Ldc_I4(0);                                                   // stack_1 = 0
            il.Ldloc(tempInteger);                                          // stack_2 = tempInteger >> 1
            il.Ldc_I4(1);
            il.Shr();
            il.Newobj(NewString);                                           // stack_0 = new string(stack_0, stack_1, stack_2)
            EmitParseFromString(il);                                        // stack_0 = Parse(stack_0)
            il.IncreasePointer(context.DataPointerVar, tempInteger);        // data += tempInteger
            il.DecreaseInteger(context.RemainingBytesVar, tempInteger);     // remainingBytes -= tempInteger
            il.MarkLabel(endOfSubmethodLabel);                              // label endOfSubmethodLabel
        }
 public void EmitEncode(IEmittingContext emittingContext)
 {
     codec.EmitEncode(emittingContext, emitLoad);
 }
Esempio n. 56
0
 public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
 {
     var il = context.IL;
     context.EmitLoadManualCodecFor(type);
     il.Ldloca(context.DataPointerVar);
     il.Ldloca(context.RemainingBytesVar);
     il.Ldc_I4(0);
     il.Callvirt(ManualCodecMethods.Decode(type));
 }
Esempio n. 57
0
        public void EmitDecode(IEmittingContext context, bool doNotCheckBounds)
        {
            var il = context.IL;

            var enoughBytesForLengthLabel = il.DefineLabel();
            var enoughBytesForDataLabel   = il.DefineLabel();
            var lengthIsMinusOneLabel     = il.DefineLabel();
            var lengthIsZeroLabel         = il.DefineLabel();
            var labelGroup            = new[] { lengthIsMinusOneLabel, lengthIsZeroLabel };
            var lengthIsPositiveLabel = il.DefineLabel();
            var endOfMethodLabel      = il.DefineLabel();

            if (!doNotCheckBounds)
            {
                il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeof(int))
                il.Ldc_I4(sizeof(int));                                 //     goto enoughBytesForLengthLabel
                il.Bge(enoughBytesForLengthLabel);

                // not enough bytes for length
                il.ThrowUnexpectedEndException();                       // throw new InvalidDataException(...)
            }

            // enough bytes for length
            il.MarkLabel(enoughBytesForLengthLabel);
            var lengthVar = context.GetSharedVariable <int>("length");    // var length = *(int*)data

            il.Ldloc(context.DataPointerVar);
            il.Ldind_I4();
            il.Stloc(lengthVar);
            il.IncreasePointer(context.DataPointerVar, sizeof(int));    // data += sizeof(int)
            il.DecreaseInteger(context.RemainingBytesVar, sizeof(int)); // remainingBytes -= sizeof(int)
            il.Ldloc(lengthVar);                                        // switch(length + 1)
            il.Ldc_I4(1);                                               //     case 0:  goto lengthIsMinusOneLabel
            il.Add();                                                   //     case 1:  goto lengthIsZeroLabel
            il.Switch(labelGroup);                                      //     default: goto lengthIsPositiveLabel
            il.Br(lengthIsPositiveLabel);

            // length is -1
            il.MarkLabel(lengthIsMinusOneLabel);
            il.Ldnull();                                                // stack_0 = null
            il.Br(endOfMethodLabel);                                    // goto endOfMethodLabel

            // length is 0
            il.MarkLabel(lengthIsZeroLabel);
            il.Ldc_I4(0);                                               // stack_0 = new T[0]
            il.Newarr(typeOfStruct);
            il.Br(endOfMethodLabel);                                    // goto endOfMethodLabel

            // length is positive
            il.MarkLabel(lengthIsPositiveLabel);
            var sizeVar = context.GetSharedVariable <int>("sizeInBytes");// var sizeInBytes = length * sizeOfStruct

            il.Ldloc(lengthVar);
            il.Ldc_I4(sizeOfStruct);
            il.Mul();
            il.Stloc(sizeVar);

            if (!doNotCheckBounds)
            {
                il.Ldloc(context.RemainingBytesVar);                    // if (remainingBytes >= sizeInBytes)
                il.Ldloc(sizeVar);                                      //     goto enoughBytesForDataLabel
                il.Bge(enoughBytesForDataLabel);

                // not enough bytes for data
                il.ThrowUnexpectedEndException();                       // throw new InvalidDataException(...)
            }

            // enough bytes for data
            il.MarkLabel(enoughBytesForDataLabel);
            var resultVar = context.GetSharedVariable(                   // var result = new T[length]
                typeOfStruct.MakeArrayType(), "arrayOf");

            il.Ldloc(lengthVar);
            il.Newarr(typeOfStruct);
            il.Stloc(resultVar);
            var pointerVar = il.PinArray(typeOfStruct, resultVar); // var pinned arrayPointer = pin(value)

            il.Ldloc(pointerVar);                                  // cpblk((byte*)arrayPointer, data, sizeInBytes)
            il.Conv_I();
            il.Ldloc(context.DataPointerVar);
            il.Ldloc(sizeVar);
            il.Cpblk();
            il.UnpinArray(pointerVar);                              // unpin(arrayPointer)
            il.IncreasePointer(context.DataPointerVar, sizeVar);    // data += size
            il.DecreaseInteger(context.RemainingBytesVar, sizeVar); // remainingBytes -= size
            il.Ldloc(resultVar);                                    // stack_0 = result
            il.MarkLabel(endOfMethodLabel);
        }
 public static void EmitEncode(this IEmittingCodec codec, IEmittingContext context, Action <MyILGenerator> emitLoadParent, MethodInfo propertyGetter)
 {
     codec.EmitEncode(context, il => { emitLoadParent(il); il.Call(propertyGetter); });
 }
Esempio n. 59
0
        private static void EmitEncodeDirect(IEmittingContext emittingContext, HandlerParameterCodec[] responseParameterCodecs, Type retvalType)
        {
            var il = emittingContext.IL;
            bool hasRetval = retvalType != typeof(void);

            if (hasRetval || responseParameterCodecs.Any())
            {
                HandlerRetvalCodec retvalCodec = null;

                if (hasRetval)
                {
                    retvalCodec = new HandlerRetvalCodec(emittingContext, retvalType);
                    retvalCodec.EmitStore();                                                // var ret = stack_0
                    retvalCodec.EmitCalculateSize();                                        // stack_0 = calculateSize(ret)
                }

                bool hasSizeOnStack = hasRetval;
                foreach (var codec in responseParameterCodecs)
                {
                    codec.EmitCalculateSize();                                              // stack_0 += calculateSize(param_i)
                    EmitAddIf(il, ref hasSizeOnStack);
                }

                var dataArrayVar = il.DeclareLocal(typeof(byte[]));                         // var dataArray = new byte[size of retval]
                il.Newarr(typeof(byte));
                il.Stloc(dataArrayVar);

                var pinnedVar = il.PinArray(typeof(byte), dataArrayVar);                    // var pinned dataPointer = pin(dataArrayVar)
                il.Ldloc(pinnedVar);                                                        // data = dataPointer
                il.Stloc(emittingContext.DataPointerVar);

                foreach (var codec in responseParameterCodecs)
                    codec.EmitEncode();                                                     // encode(data, param_i)

                if (hasRetval)
                    retvalCodec.EmitEncode();                                               // encode(data, ret)

                il.Ldloc(dataArrayVar);                                                     // stack_0 = dataArray
            }
            else
            {
                il.Ldc_I4(0);                                                               // stack_0 = new byte[0]
                il.Newarr(typeof(byte));
            }
        }
Esempio n. 60
0
 private static void EmitProcessAndEncodeAsyncVoid(IEmittingContext emittingContext)
 {
     var il = emittingContext.IL;
     il.Call(ToEmptyByteArrayTaskMethod);
 }