private static void GenerateArray(ModuleDefinition mainModule, MethodDefinition method, TypeReference TFunc, GenericParameter T, TypeReference baseEnumerable) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, baseEnumerable)); method.Parameters.Add(new ParameterDefinition("func", ParameterAttributes.None, TFunc)); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(mainModule.TypeSystem.Int32)); var loopStart = Instruction.Create(OpCodes.Ldloc_0); var next = Instruction.Create(OpCodes.Ldloc_0); var retVal = InstructionUtility.LoadConstant(IsAll); body.GetILProcessor() .ArgumentNullCheck(0, 1, loopStart) .LdArg(0) .LdLen() .ConvI4() .BgeS(retVal) .LdArg(1) .LdArg(0) .LdLoc(0) .LdElemAny(T) .CallVirtual(TFunc.FindMethod("Invoke", 1)) .BrBoolS(next, IsAll) .LdC(!IsAll) .Ret() .Add(next) .LdC(1) .Add() .StLoc(0) .BrS(loopStart) .Add(retVal) .Ret(); }
private static void GenerateNativeArray(MethodDefinition method, TypeReference baseEnumerable, GenericParameter T) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.In, new ByReferenceType(baseEnumerable)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("index", ParameterAttributes.None, method.Module.TypeSystem.Int32)); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(T))); var fail = InstructionUtility.LoadConstant(false); var notMinus = Instruction.Create(OpCodes.Ldarg_0); method.Body.GetILProcessor() .LdArg(1) .LdC(0) .BgeS(notMinus) .Add(fail) .Ret() .Add(notMinus) .Call(baseEnumerable.FindMethod("get_Length")) .LdArg(1) .BleS(fail) .Add(Instruction.Create(OpCodes.Nop)) .LdArg(2) .LdArg(0) .LdArg(1) .Call(baseEnumerable.FindMethod("get_Item")) .StObj(T) .LdC(true) .Ret(); }
private static void GenerateArray(MethodDefinition method, TypeReference enumerable, TypeReference T, TypeReference Func) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, enumerable)); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(T))); method.Parameters.Add(new ParameterDefinition("func", ParameterAttributes.None, Func)); var loopStart = Instruction.Create(OpCodes.Ldarg_0); var @return = Instruction.Create(OpCodes.Ldloc_2); var fail = InstructionUtility.LoadConstant(false); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.IntPtr)); body.Variables.Add(new VariableDefinition(new ByReferenceType(T))); body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Boolean)); body.GetILProcessor() .ArgumentNullCheck(0, 2, Instruction.Create(OpCodes.Ldarg_0)) .LdLen() .BrTrueS(loopStart) .LdC(false) .Ret() .Add(loopStart) .LdLen() .LdLoc(0) .BleS(@return) .LdArg(2) .LdArg(0) .LdLoc(0) .Dup() .LdC(1) .Add() .StLoc(0) .LdElemA(T) .Dup() .StLoc(1) .LdObj(T) .CallVirtual(Func.FindMethod("Invoke")) .BrFalseS(loopStart) .LdLoc(2) .BrTrueS(fail) .LdArg(1) .LdLoc(1) .CpObj(T) .LdC(true) .StLoc(2) .BrS(loopStart) .Add(fail) .Ret() .Add(@return) .Ret(); }
private static void GenerateArray(MethodDefinition method, TypeReference enumerable, TypeReference T) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, enumerable)); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(T))); var fail = InstructionUtility.LoadConstant(false); method.Body.GetILProcessor() .ArgumentNullCheck(0, Instruction.Create(OpCodes.Ldarg_0)) .LdLen() .LdC(1) .BneS(fail) .LdArg(1) .LdArg(0) .LdC(0) .LdElemA(T) .CpObj(T) .LdC(true) .Ret() .Add(fail) .Ret(); }
private static void GenerateNativeArray(MethodDefinition method, TypeReference enumerable, GenericParameter T, TypeReference TOperator, GenericInstanceType equatable) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.In, new ByReferenceType(enumerable)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.In, new ByReferenceType(T)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("func", ParameterAttributes.In, new ByReferenceType(TOperator)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Int32)); body.Variables.Add(new VariableDefinition(T)); var loopStart = Instruction.Create(OpCodes.Ldarg_2); var @return = InstructionUtility.LoadConstant(true); var getLength = enumerable.FindMethod("get_Length"); body.GetILProcessor() .LdArg(0) .Call(getLength) .BrTrueS(loopStart) .LdC(false) .Ret() .Add(loopStart) .LdArg(1) .LdArg(0) .LdLoc(0) .Call(enumerable.FindMethod("get_Item")) .StLoc(1) .LdLocA(1) .Constrained(TOperator) .CallVirtual(equatable.FindMethod("Calc")) .BrTrueS(@return) .LdLoc(0) .LdC(1) .Add() .Dup() .StLoc(0) .LdArg(0) .Call(getLength) .BltS(loopStart) .LdC(false) .Ret() .Add(@return) .Ret(); }
private static void GenerateNativeArray(MethodDefinition method, TypeReference enumerable, GenericParameter T) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.In, new ByReferenceType(enumerable)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(T))); var fail = InstructionUtility.LoadConstant(false); method.Body.GetILProcessor() .LdArg(0) .Call(enumerable.FindMethod("get_Length")) .LdC(1) .BneS(fail) .LdArg(1) .LdArg(0) .LdC(0) .Call(enumerable.FindMethod("get_Item")) .StObj(T) .LdC(true) .Ret() .Add(fail) .Ret(); }
public static void GenerateSum_Array(this TypeReference returnType, MethodDefinition method, TypeReference baseEnumerable) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, baseEnumerable)); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(returnType)); body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Int32)); var condition = Instruction.Create(OpCodes.Ldloc_1); var loopStart = Instruction.Create(OpCodes.Ldloc_0); body.GetILProcessor() .ArgumentNullCheck(0, InstructionUtility.LoadConstant(0)) .StLoc(1) .BrS(condition) .Add(loopStart) .LdArg(0) .LdLoc(1) .LdElem(returnType) .Add() .StLoc(0) .LdLoc(1) .LdC(1) .Add() .StLoc(1) .Add(condition) .LdArg(0) .LdLen() .ConvI4() .BltS(loopStart) .LdLoc(0) .Ret(); }
private static void GenerateArray(MethodDefinition method, TypeReference baseEnumerable, GenericParameter T) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, baseEnumerable)); method.Parameters.Add(new ParameterDefinition("index", ParameterAttributes.None, method.Module.TypeSystem.Int64)); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(T))); var fail = InstructionUtility.LoadConstant(false); method.Body.GetILProcessor() .ArgumentNullCheck(0, Instruction.Create(OpCodes.Ldarg_1)) .LdC(0L) .BltS(fail) .LdArg(0) .LdLen() .ConvI8() .LdArg(1) .BleS(fail) .LdArg(2) .LdArg(0) .LdArg(1) .LdElemA(T) .CpObj(T) .LdC(true) .Ret() .Add(fail) .Ret(); }
private static void GenerateNativeArray(MethodDefinition method, TypeReference baseEnumerable, TypeReference enumerable, GenericParameter T, TypeReference IEquatable) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, baseEnumerable)); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(method.Module.TypeSystem.Int32))); method.Parameters.Add(new ParameterDefinition("comparer", ParameterAttributes.None, T)); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Int32)); body.Variables.Add(new VariableDefinition(new ByReferenceType(T))); body.Variables.Add(new VariableDefinition(enumerable)); var loopStart = Instruction.Create(OpCodes.Ldloca_S, body.Variables[2]); var success = Instruction.Create(OpCodes.Ldarg_1); var fail = InstructionUtility.LoadConstant(false); var getLength = baseEnumerable.FindMethod("get_Length"); method.Body.GetILProcessor() .LdArgA(0) .Call(getLength) .BrFalseS(fail) .LdLocA(2) .LdArg(0) .Call(enumerable.FindMethod(".ctor")) .Add(loopStart) .LdLoc(0) .Call(enumerable.FindMethod("get_Item")) .Dup() .StLoc(1) .LdArg(2) .Constrained(T) .CallVirtual(IEquatable.FindMethod("Equals")) .BrTrueS(success) .LdLoc(0) .LdC(1) .Add() .Dup() .StLoc(0) .LdArgA(0) .Call(getLength) .ConvI8() .BltS(loopStart) .Add(fail) .Ret() .Add(success) .LdLoc(0) .StObj(method.Module.TypeSystem.Int32) .LdC(true) .Ret(); }
private static void GenerateNativeArray(MethodDefinition method, TypeReference baseEnumerable, TypeReference enumerable, GenericParameter T, TypeReference TPredicate) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, baseEnumerable)); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(T))); method.Parameters.Add(new ParameterDefinition("predicate", ParameterAttributes.None, TPredicate)); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Int64)); body.Variables.Add(new VariableDefinition(new ByReferenceType(T))); body.Variables.Add(new VariableDefinition(enumerable)); var loopStart = Instruction.Create(OpCodes.Ldarg_2); var success = Instruction.Create(OpCodes.Ldarg_1); var fail = InstructionUtility.LoadConstant(false); var getLength = baseEnumerable.FindMethod("get_Length"); method.Body.GetILProcessor() .ArgumentNullCheck(2, Instruction.Create(OpCodes.Ldarg_0)) .Call(getLength) .BrFalseS(fail) .LdLocA(2) .LdArg(0) .Call(enumerable.FindMethod(".ctor")) .LdArgA(0) .Call(getLength) .ConvI8() .StLoc(0) .Add(loopStart) .LdLocA(2) .LdLoc(0) .LdC(1) .Sub() .Dup() .StLoc(0) .Call(enumerable.FindMethod("get_Item")) .Dup() .StLoc(1) .CallVirtual(TPredicate.FindMethod("Invoke")) .BrTrueS(success) .LdLoc(0) .BrTrueS(loopStart) .Add(fail) .Ret() .Add(success) .LdLoc(1) .CpObj(T) .LdC(true) .Ret(); }
private static void GenerateArray(MethodDefinition method, TypeReference baseEnumerable, GenericParameter T, TypeReference TPredicate, TypeReference predicate) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, baseEnumerable)); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(T))); method.Parameters.Add(new ParameterDefinition("TPredicate", ParameterAttributes.In, new ByReferenceType(TPredicate)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); var loopStart = Instruction.Create(OpCodes.Ldarg_0); var success = Instruction.Create(OpCodes.Ldarg_1); var fail = InstructionUtility.LoadConstant(false); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.IntPtr)); body.Variables.Add(new VariableDefinition(new ByReferenceType(T))); method.Body.GetILProcessor() .ArgumentNullCheck(0, Instruction.Create(OpCodes.Ldarg_0)) .LdLen() .BrFalseS(fail) .LdArg(0) .LdLen() .StLoc(0) .Add(loopStart) .LdLoc(0) .LdC(1) .Sub() .Dup() .StLoc(0) .LdElemA(T) .StLoc(1) .LdArg(2) .LdLoc(1) .Constrained(TPredicate) .CallVirtual(predicate.FindMethod("Calc")) .BrTrueS(success) .LdLoc(0) .BrTrueS(loopStart) .Add(fail) .Ret() .Add(success) .LdLoc(1) .CpObj(T) .LdC(true) .Ret(); }
private static void GenerateNormalCanFastCount(MethodDefinition method, GenericParameter T, TypeReference enumerable, TypeReference enumerator, ParameterDefinition paramIndex) { var body = method.Body; var enumeratorVariable = new VariableDefinition(enumerator); body.Variables.Add(enumeratorVariable); var loopStart = Instruction.Create(OpCodes.Ldloca_S, enumeratorVariable); var @return = Instruction.Create(OpCodes.Ldarg_2); var fail = InstructionUtility.LoadConstant(false); var dispose = enumerator.FindMethod("Dispose", 0); body.GetILProcessor() .LdArg(1) .LdC(0L) .BltS(fail) .LdArg(1) .LdArg(0) .Call(enumerable.FindMethod("LongCount")) .BgeS(fail) .LdArg(0) .Call(enumerable.FindMethod("GetEnumerator", 0)) .StLoc(0) .Add(loopStart) .Call(enumerator.FindMethod("MoveNext")) .Pop() .LdArg(1) .LdC(0L) .BeqS(@return) .LdArg(1) .LdC(1L) .Sub() .StArgS(paramIndex) .BrS(loopStart) .Add(Instruction.Create(OpCodes.Nop)) .Add(@return) .LdLocA(0) .Call(enumerator.FindMethod("get_Current")) .LdObj(T) .StObj(T) .LdLocA(0) .Call(dispose) .LdC(true) .Ret() .Add(fail) .Ret(); }
private static void GenerateNormal(MethodDefinition method, GenericParameter T, TypeReference enumerable, TypeReference enumerator, TypeReference TOperator, GenericInstanceType equatable) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.In, new ByReferenceType(enumerable)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.In, new ByReferenceType(T)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("func", ParameterAttributes.In, new ByReferenceType(TOperator)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); var body = method.Body; body.InitLocals = true; var enumeratorVariable = new VariableDefinition(enumerator); body.Variables.Add(enumeratorVariable); body.Variables.Add(new VariableDefinition(T)); var loopStart = Instruction.Create(OpCodes.Ldloca_S, enumeratorVariable); var fail = InstructionUtility.LoadConstant(false); var dispose = Instruction.Create(OpCodes.Ldloca_S, enumeratorVariable); body.GetILProcessor() .LdArg(0) .Call(enumerable.FindMethod("GetEnumerator", 0)) .StLoc(0) .Add(loopStart) .LdLocA(1) .Call(enumerator.FindMethod("TryMoveNext")) .BrFalseS(fail) .LdArg(2) .LdArg(1) .LdLocA(1) .Constrained(TOperator) .CallVirtual(equatable.FindMethod("Calc")) .BrFalseS(loopStart) .LdC(true) .BrS(dispose) .Add(fail) .Add(dispose) .Call(enumerator.FindMethod("Dispose", 0)) .Ret(); }
public static void SerializeFixedSizeBuffer(ILProcessor processor, ParameterDefinition valueParam, FieldReference fixedFieldImportedReference, ModuleDefinition module, MessagePackWriterHelper writer, FixedSizeBufferElementType elementType, int count, ref VariableDefinition notPinnedVariable) #endif { var writingElement = writer.WriteMessagePackPrimitive(GetType(module, elementType)); var ldInd = LdInd(elementType); var stride = SizeOf(elementType); processor.Append(Instruction.Create(OpCodes.Ldarg_1)); // { writer } processor.Append(InstructionUtility.LdcI4(count)); // { writer, int32 } processor.Append(Instruction.Create(OpCodes.Call, writer.WriteArrayHeaderInt)); // { } processor.Append(Instruction.Create(OpCodes.Ldarg_1)); // { writer } processor.Append(Instruction.Create(OpCodes.Ldarga_S, valueParam)); // { writer, value& } processor.Append(Instruction.Create(OpCodes.Ldflda, fixedFieldImportedReference)); // { writer, field& } processor.Append(Instruction.Create(OpCodes.Conv_U)); // { writer, native uint } if (count == 1) { processor.Append(Instruction.Create(ldInd)); // { writer, binary } processor.Append(Instruction.Create(OpCodes.Call, writingElement)); // { } } else { if (notPinnedVariable is null) { notPinnedVariable = new VariableDefinition(module.TypeSystem.IntPtr); processor.Body.Variables.Add(notPinnedVariable); } processor.Append(Instruction.Create(OpCodes.Dup)); // { writer, native uint, native uint } processor.Append(InstructionUtility.Store(notPinnedVariable)); // { writer, native uint } processor.Append(Instruction.Create(ldInd)); // { writer, binary } processor.Append(Instruction.Create(OpCodes.Call, writingElement)); // { } for (var i = 1; i < count; i++) { processor.Append(Instruction.Create(OpCodes.Ldarg_1)); // { writer } processor.Append(InstructionUtility.Load(notPinnedVariable)); // { writer, native uint } processor.Append(InstructionUtility.LdcI4(stride)); // { writer, native uint, int32 } processor.Append(Instruction.Create(OpCodes.Add)); // { writer, native uint } if (i != count - 1) { processor.Append(Instruction.Create(OpCodes.Dup)); // { writer, native int, native int } processor.Append(InstructionUtility.Store(notPinnedVariable)); // { writer, native int } } processor.Append(Instruction.Create(ldInd)); // { writer, binary } processor.Append(Instruction.Create(OpCodes.Call, writingElement)); // { } } } }
private static void GenerateArray(MethodDefinition method, TypeReference enumerable, GenericParameter T, TypeReference TRefFunc) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.None, enumerable)); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.In, new ByReferenceType(T)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("func", ParameterAttributes.None, TRefFunc)); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.IntPtr)); var loopStart = Instruction.Create(OpCodes.Ldarg_2); var @return = InstructionUtility.LoadConstant(true); body.GetILProcessor() .ArgumentNullCheck(0, 2, Instruction.Create(OpCodes.Ldarg_0)) .LdLen() .BrTrueS(loopStart) .LdC(false) .Ret() .Add(loopStart) .LdArg(1) .LdArg(0) .LdLoc(0) .LdElemA(T) .CallVirtual(TRefFunc.FindMethod("Invoke")) .BrTrueS(@return) .LdLoc(0) .LdC(1) .Add() .Dup() .StLoc(0) .LdArg(0) .LdLen() .BltS(loopStart) .LdC(false) .Ret() .Add(@return) .Ret(); }
private static void GenerateCanIndexAccess(MethodDefinition method, TypeReference enumerable, TypeReference TPredicate, TypeReference T) { var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Int64)); var fail = InstructionUtility.LoadConstant(false); var success = Instruction.Create(OpCodes.Ldarg_1); var loopStart = Instruction.Create(OpCodes.Ldarg_2); body.GetILProcessor() .ArgumentNullCheck(2, Instruction.Create(OpCodes.Ldarg_0)) .Call(enumerable.FindMethod("LongCount", 0)) .Dup() .StLoc(0) .BrFalseS(fail) .Add(loopStart) .LdArg(0) .LdLoc(0) .LdC(1) .Sub() .Dup() .StLoc(0) .Call(enumerable.FindMethod("get_Item")) .LdObj(T) .CallVirtual(TPredicate.FindMethod("Invoke")) .BrTrueS(success) .LdLoc(0) .BrTrueS(loopStart) .Add(fail) .Ret() .Add(success) .LdArg(0) .LdLoc(0) .Call(enumerable.FindMethod("get_Item")) .CpObj(T) .LdC(true) .Ret(); }
private static void GenerateNativeArray(MethodDefinition method, TypeReference TFunc, TypeReference baseEnumerable) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.In, new ByReferenceType(baseEnumerable)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("func", ParameterAttributes.None, TFunc)); var body = method.Body; body.InitLocals = true; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Int32)); var loopStart = Instruction.Create(OpCodes.Ldloc_0); var next = Instruction.Create(OpCodes.Ldloc_0); var retVal = InstructionUtility.LoadConstant(IsAll); body.GetILProcessor() .ArgumentNullCheck(1, loopStart) .LdArg(0) .Call(baseEnumerable.FindMethod("get_Length")) .BgeS(retVal) .LdArg(1) .LdArg(0) .LdLoc(0) .Call(baseEnumerable.FindMethod("get_Item", 1)) .CallVirtual(TFunc.FindMethod("Invoke", 1)) .BrBoolS(next, IsAll) .LdC(!IsAll) .Ret() .Add(next) .LdC(1) .Add() .StLoc(0) .BrS(loopStart) .Add(retVal) .Ret(); }
private void GenerateGeneric(TypeDefinition @static, ModuleDefinition mainModule) { var method = new MethodDefinition(Api.Name, Helper.StaticMethodAttributes, mainModule.TypeSystem.Boolean) { DeclaringType = @static, AggressiveInlining = true, CustomAttributes = { Helper.ExtensionAttribute } }; @static.Methods.Add(method); var(T, TEnumerator, TEnumerable) = method.Define3GenericParameters(); var IEquatable = new GenericInstanceType(mainModule.GetType("UniNativeLinq", "IRefFunc`3")) { GenericArguments = { T, T, mainModule.TypeSystem.Boolean } }; var TOperator = new GenericParameter("TOperator", method) { HasNotNullableValueTypeConstraint = true, Constraints = { IEquatable } }; method.GenericParameters.Add(TOperator); method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.In, new ByReferenceType(TEnumerable)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.In, new ByReferenceType(T)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("func", ParameterAttributes.In, new ByReferenceType(TOperator)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); var body = method.Body; body.InitLocals = true; var enumeratorVariable = new VariableDefinition(TEnumerator); body.Variables.Add(enumeratorVariable); body.Variables.Add(new VariableDefinition(T)); var loopStart = Instruction.Create(OpCodes.Ldloca_S, enumeratorVariable); var fail = InstructionUtility.LoadConstant(false); var dispose = Instruction.Create(OpCodes.Ldloca_S, enumeratorVariable); body.GetILProcessor() .LdArg(0) .GetEnumeratorEnumerable(TEnumerable) .StLoc(0) .Add(loopStart) .LdLocA(1) .TryMoveNextEnumerator(TEnumerator) .BrFalseS(fail) .LdArg(2) .LdArg(1) .LdLocA(1) .Constrained(TOperator) .CallVirtual(IEquatable.FindMethod("Calc")) .BrFalseS(loopStart) .LdC(true) .BrS(dispose) .Add(fail) .Add(dispose) .DisposeEnumerator(TEnumerator) .Ret(); }
private static void GenerateNativeArray(MethodDefinition method, TypeReference enumerable, GenericParameter T, GenericInstanceType Func) { method.Parameters.Add(new ParameterDefinition("@this", ParameterAttributes.In, new ByReferenceType(enumerable)) { CustomAttributes = { Helper.GetSystemRuntimeCompilerServicesIsReadOnlyAttributeTypeReference() } }); method.Parameters.Add(new ParameterDefinition("value", ParameterAttributes.Out, new ByReferenceType(T))); method.Parameters.Add(new ParameterDefinition("func", ParameterAttributes.None, Func)); var loopStart = Instruction.Create(OpCodes.Ldarg_0); var @return = Instruction.Create(OpCodes.Ldloc_2); var fail = InstructionUtility.LoadConstant(false); var body = method.Body; body.InitLocals = true; body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Int32)); body.Variables.Add(new VariableDefinition(T)); body.Variables.Add(new VariableDefinition(method.Module.TypeSystem.Boolean)); var getLength = enumerable.FindMethod("get_Length"); body.GetILProcessor() .ArgumentNullCheck(2, Instruction.Create(OpCodes.Ldarg_0)) .Call(getLength) .BrTrueS(loopStart) .LdC(false) .Ret() .Add(loopStart) .Call(getLength) .LdLoc(0) .BleS(@return) .LdArg(2) .LdArg(0) .LdLoc(0) .Dup() .LdC(1) .Add() .StLoc(0) .Call(enumerable.FindMethod("get_Item")) .Dup() .StLoc(1) .CallVirtual(Func.FindMethod("Invoke")) .BrFalseS(loopStart) .LdLoc(2) .BrTrueS(fail) .LdArg(1) .LdLocA(1) .CpObj(T) .LdC(true) .StLoc(2) .BrS(loopStart) .Add(fail) .Ret() .Add(@return) .Ret(); }
public static Instruction[] DeserializeFixedSizeBuffer(VariableDefinition targetVariable, FieldDefinition fixedField, ModuleDefinition module, MessagePackReaderHelper reader, ModuleImporter importer, SystemInvalidOperationExceptionHelper invalidOperationExceptionHelper, FixedSizeBufferElementType elementType, int count) { var same = Instruction.Create(OpCodes.Ldloca_S, targetVariable); var read = reader.ReadMessagePackPrimitive(GetType(module, elementType)); var stride = SizeOf(elementType); switch (count) { case 1: return(new[] { Instruction.Create(OpCodes.Ldarg_1), Instruction.Create(OpCodes.Call, reader.ReadArrayHeader), InstructionUtility.LdcI4(count), Instruction.Create(OpCodes.Beq_S, same), Instruction.Create(OpCodes.Ldstr, "Fixed size buffer field should have " + count.ToString(CultureInfo.InvariantCulture) + " element(s)."), Instruction.Create(OpCodes.Newobj, invalidOperationExceptionHelper.Ctor), Instruction.Create(OpCodes.Throw), same, Instruction.Create(OpCodes.Ldflda, importer.Import(fixedField)), Instruction.Create(OpCodes.Ldarg_1), Instruction.Create(OpCodes.Call, read), Instruction.Create(StInd(elementType)), }); case 2: return(new[] { Instruction.Create(OpCodes.Ldarg_1), Instruction.Create(OpCodes.Call, reader.ReadArrayHeader), InstructionUtility.LdcI4(count), Instruction.Create(OpCodes.Beq_S, same), Instruction.Create(OpCodes.Ldstr, "Fixed size buffer field should have " + count.ToString(CultureInfo.InvariantCulture) + " element(s)."), Instruction.Create(OpCodes.Newobj, invalidOperationExceptionHelper.Ctor), Instruction.Create(OpCodes.Throw), same, Instruction.Create(OpCodes.Ldflda, importer.Import(fixedField)), Instruction.Create(OpCodes.Dup), Instruction.Create(OpCodes.Ldarg_1), Instruction.Create(OpCodes.Call, read), Instruction.Create(StInd(elementType)), InstructionUtility.LdcI4(stride), Instruction.Create(OpCodes.Add), Instruction.Create(OpCodes.Ldarg_1), Instruction.Create(OpCodes.Call, read), Instruction.Create(StInd(elementType)), }); default: { var answer = new Instruction[6 + (6 * count)]; answer[0] = Instruction.Create(OpCodes.Ldarg_1); answer[1] = Instruction.Create(OpCodes.Call, reader.ReadArrayHeader); answer[2] = InstructionUtility.LdcI4(count); answer[3] = Instruction.Create(OpCodes.Beq_S, same); answer[4] = Instruction.Create(OpCodes.Ldstr, "Fixed size buffer field should have " + count.ToString(CultureInfo.InvariantCulture) + " element(s). field : " + fixedField.FullName); answer[5] = Instruction.Create(OpCodes.Newobj, invalidOperationExceptionHelper.Ctor); answer[6] = Instruction.Create(OpCodes.Throw); answer[7] = same; answer[8] = Instruction.Create(OpCodes.Ldflda, importer.Import(fixedField)); answer[9] = Instruction.Create(OpCodes.Dup); answer[10] = Instruction.Create(OpCodes.Ldarg_1); answer[11] = Instruction.Create(OpCodes.Call, read); answer[12] = Instruction.Create(StInd(elementType)); for (var i = 1; i < count - 1; i++) { var start = 7 + (i * 6); answer[start++] = Instruction.Create(OpCodes.Dup); answer[start++] = InstructionUtility.LdcI4(stride); answer[start++] = Instruction.Create(OpCodes.Add); answer[start++] = Instruction.Create(OpCodes.Ldarg_1); answer[start++] = Instruction.Create(OpCodes.Call, read); answer[start] = Instruction.Create(StInd(elementType)); } answer[1 + (6 * count)] = InstructionUtility.LdcI4(stride); answer[2 + (6 * count)] = Instruction.Create(OpCodes.Add); answer[3 + (6 * count)] = Instruction.Create(OpCodes.Ldarg_1); answer[4 + (6 * count)] = Instruction.Create(OpCodes.Call, read); answer[5 + (6 * count)] = Instruction.Create(StInd(elementType)); return(answer); } } }