PageRenderTime 102ms CodeModel.GetById 40ms app.highlight 20ms RepoModel.GetById 40ms app.codeStats 0ms

/src/LinFu.AOP/Emitters/GetInterceptionDisabled.cs

http://github.com/philiplaureano/LinFu
C# | 74 lines | 45 code | 9 blank | 20 comment | 1 complexity | 184fd05fcde1a604bb87d8514289911c MD5 | raw file
 1using LinFu.AOP.Cecil.Interfaces;
 2using LinFu.AOP.Interfaces;
 3using LinFu.Reflection.Emit;
 4using Mono.Cecil;
 5using Mono.Cecil.Cil;
 6
 7namespace LinFu.AOP.Cecil
 8{
 9    /// <summary>
10    ///     Represents a class that emits the instructions that determine whether or not method interception is disabled.
11    /// </summary>
12    public class GetInterceptionDisabled : IInstructionEmitter
13    {
14        private readonly MethodReference _hostMethod;
15        private readonly VariableDefinition _interceptionDisabled;
16
17        /// <summary>
18        ///     Initializes a new instance of the <see cref="GetInterceptionDisabled" /> class.
19        /// </summary>
20        /// <param name="parameters">The <see cref="IMethodBodyRewriterParameters" /> instance.</param>
21        public GetInterceptionDisabled(IMethodBodyRewriterParameters parameters)
22        {
23            _hostMethod = parameters.TargetMethod;
24            _interceptionDisabled = parameters.InterceptionDisabled;
25        }
26
27        /// <summary>
28        ///     Initializes a new instance of the <see cref="GetInterceptionDisabled" /> class.
29        /// </summary>
30        /// <param name="hostMethod">The target method.</param>
31        /// <param name="interceptionDisabled">The local variable that determines whether or not method interception is disabled.</param>
32        public GetInterceptionDisabled(MethodReference hostMethod, VariableDefinition interceptionDisabled)
33        {
34            _hostMethod = hostMethod;
35            _interceptionDisabled = interceptionDisabled;
36        }
37
38
39        /// <summary>
40        ///     Emits the instructions that determine whether or not method interception is disabled.
41        /// </summary>
42        /// <param name="IL">
43        ///     The <see cref="ILProcessor" /> instance responsible for adding or removing instructions to the method
44        ///     body.
45        /// </param>
46        public void Emit(ILProcessor IL)
47        {
48            var module = IL.Body.Method.DeclaringType.Module;
49            var modifiableType = module.ImportType<IModifiableType>();
50            var getInterceptionDisabledMethod =
51                module.ImportMethod<IModifiableType>("get_IsInterceptionDisabled");
52            if (!_hostMethod.HasThis)
53            {
54                IL.Emit(OpCodes.Ldc_I4_0);
55                IL.Emit(OpCodes.Stloc, _interceptionDisabled);
56                return;
57            }
58
59            var skipLabel = IL.Create(OpCodes.Nop);
60
61            // var interceptionDisabled = this.IsInterceptionDisabled;
62            IL.Emit(OpCodes.Ldarg_0);
63            IL.Emit(OpCodes.Isinst, modifiableType);
64            IL.Emit(OpCodes.Brfalse, skipLabel);
65
66            IL.Emit(OpCodes.Ldarg_0);
67            IL.Emit(OpCodes.Isinst, modifiableType);
68            IL.Emit(OpCodes.Callvirt, getInterceptionDisabledMethod);
69            IL.Emit(OpCodes.Stloc, _interceptionDisabled);
70
71            IL.Append(skipLabel);
72        }
73    }
74}