/// <summary> /// Adds a prolog to the given method body. /// </summary> /// <param name="IL">The <see cref="CilWorker"/> that points to the given method body.</param> public void AddProlog(CilWorker IL) { MethodDefinition method = IL.GetMethod(); _surroundingImplementation = method.AddLocal <IAroundInvoke>(); _surroundingClassImplementation = method.AddLocal <IAroundInvoke>(); Instruction skipProlog = IL.Create(OpCodes.Nop); TypeDefinition declaringType = method.DeclaringType; ModuleDefinition module = declaringType.Module; TypeReference modifiableType = module.ImportType <IModifiableType>(); if (method.HasThis) { IL.Emit(OpCodes.Ldarg_0); IL.Emit(OpCodes.Isinst, modifiableType); IL.Emit(OpCodes.Brfalse, skipProlog); } IL.Emit(OpCodes.Ldloc, _interceptionDisabled); IL.Emit(OpCodes.Brtrue, skipProlog); // var provider = this.MethodReplacementProvider; if (_getMethodReplacementProvider != null) { _getMethodReplacementProvider.Emit(IL); } var getAroundInvokeProvider = new GetAroundInvokeProvider(_aroundInvokeProvider, _providerName); getAroundInvokeProvider.Emit(IL); // if (aroundInvokeProvider != null ) { Instruction skipGetSurroundingImplementation = IL.Create(OpCodes.Nop); var getSurroundingImplementationInstance = new GetSurroundingImplementationInstance(_aroundInvokeProvider, _invocationInfo, _surroundingImplementation, skipGetSurroundingImplementation); getSurroundingImplementationInstance.Emit(IL); // } IL.Append(skipGetSurroundingImplementation); var emitBeforeInvoke = new EmitBeforeInvoke(_invocationInfo, _surroundingClassImplementation, _surroundingImplementation, _registryType); emitBeforeInvoke.Emit(IL); IL.Append(skipProlog); }
/// <summary> /// Adds a prolog to the given method body. /// </summary> /// <param name="IL">The <see cref="CilWorker"/> that points to the given method body.</param> public void AddProlog(CilWorker IL) { var method = IL.GetMethod(); _surroundingImplementation = method.AddLocal<IAroundInvoke>(); _surroundingClassImplementation = method.AddLocal<IAroundInvoke>(); var skipProlog = IL.Create(OpCodes.Nop); var declaringType = method.DeclaringType; var module = declaringType.Module; var modifiableType = module.ImportType<IModifiableType>(); if (method.HasThis) { IL.Emit(OpCodes.Ldarg_0); IL.Emit(OpCodes.Isinst, modifiableType); IL.Emit(OpCodes.Brfalse, skipProlog); } IL.Emit(OpCodes.Ldloc, _interceptionDisabled); IL.Emit(OpCodes.Brtrue, skipProlog); // var provider = this.MethodReplacementProvider; if (_getMethodReplacementProvider != null) _getMethodReplacementProvider.Emit(IL); var getAroundInvokeProvider = new GetAroundInvokeProvider(_aroundInvokeProvider, _providerName); getAroundInvokeProvider.Emit(IL); // if (aroundInvokeProvider != null ) { var skipGetSurroundingImplementation = IL.Create(OpCodes.Nop); var getSurroundingImplementationInstance = new GetSurroundingImplementationInstance(_aroundInvokeProvider, _invocationInfo, _surroundingImplementation, skipGetSurroundingImplementation); getSurroundingImplementationInstance.Emit(IL); // } IL.Append(skipGetSurroundingImplementation); var emitBeforeInvoke = new EmitBeforeInvoke(_invocationInfo, _surroundingClassImplementation, _surroundingImplementation, _registryType); emitBeforeInvoke.Emit(IL); IL.Append(skipProlog); }