| File: Expression\IlGeneratorExtensions.cs | Web Access |
| Project: src\src\Microsoft.ML.Transforms\Microsoft.ML.Transforms.csproj (Microsoft.ML.Transforms) |
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. // See the LICENSE file in the project root for more information. using System; using System.Reflection; using System.Reflection.Emit; using Microsoft.ML.Runtime; #pragma warning disable MSML_GeneralName // The names are derived from .NET OpCode names. These do not adhere to .NET naming standards. namespace Microsoft.ML.Transforms { /// <summary> /// Helper extension methods for using ILGenerator. /// Rather than typing out something like: /// il.Emit(OpCodes.Ldarg_0); /// il.Emit(OpCodes.Ldarg_1); /// il.Emit(OpCodes.Ldc_I4, i); /// il.Emit(OpCodes.Ldelem_Ref); /// il.Emit(OpCodes.Stfld, literalFields[i]); /// You can do: /// il /// .Ldarg(0) /// .Ldarg(1) /// .Ldc_I4(i) /// .Ldelem_Ref() /// .Stfld(literalFields[i]); /// It also provides some type safety over the Emit methods by ensuring /// that you don't pass any args when using Add or that you only /// pass a Label when using Br. /// </summary> internal static class ILGeneratorExtensions { public static ILGenerator Add(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Add); return il; } public static ILGenerator Beq(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Beq, label); return il; } public static ILGenerator Bge(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Bge, label); return il; } public static ILGenerator Bge_Un(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Bge_Un, label); return il; } public static ILGenerator Bgt(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Bgt, label); return il; } public static ILGenerator Bgt_Un(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Bgt_Un, label); return il; } public static ILGenerator Ble(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Ble, label); return il; } public static ILGenerator Ble_Un(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Ble_Un, label); return il; } public static ILGenerator Blt(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Blt, label); return il; } public static ILGenerator Blt_Un(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Blt_Un, label); return il; } public static ILGenerator Bne_Un(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Bne_Un, label); return il; } public static ILGenerator Br(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Br, label); return il; } public static ILGenerator Brfalse(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Brfalse, label); return il; } public static ILGenerator Brtrue(this ILGenerator il, Label label) { Contracts.AssertValue(il); il.Emit(OpCodes.Brtrue, label); return il; } public static ILGenerator Call(this ILGenerator il, MethodInfo info) { Contracts.AssertValue(il); Contracts.AssertValue(info); Contracts.Assert(!info.IsVirtual); il.Emit(OpCodes.Call, info); return il; } public static ILGenerator Ceq(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Ceq); return il; } public static ILGenerator Cgt(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Cgt); return il; } public static ILGenerator Cgt_Un(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Cgt_Un); return il; } public static ILGenerator Clt(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Clt); return il; } public static ILGenerator Clt_Un(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Clt_Un); return il; } public static ILGenerator Conv_I8(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Conv_I8); return il; } public static ILGenerator Conv_R4(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Conv_R4); return il; } public static ILGenerator Conv_R8(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Conv_R8); return il; } public static ILGenerator Div(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Div); return il; } public static ILGenerator Dup(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Dup); return il; } public static ILGenerator Ldarg(this ILGenerator il, int arg) { Contracts.AssertValue(il); Contracts.Assert(0 <= arg && arg <= short.MaxValue); switch (arg) { case 0: il.Emit(OpCodes.Ldarg_0); break; case 1: il.Emit(OpCodes.Ldarg_1); break; case 2: il.Emit(OpCodes.Ldarg_2); break; case 3: il.Emit(OpCodes.Ldarg_3); break; default: if (arg <= byte.MaxValue) il.Emit(OpCodes.Ldarg_S, (byte)arg); else il.Emit(OpCodes.Ldarg, (short)arg); break; } return il; } public static ILGenerator Ldc_I4(this ILGenerator il, int arg) { Contracts.AssertValue(il); switch (arg) { case -1: il.Emit(OpCodes.Ldc_I4_M1); break; case 0: il.Emit(OpCodes.Ldc_I4_0); break; case 1: il.Emit(OpCodes.Ldc_I4_1); break; case 2: il.Emit(OpCodes.Ldc_I4_2); break; case 3: il.Emit(OpCodes.Ldc_I4_3); break; case 4: il.Emit(OpCodes.Ldc_I4_4); break; case 5: il.Emit(OpCodes.Ldc_I4_5); break; case 6: il.Emit(OpCodes.Ldc_I4_6); break; case 7: il.Emit(OpCodes.Ldc_I4_7); break; case 8: il.Emit(OpCodes.Ldc_I4_8); break; default: // REVIEW: Docs say use ILGenerator.Emit(OpCode, byte) even though the value is signed if (sbyte.MinValue <= arg && arg <= sbyte.MaxValue) il.Emit(OpCodes.Ldc_I4_S, (byte)arg); else il.Emit(OpCodes.Ldc_I4, arg); break; } return il; } public static ILGenerator Ldc_I8(this ILGenerator il, long arg) { Contracts.AssertValue(il); il.Emit(OpCodes.Ldc_I8, arg); return il; } public static ILGenerator Ldc_R4(this ILGenerator il, float arg) { Contracts.AssertValue(il); il.Emit(OpCodes.Ldc_R4, arg); return il; } public static ILGenerator Ldc_R8(this ILGenerator il, double arg) { Contracts.AssertValue(il); il.Emit(OpCodes.Ldc_R8, arg); return il; } public static ILGenerator Ldloc(this ILGenerator il, LocalBuilder builder) { Contracts.AssertValue(il); Contracts.AssertValue(builder); il.Emit(OpCodes.Ldloc, builder); return il; } public static ILGenerator Ldstr(this ILGenerator il, string str) { Contracts.AssertValue(il); Contracts.AssertValue(str); il.Emit(OpCodes.Ldstr, str); return il; } public static ILGenerator Mul(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Mul); return il; } public static ILGenerator Mul_Ovf(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Mul_Ovf); return il; } public static ILGenerator Neg(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Neg); return il; } public static ILGenerator Newarr(this ILGenerator il, Type type) { Contracts.AssertValue(il); Contracts.AssertValue(type); il.Emit(OpCodes.Newarr, type); return il; } public static ILGenerator Pop(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Pop); return il; } public static ILGenerator Rem(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Rem); return il; } public static ILGenerator Ret(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Ret); return il; } public static ILGenerator Stelem(this ILGenerator il, Type type) { Contracts.AssertValue(il); Contracts.AssertValue(type); il.Emit(OpCodes.Stelem, type); return il; } public static ILGenerator Stloc(this ILGenerator il, LocalBuilder builder) { Contracts.AssertValue(il); Contracts.AssertValue(builder); il.Emit(OpCodes.Stloc, builder); return il; } public static ILGenerator Sub(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Sub); return il; } public static ILGenerator Xor(this ILGenerator il) { Contracts.AssertValue(il); il.Emit(OpCodes.Xor); return il; } } } #pragma warning restore MSML_GeneralName