Beispiel #1
0
        private MethodDefinition GenerateGetPair(int bitmask, FieldDefinition tableField, ArrayType pairArray)
        {
            var getPair = new MethodDefinition(
                "GetPair",
                MethodAttributes.Public | MethodAttributes.HideBySig | MethodAttributes.Static,
                importer.Import(pairGenerator.Value.FieldType).Reference)
            {
                HasThis    = false,
                Parameters =
                {
                    new ParameterDefinition("type", ParameterAttributes.None, typeHelper.Type),
                },
                Body =
                {
                    InitLocals = true,
                    Variables  =
                    {
                        new VariableDefinition(pairArray),
                        new VariableDefinition(module.TypeSystem.IntPtr),
                    },
                },
            };
            var processor = getPair.Body.GetILProcessor();

            processor.Append(Instruction.Create(OpCodes.Ldsfld, tableField));                       // { Pair[][] }
            processor.Append(InstructionUtility.LdcI4(bitmask));                                    // { Pair[][], int32 }
            processor.Append(Instruction.Create(OpCodes.Ldarg_0));                                  // { Pair[][], int32, Type }
            processor.Append(Instruction.Create(OpCodes.Callvirt, systemObjectHelper.GetHashCode)); // { Pair[][], int32, int32 }
            processor.Append(Instruction.Create(OpCodes.And));                                      // { Pair[][], int32 }
            processor.Append(Instruction.Create(OpCodes.Ldelem_Ref));                               // { Pair[] }
            processor.Append(Instruction.Create(OpCodes.Dup));                                      // { Pair[], Pair[] }
            processor.Append(Instruction.Create(OpCodes.Stloc_0));                                  // { Pair[] }

            var condition = Instruction.Create(OpCodes.Ldloc_1);

            processor.Append(Instruction.Create(OpCodes.Brtrue_S, condition)); // { }

            ReturnDefaultValue(processor);

            var loopStart = Instruction.Create(OpCodes.Ldloc_0);

            processor.Append(loopStart);                                                                          // { Pair[] }
            processor.Append(Instruction.Create(OpCodes.Ldloc_1));                                                // { Pair[], native int }
            processor.Append(Instruction.Create(OpCodes.Ldelema, importer.Import(pairGenerator.Pair).Reference)); // { Pair& }
            processor.Append(Instruction.Create(OpCodes.Dup));                                                    // { Pair&, Pair& }
            processor.Append(Instruction.Create(OpCodes.Ldfld, importer.Import(pairGenerator.Key)));              // { Pair&, Type }
            processor.Append(Instruction.Create(OpCodes.Ldarg_0));                                                // { Pair&, Type, Type }
            var continuation = Instruction.Create(OpCodes.Pop);

            processor.Append(Instruction.Create(OpCodes.Bne_Un_S, continuation));                      // { Pair& }

            processor.Append(Instruction.Create(OpCodes.Ldfld, importer.Import(pairGenerator.Value))); // { uint64 }
            processor.Append(Instruction.Create(OpCodes.Ret));

            processor.Append(continuation);                                 // {  }
            processor.Append(Instruction.Create(OpCodes.Ldloc_1));          // { native int }
            processor.Append(InstructionUtility.LdcI4(1));                  // { native int, int32 }
            processor.Append(Instruction.Create(OpCodes.Conv_I));           // { native int, native int }
            processor.Append(Instruction.Create(OpCodes.Add));              // { native int }
            processor.Append(Instruction.Create(OpCodes.Stloc_1));          // { }

            processor.Append(condition);                                    // { native int }
            processor.Append(Instruction.Create(OpCodes.Ldloc_0));          // { native int, Pair[] }
            processor.Append(Instruction.Create(OpCodes.Ldlen));            // { native int, native int }
            processor.Append(Instruction.Create(OpCodes.Blt_S, loopStart)); // { }

            ReturnDefaultValue(processor);

            return(getPair);
        }
Beispiel #2
0
        private void LoadAppropriateValueFromFormatterInfo(ILProcessor processor, FormatterTableItemInfo formatterTableItemInfo)
        {
            foreach (var constructorArgument in formatterTableItemInfo.FormatterConstructorArguments)
            {
                void Load(CustomAttributeArgument argument)
                {
                    var value = argument.Value;

                    switch (argument.Type.FullName)
                    {
                    case "System.Char":
                        processor.Append(InstructionUtility.LdcI4((char)value));
                        break;

                    case "System.Boolean":
                        processor.Append(InstructionUtility.LdcBoolean((bool)value));
                        break;

                    case "System.Type":
                        processor.Append(Instruction.Create(OpCodes.Ldtoken, importer.Import((TypeReference)value).Reference));
                        processor.Append(Instruction.Create(OpCodes.Call, typeHelper.GetTypeFromHandle));
                        break;

                    case "System.Object":
                        processor.Append(Instruction.Create(OpCodes.Ldnull));
                        break;

                    case "System.Byte":
                        processor.Append(InstructionUtility.LdcI4((byte)value));
                        break;

                    case "System.SByte":
                        processor.Append(InstructionUtility.LdcI4((sbyte)value));
                        break;

                    case "System.Int16":
                        processor.Append(InstructionUtility.LdcI4((short)value));
                        break;

                    case "System.Int32":
                        processor.Append(InstructionUtility.LdcI4((int)value));
                        break;

                    case "System.Int64":
                    {
                        var(instruction0, instruction1) = InstructionUtility.LdcI8((long)value);
                        processor.Append(instruction0);
                        if (!(instruction1 is null))
                        {
                            processor.Append(instruction1);
                        }
                    }

                    break;

                    case "System.UInt16":
                        processor.Append(InstructionUtility.LdcI4((ushort)value));
                        break;

                    case "System.UInt32":
                        processor.Append(InstructionUtility.LdcI4((int)(uint)value));
                        break;

                    case "System.UInt64":
                    {
                        var(instruction0, instruction1) = InstructionUtility.LdcU8((ulong)value);
                        processor.Append(instruction0);
                        if (!(instruction1 is null))
                        {
                            processor.Append(instruction1);
                        }
                    }

                    break;

                    case "System.Single":
                        processor.Append(InstructionUtility.LdcR4((float)value));
                        break;

                    case "System.Double":
                        processor.Append(InstructionUtility.LdcR8((double)value));
                        break;

                    case "System.String":
                        processor.Append(InstructionUtility.LdStr((string)value));
                        break;

                    default: throw new MessagePackGeneratorResolveFailedException(argument.Type.FullName + " is not supported.");
                    }
                }

                Load(constructorArgument);
            }

            processor.Append(Instruction.Create(OpCodes.Newobj, customFormatterConstructorImporter.Import(formatterTableItemInfo))); // { Pair&, formatter }
        }