/// <summary> /// 从指定类型继承 /// </summary> /// <param name="typeBuilder"></param> /// <param name="proxyMethodBuilder"></param> /// <param name="type"></param> /// <param name="declaredMembersOnly"></param> protected virtual void InheritType(TypeBuilder typeBuilder, IProxyMethodBuilder proxyMethodBuilder, Type type, bool declaredMembersOnly) { IDictionary <string, MethodBuilder> methodMap = new Dictionary <string, MethodBuilder>(); BindingFlags bindingFlags = BindingFlags.Public | BindingFlags.Instance | BindingFlags.NonPublic; if (declaredMembersOnly) { bindingFlags |= BindingFlags.DeclaredOnly; } // 重写虚方法 MethodInfo[] methods = type.GetMethods(bindingFlags); foreach (MethodInfo method in methods) { MethodAttributes memberAccess = method.Attributes & MethodAttributes.MemberAccessMask; if (method.IsVirtual && !method.IsFinal && !method.Name.Equals("Finalize") && (memberAccess == MethodAttributes.Public || memberAccess == MethodAttributes.Family || memberAccess == MethodAttributes.FamORAssem)) { MethodBuilder methodBuilder = proxyMethodBuilder.BuildProxyMethod(method, null); ApplyMethodAttributes(methodBuilder, method); methodMap[method.Name] = methodBuilder; } } // 重写虚属性 foreach (PropertyInfo property in type.GetProperties(bindingFlags)) { ImplementProperty(typeBuilder, type, property, methodMap); } // 重写虚事件 foreach (EventInfo evt in type.GetEvents(bindingFlags)) { ImplementEvent(typeBuilder, type, evt, methodMap); } }
/// <summary> /// Implements an interface. /// </summary> /// <remarks> /// Generates proxy methods that belongs to the interface /// using the specified <paramref name="proxyMethodBuilder"/>. /// </remarks> /// <param name="typeBuilder">The type builder to use.</param> /// <param name="proxyMethodBuilder"> /// The <see cref="IProxyMethodBuilder"/> implementation to use /// </param> /// <param name="intf">The interface to implement.</param> /// <param name="targetType"> /// The <see cref="System.Type"/> of the target object. /// </param> /// <param name="proxyVirtualMethods"> /// <see langword="false"/> if target virtual methods should not be proxied; /// otherwise <see langword="true"/>. /// </param> protected virtual void ImplementInterface(TypeBuilder typeBuilder, IProxyMethodBuilder proxyMethodBuilder, Type intf, Type targetType, bool proxyVirtualMethods) { IDictionary methodMap = new Hashtable(); InterfaceMapping mapping = GetInterfaceMapping(targetType, intf); typeBuilder.AddInterfaceImplementation(intf); for (int i = 0; i < mapping.InterfaceMethods.Length; i++) { if (!proxyVirtualMethods && !mapping.TargetMethods[i].DeclaringType.IsInterface && mapping.TargetMethods[i].IsVirtual && !mapping.TargetMethods[i].IsFinal) { continue; } MethodBuilder methodBuilder = proxyMethodBuilder.BuildProxyMethod( mapping.TargetMethods[i], mapping.InterfaceMethods[i]); ApplyMethodAttributes(methodBuilder, mapping.TargetMethods[i]); methodMap[mapping.InterfaceMethods[i].Name] = methodBuilder; } foreach (PropertyInfo property in intf.GetProperties()) { ImplementProperty(typeBuilder, intf, property, methodMap); } foreach (EventInfo evt in intf.GetEvents()) { ImplementEvent(typeBuilder, intf, evt, methodMap); } }
/// <summary> /// Inherit from a type. /// </summary> /// <remarks> /// Generates proxy methods for base virtual methods /// using the specified <paramref name="proxyMethodBuilder"/>. /// </remarks> /// <param name="typeBuilder"> /// The <see cref="System.Type"/> builder to use for code generation. /// </param> /// <param name="proxyMethodBuilder"> /// The <see cref="IProxyMethodBuilder"/> implementation to use to override base virtual methods. /// </param> /// <param name="type">The <see cref="System.Type"/> to inherit from.</param> /// <param name="declaredMembersOnly"> /// <see langword="true"/> if only members declared at the level /// of the supplied <paramref name="type"/>'s hierarchy should be proxied; /// otherwise <see langword="false"/>. /// </param> protected virtual void InheritType(TypeBuilder typeBuilder, IProxyMethodBuilder proxyMethodBuilder, Type type, bool declaredMembersOnly) { IDictionary<string, MethodBuilder> methodMap = new Dictionary<string, MethodBuilder>(); BindingFlags bindingFlags = BindingFlags.Public | BindingFlags.Instance | BindingFlags.NonPublic; if (declaredMembersOnly) { bindingFlags |= BindingFlags.DeclaredOnly; } // override virtual methods MethodInfo[] methods = type.GetMethods(bindingFlags); foreach (MethodInfo method in methods) { MethodAttributes memberAccess = method.Attributes & MethodAttributes.MemberAccessMask; if (method.IsVirtual && !method.IsFinal && !method.Name.Equals("Finalize") && (memberAccess == MethodAttributes.Public || memberAccess == MethodAttributes.Family || memberAccess == MethodAttributes.FamORAssem)) { MethodBuilder methodBuilder = proxyMethodBuilder.BuildProxyMethod(method, null); ApplyMethodAttributes(methodBuilder, method); methodMap[method.Name] = methodBuilder; } } // override virtual properties foreach (PropertyInfo property in type.GetProperties(bindingFlags)) { ImplementProperty(typeBuilder, type, property, methodMap); } // override virtual events foreach (EventInfo evt in type.GetEvents(bindingFlags)) { ImplementEvent(typeBuilder, type, evt, methodMap); } }
/// <summary> /// Implements an interface. /// </summary> /// <remarks> /// Generates proxy methods that belongs to the interface /// using the specified <paramref name="proxyMethodBuilder"/>. /// </remarks> /// <param name="typeBuilder">The type builder to use.</param> /// <param name="proxyMethodBuilder"> /// The <see cref="IProxyMethodBuilder"/> implementation to use /// </param> /// <param name="intf">The interface to implement.</param> /// <param name="targetType"> /// The <see cref="System.Type"/> of the target object. /// </param> /// <param name="proxyVirtualMethods"> /// <see langword="false"/> if target virtual methods should not be proxied; /// otherwise <see langword="true"/>. /// </param> protected virtual void ImplementInterface(TypeBuilder typeBuilder, IProxyMethodBuilder proxyMethodBuilder, Type intf, Type targetType, bool proxyVirtualMethods) { Dictionary<string, MethodBuilder> methodMap = new Dictionary<string, MethodBuilder>(); InterfaceMapping mapping = GetInterfaceMapping(targetType, intf); typeBuilder.AddInterfaceImplementation(intf); for (int i = 0; i < mapping.InterfaceMethods.Length; i++) { if (!proxyVirtualMethods && !mapping.TargetMethods[i].DeclaringType.IsInterface && mapping.TargetMethods[i].IsVirtual && !mapping.TargetMethods[i].IsFinal) continue; MethodBuilder methodBuilder = proxyMethodBuilder.BuildProxyMethod( mapping.TargetMethods[i], mapping.InterfaceMethods[i]); ApplyMethodAttributes(methodBuilder, mapping.TargetMethods[i]); methodMap[mapping.InterfaceMethods[i].Name] = methodBuilder; } foreach (PropertyInfo property in intf.GetProperties()) { ImplementProperty(typeBuilder, intf, property, methodMap); } foreach (EventInfo evt in intf.GetEvents()) { ImplementEvent(typeBuilder, intf, evt, methodMap); } }