/// <summary> /// Adds a GetServiceHashCode method to a target type. /// </summary> /// <param name="targetType">The target type.</param> /// <param name="shouldBeVisible">A boolean flag that indicates whether or not the method should be public.</param> /// <returns>The GetServiceHashCode method.</returns> public MethodDefinition AddGetServiceHashMethodTo(TypeDefinition targetType, bool shouldBeVisible) { var options = new MethodBuilderOptions(); DefineOptions(targetType, shouldBeVisible, options); var module = targetType.Module; var methodBuilder = new MethodBuilder(); var method = methodBuilder.CreateMethod(options); var body = method.Body; var il = body.GetILProcessor (); var getHashCodeMethod = module.ImportMethod<object>("GetHashCode"); var hashVariable = EmitGetServiceTypeHashCode(module, body, il, getHashCodeMethod); // Calculate the hash code for the service name // if it isn't null il.Emit(OpCodes.Ldarg_1); il.Emit(OpCodes.Ldnull); il.Emit(OpCodes.Ceq); var skipNameHash = il.Create(OpCodes.Nop); il.Emit(OpCodes.Brtrue, skipNameHash); EmitGetServiceNameHashCode(il, getHashCodeMethod, hashVariable); il.Append(skipNameHash); il.Emit(OpCodes.Ldloc, hashVariable); il.Emit(OpCodes.Ret); return method; }
/// <summary> /// Sets the default method options for the GetServiceHashCode method. /// </summary> /// <param name="targetType">The targe type.</param> /// <param name="shouldBeVisible">A boolean flag that determines whether or not the method should be publicly visible.</param> /// <param name="options">The <see cref="MethodBuilderOptions"/> object to be modified.</param> private static void DefineOptions(TypeDefinition targetType, bool shouldBeVisible, MethodBuilderOptions options) { options.HostType = targetType; options.MethodName = "GetServiceHashCode"; options.ReturnType = typeof(int); options.SetMethodParameters(typeof(Type), typeof(string)); options.IsPublic = shouldBeVisible; options.IsStatic = true; }
/// <summary> /// Adds a method override for a particular <paramref name="targetMethod"/>. /// </summary> /// <param name="targetMethod">The target method.</param> /// <param name="hostType">The type that will host the new method.</param> /// <returns>The overridden method.</returns> public MethodDefinition AddOverrideFor(MethodInfo targetMethod, TypeDefinition hostType) { var module = hostType.Module; var options = new MethodBuilderOptions(); options.IsPublic = true; options.MethodName = targetMethod.Name; var parameterTypes = new List<System.Type>(); foreach (var param in targetMethod.GetParameters()) { parameterTypes.Add(param.ParameterType); } options.HostType = hostType; options.SetMethodParameters(parameterTypes.ToArray()); options.ReturnType = targetMethod.ReturnType; var builder = new MethodBuilder(); return builder.CreateMethod(options); }
/// <summary> /// Creates a method on the given host type. /// </summary> /// <param name="options">The method options object that describes the method to be created.</param> /// <returns>A method definition.</returns> public MethodDefinition CreateMethod(MethodBuilderOptions options) { var methodAttributes = MethodAttributes.HideBySig; if (options.IsPublic) { methodAttributes |= MethodAttributes.Public; } var instanceAttributes = MethodAttributes.NewSlot | MethodAttributes.Virtual; methodAttributes |= options.IsStatic ? MethodAttributes.Static : instanceAttributes; var targetType = options.HostType; var methodName = options.MethodName; var returnType = options.ReturnType; var parameterTypes = new List<System.Type>(options.ParameterTypes); var newMethod = targetType.DefineMethod(methodName, methodAttributes, returnType, parameterTypes.ToArray(), new System.Type[0]); newMethod.SetReturnType(options.ReturnType); return newMethod; }
/// <summary> /// Adds a method override for a particular <paramref name="targetMethod"/>. /// </summary> /// <param name="targetMethod">The target method.</param> /// <param name="hostType">The type that will host the new method.</param> /// <returns>The overridden method.</returns> public MethodDefinition AddOverrideFor(MethodInfo targetMethod, TypeDefinition hostType) { var module = hostType.Module; var options = new MethodBuilderOptions(); options.IsPublic = true; options.MethodName = targetMethod.Name; var parameterTypes = new List <Type>(); foreach (var param in targetMethod.GetParameters()) { parameterTypes.Add(param.ParameterType); } options.HostType = hostType; options.SetMethodParameters(parameterTypes.ToArray()); options.ReturnType = targetMethod.ReturnType; var builder = new MethodBuilder(); return(builder.CreateMethod(options)); }
/// <summary> /// Creates a method on the given host type. /// </summary> /// <param name="options">The method options object that describes the method to be created.</param> /// <returns>A method definition.</returns> public MethodDefinition CreateMethod(MethodBuilderOptions options) { var methodAttributes = MethodAttributes.HideBySig; if (options.IsPublic) { methodAttributes |= MethodAttributes.Public; } var instanceAttributes = MethodAttributes.NewSlot | MethodAttributes.Virtual; methodAttributes |= options.IsStatic ? MethodAttributes.Static : instanceAttributes; var targetType = options.HostType; var methodName = options.MethodName; var returnType = options.ReturnType; var parameterTypes = new List <System.Type>(options.ParameterTypes); var newMethod = targetType.DefineMethod(methodName, methodAttributes, returnType, parameterTypes.ToArray(), new System.Type[0]); newMethod.SetReturnType(options.ReturnType); return(newMethod); }
/// <summary> /// Adds a GetServiceHashCode method to a target type. /// </summary> /// <param name="targetType">The target type.</param> /// <param name="shouldBeVisible">A boolean flag that indicates whether or not the method should be public.</param> /// <returns>The GetServiceHashCode method.</returns> public MethodDefinition AddGetServiceHashMethodTo(TypeDefinition targetType, bool shouldBeVisible) { var options = new MethodBuilderOptions(); DefineOptions(targetType, shouldBeVisible, options); var module = targetType.Module; var methodBuilder = new MethodBuilder(); var method = methodBuilder.CreateMethod(options); var body = method.Body; var il = body.GetILProcessor(); var getHashCodeMethod = module.ImportMethod <object>("GetHashCode"); var hashVariable = EmitGetServiceTypeHashCode(module, body, il, getHashCodeMethod); // Calculate the hash code for the service name // if it isn't null il.Emit(OpCodes.Ldarg_1); il.Emit(OpCodes.Ldnull); il.Emit(OpCodes.Ceq); var skipNameHash = il.Create(OpCodes.Nop); il.Emit(OpCodes.Brtrue, skipNameHash); EmitGetServiceNameHashCode(il, getHashCodeMethod, hashVariable); il.Append(skipNameHash); il.Emit(OpCodes.Ldloc, hashVariable); il.Emit(OpCodes.Ret); return(method); }
/// <summary> /// Sets the default method options for the GetServiceHashCode method. /// </summary> /// <param name="targetType">The targe type.</param> /// <param name="shouldBeVisible">A boolean flag that determines whether or not the method should be publicly visible.</param> /// <param name="options">The <see cref="MethodBuilderOptions"/> object to be modified.</param> private static void DefineOptions(TypeDefinition targetType, bool shouldBeVisible, MethodBuilderOptions options) { options.HostType = targetType; options.MethodName = "GetServiceHashCode"; options.ReturnType = typeof(int); options.SetMethodParameters(typeof(System.Type), typeof(string)); options.IsPublic = shouldBeVisible; options.IsStatic = true; }