diff --git a/src/Castle.Core/DynamicProxy/Generators/BaseInterfaceProxyGenerator.cs b/src/Castle.Core/DynamicProxy/Generators/BaseInterfaceProxyGenerator.cs new file mode 100644 index 0000000000..b4225dba2f --- /dev/null +++ b/src/Castle.Core/DynamicProxy/Generators/BaseInterfaceProxyGenerator.cs @@ -0,0 +1,281 @@ +// Copyright 2004-2021 Castle Project - http://www.castleproject.org/ +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +namespace Castle.DynamicProxy.Generators +{ + using System; + using System.Collections.Generic; + using System.Linq; + using System.Reflection; +#if FEATURE_SERIALIZATION + using System.Xml.Serialization; +#endif + + using Castle.DynamicProxy.Contributors; + using Castle.DynamicProxy.Generators.Emitters; + using Castle.DynamicProxy.Generators.Emitters.SimpleAST; + using Castle.DynamicProxy.Internal; + + internal abstract class BaseInterfaceProxyGenerator : BaseProxyGenerator + { + protected readonly Type proxyTargetType; + + protected FieldReference targetField; + + protected BaseInterfaceProxyGenerator(ModuleScope scope, Type targetType, Type[] interfaces, + Type proxyTargetType, ProxyGenerationOptions options) + : base(scope, targetType, interfaces, options) + { + CheckNotGenericTypeDefinition(proxyTargetType, "proxyTargetType"); + EnsureValidBaseType(ProxyGenerationOptions.BaseTypeForInterfaceProxy); + + this.proxyTargetType = proxyTargetType; + } + + protected abstract bool AllowChangeTarget { get; } + + protected abstract string GeneratorType { get; } + + protected abstract CompositeTypeContributor GetProxyTargetContributor(Type proxyTargetType, INamingScope namingScope); + + protected abstract void AddMappingForAdditionalInterfaces(CompositeTypeContributor contributor, Type[] proxiedInterfaces, + IDictionary typeImplementerMapping, + ICollection targetInterfaces); + + protected virtual ITypeContributor AddMappingForTargetType(IDictionary typeImplementerMapping, + Type proxyTargetType, ICollection targetInterfaces, + INamingScope namingScope) + { + var contributor = GetProxyTargetContributor(proxyTargetType, namingScope); + var proxiedInterfaces = targetType.GetAllInterfaces(); + foreach (var @interface in proxiedInterfaces) + { + contributor.AddInterfaceToProxy(@interface); + AddMappingNoCheck(@interface, contributor, typeImplementerMapping); + } + + AddMappingForAdditionalInterfaces(contributor, proxiedInterfaces, typeImplementerMapping, targetInterfaces); + return contributor; + } + +#if FEATURE_SERIALIZATION + protected override void CreateTypeAttributes(ClassEmitter emitter) + { + base.CreateTypeAttributes(emitter); + emitter.DefineCustomAttribute(); + } +#endif + + protected override CacheKey GetCacheKey() + { + return new CacheKey(proxyTargetType, targetType, interfaces, ProxyGenerationOptions); + } + + protected override Type GenerateType(string typeName, INamingScope namingScope) + { + IEnumerable contributors; + var allInterfaces = GetTypeImplementerMapping(proxyTargetType, out contributors, namingScope); + + var model = new MetaType(); + // Collect methods + foreach (var contributor in contributors) + { + contributor.CollectElementsToProxy(ProxyGenerationOptions.Hook, model); + } + + ProxyGenerationOptions.Hook.MethodsInspected(); + + ClassEmitter emitter; + FieldReference interceptorsField; + var baseType = Init(typeName, out emitter, proxyTargetType, out interceptorsField, allInterfaces); + + // Constructor + + var cctor = GenerateStaticConstructor(emitter); + var ctorArguments = new List(); + + foreach (var contributor in contributors) + { + contributor.Generate(emitter); + + // TODO: redo it + if (contributor is MixinContributor) + { + ctorArguments.AddRange((contributor as MixinContributor).Fields); + } + } + + ctorArguments.Add(interceptorsField); + ctorArguments.Add(targetField); + var selector = emitter.GetField("__selector"); + if (selector != null) + { + ctorArguments.Add(selector); + } + + GenerateConstructors(emitter, baseType, ctorArguments.ToArray()); + + // Complete type initializer code body + CompleteInitCacheMethod(cctor.CodeBuilder); + + // Crosses fingers and build type + var generatedType = emitter.BuildType(); + + InitializeStaticFields(generatedType); + return generatedType; + } + + protected virtual InterfaceProxyWithoutTargetContributor GetContributorForAdditionalInterfaces( + INamingScope namingScope) + { + return new InterfaceProxyWithoutTargetContributor(namingScope, (c, m) => NullExpression.Instance) { Logger = Logger }; + } + + protected virtual IEnumerable GetTypeImplementerMapping(Type proxyTargetType, + out IEnumerable contributors, + INamingScope namingScope) + { + IDictionary typeImplementerMapping = new Dictionary(); + var mixins = new MixinContributor(namingScope, AllowChangeTarget) { Logger = Logger }; + // Order of interface precedence: + // 1. first target + var targetInterfaces = proxyTargetType.GetAllInterfaces(); + var target = AddMappingForTargetType(typeImplementerMapping, proxyTargetType, targetInterfaces, namingScope); + + // 2. then mixins + if (ProxyGenerationOptions.HasMixins) + { + foreach (var mixinInterface in ProxyGenerationOptions.MixinData.MixinInterfaces) + { + if (targetInterfaces.Contains(mixinInterface)) + { + // OK, so the target implements this interface. We now do one of two things: + if (interfaces.Contains(mixinInterface)) + { + // we intercept the interface, and forward calls to the target type + AddMapping(mixinInterface, target, typeImplementerMapping); + } + // we do not intercept the interface + mixins.AddEmptyInterface(mixinInterface); + } + else + { + if (!typeImplementerMapping.ContainsKey(mixinInterface)) + { + mixins.AddInterfaceToProxy(mixinInterface); + typeImplementerMapping.Add(mixinInterface, mixins); + } + } + } + } + + var additionalInterfacesContributor = GetContributorForAdditionalInterfaces(namingScope); + // 3. then additional interfaces + foreach (var @interface in interfaces) + { + if (typeImplementerMapping.ContainsKey(@interface)) + { + continue; + } + if (ProxyGenerationOptions.MixinData.ContainsMixin(@interface)) + { + continue; + } + + additionalInterfacesContributor.AddInterfaceToProxy(@interface); + AddMappingNoCheck(@interface, additionalInterfacesContributor, typeImplementerMapping); + } + + // 4. plus special interfaces + var instance = new InterfaceProxyInstanceContributor(targetType, GeneratorType, interfaces); +#if FEATURE_SERIALIZATION + AddMappingForISerializable(typeImplementerMapping, instance); +#endif + try + { + AddMappingNoCheck(typeof(IProxyTargetAccessor), instance, typeImplementerMapping); + } + catch (ArgumentException) + { + HandleExplicitlyPassedProxyTargetAccessor(targetInterfaces); + } + + contributors = new List + { + target, + additionalInterfacesContributor, + mixins, + instance + }; + return typeImplementerMapping.Keys; + } + + protected virtual Type Init(string typeName, out ClassEmitter emitter, Type proxyTargetType, + out FieldReference interceptorsField, IEnumerable allInterfaces) + { + var baseType = ProxyGenerationOptions.BaseTypeForInterfaceProxy; + + emitter = BuildClassEmitter(typeName, baseType, allInterfaces); + + CreateFields(emitter, proxyTargetType); + CreateTypeAttributes(emitter); + + interceptorsField = emitter.GetField("__interceptors"); + return baseType; + } + + private void CreateFields(ClassEmitter emitter, Type proxyTargetType) + { + base.CreateFields(emitter); + targetField = emitter.CreateField("__target", proxyTargetType); +#if FEATURE_SERIALIZATION + emitter.DefineCustomAttributeFor(targetField); +#endif + } + + private void EnsureValidBaseType(Type type) + { + if (type == null) + { + throw new ArgumentException( + "Base type for proxy is null reference. Please set it to System.Object or some other valid type."); + } + + if (!type.IsClass) + { + ThrowInvalidBaseType(type, "it is not a class type"); + } + + if (type.IsSealed) + { + ThrowInvalidBaseType(type, "it is sealed"); + } + + var constructor = type.GetConstructor(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, + null, Type.EmptyTypes, null); + + if (constructor == null || constructor.IsPrivate) + { + ThrowInvalidBaseType(type, "it does not have accessible parameterless constructor"); + } + } + + private void ThrowInvalidBaseType(Type type, string doesNotHaveAccessibleParameterlessConstructor) + { + var format = + "Type {0} is not valid base type for interface proxy, because {1}. Only a non-sealed class with non-private default constructor can be used as base type for interface proxy. Please use some other valid type."; + throw new ArgumentException(string.Format(format, type, doesNotHaveAccessibleParameterlessConstructor)); + } + } +} \ No newline at end of file diff --git a/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithTargetGenerator.cs b/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithTargetGenerator.cs index ea8fd6797a..ab30754080 100644 --- a/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithTargetGenerator.cs +++ b/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithTargetGenerator.cs @@ -17,56 +17,30 @@ namespace Castle.DynamicProxy.Generators using System; using System.Collections.Generic; using System.Linq; - using System.Reflection; -#if FEATURE_SERIALIZATION - using System.Xml.Serialization; -#endif using Castle.DynamicProxy.Contributors; - using Castle.DynamicProxy.Generators.Emitters; - using Castle.DynamicProxy.Generators.Emitters.SimpleAST; - using Castle.DynamicProxy.Internal; using Castle.DynamicProxy.Serialization; - internal class InterfaceProxyWithTargetGenerator : BaseProxyGenerator + internal sealed class InterfaceProxyWithTargetGenerator : BaseInterfaceProxyGenerator { - protected readonly Type proxyTargetType; - - protected FieldReference targetField; - public InterfaceProxyWithTargetGenerator(ModuleScope scope, Type targetType, Type[] interfaces, Type proxyTargetType, ProxyGenerationOptions options) - : base(scope, targetType, interfaces, options) - { - CheckNotGenericTypeDefinition(proxyTargetType, "proxyTargetType"); - EnsureValidBaseType(ProxyGenerationOptions.BaseTypeForInterfaceProxy); + : base(scope, targetType, interfaces, proxyTargetType, options) + { } - this.proxyTargetType = proxyTargetType; - } + protected override bool AllowChangeTarget => false; - protected virtual bool AllowChangeTarget - { - get { return false; } - } + protected override string GeneratorType => ProxyTypeConstants.InterfaceWithTarget; - protected virtual string GeneratorType + protected override CompositeTypeContributor GetProxyTargetContributor(Type proxyTargetType, INamingScope namingScope) { - get { return ProxyTypeConstants.InterfaceWithTarget; } + return new InterfaceProxyTargetContributor(proxyTargetType, AllowChangeTarget, namingScope) { Logger = Logger }; } - protected virtual ITypeContributor AddMappingForTargetType(IDictionary typeImplementerMapping, - Type proxyTargetType, ICollection targetInterfaces, - INamingScope namingScope) + protected override void AddMappingForAdditionalInterfaces(CompositeTypeContributor contributor, Type[] proxiedInterfaces, + IDictionary typeImplementerMapping, + ICollection targetInterfaces) { - var contributor = new InterfaceProxyTargetContributor(proxyTargetType, AllowChangeTarget, namingScope) - { Logger = Logger }; - var proxiedInterfaces = targetType.GetAllInterfaces(); - foreach (var @interface in proxiedInterfaces) - { - contributor.AddInterfaceToProxy(@interface); - AddMappingNoCheck(@interface, contributor, typeImplementerMapping); - } - foreach (var @interface in interfaces) { if (!ImplementedByTarget(targetInterfaces, @interface) || proxiedInterfaces.Contains(@interface)) @@ -77,221 +51,11 @@ protected virtual ITypeContributor AddMappingForTargetType(IDictionary(); - } -#endif - - protected override CacheKey GetCacheKey() - { - return new CacheKey(proxyTargetType, targetType, interfaces, ProxyGenerationOptions); - } - - protected override Type GenerateType(string typeName, INamingScope namingScope) - { - IEnumerable contributors; - var allInterfaces = GetTypeImplementerMapping(proxyTargetType, out contributors, namingScope); - - ClassEmitter emitter; - FieldReference interceptorsField; - var baseType = Init(typeName, out emitter, proxyTargetType, out interceptorsField, allInterfaces); - - var model = new MetaType(); - // Collect methods - foreach (var contributor in contributors) - { - contributor.CollectElementsToProxy(ProxyGenerationOptions.Hook, model); - } - - ProxyGenerationOptions.Hook.MethodsInspected(); - - // Constructor - - var cctor = GenerateStaticConstructor(emitter); - var ctorArguments = new List(); - - foreach (var contributor in contributors) - { - contributor.Generate(emitter); - - // TODO: redo it - if (contributor is MixinContributor) - { - ctorArguments.AddRange((contributor as MixinContributor).Fields); - } - } - - ctorArguments.Add(interceptorsField); - ctorArguments.Add(targetField); - var selector = emitter.GetField("__selector"); - if (selector != null) - { - ctorArguments.Add(selector); - } - - GenerateConstructors(emitter, baseType, ctorArguments.ToArray()); - - // Complete type initializer code body - CompleteInitCacheMethod(cctor.CodeBuilder); - - // Crosses fingers and build type - var generatedType = emitter.BuildType(); - - InitializeStaticFields(generatedType); - return generatedType; - } - - protected virtual InterfaceProxyWithoutTargetContributor GetContributorForAdditionalInterfaces( - INamingScope namingScope) - { - return new InterfaceProxyWithoutTargetContributor(namingScope, (c, m) => NullExpression.Instance) { Logger = Logger }; - } - - protected virtual IEnumerable GetTypeImplementerMapping(Type proxyTargetType, - out IEnumerable contributors, - INamingScope namingScope) - { - IDictionary typeImplementerMapping = new Dictionary(); - var mixins = new MixinContributor(namingScope, AllowChangeTarget) { Logger = Logger }; - // Order of interface precedence: - // 1. first target - var targetInterfaces = proxyTargetType.GetAllInterfaces(); - var target = AddMappingForTargetType(typeImplementerMapping, proxyTargetType, targetInterfaces, namingScope); - - // 2. then mixins - if (ProxyGenerationOptions.HasMixins) - { - foreach (var mixinInterface in ProxyGenerationOptions.MixinData.MixinInterfaces) - { - if (targetInterfaces.Contains(mixinInterface)) - { - // OK, so the target implements this interface. We now do one of two things: - if (interfaces.Contains(mixinInterface)) - { - // we intercept the interface, and forward calls to the target type - AddMapping(mixinInterface, target, typeImplementerMapping); - } - // we do not intercept the interface - mixins.AddEmptyInterface(mixinInterface); - } - else - { - if (!typeImplementerMapping.ContainsKey(mixinInterface)) - { - mixins.AddInterfaceToProxy(mixinInterface); - typeImplementerMapping.Add(mixinInterface, mixins); - } - } - } - } - - var additionalInterfacesContributor = GetContributorForAdditionalInterfaces(namingScope); - // 3. then additional interfaces - foreach (var @interface in interfaces) - { - if (typeImplementerMapping.ContainsKey(@interface)) - { - continue; - } - if (ProxyGenerationOptions.MixinData.ContainsMixin(@interface)) - { - continue; - } - - additionalInterfacesContributor.AddInterfaceToProxy(@interface); - AddMappingNoCheck(@interface, additionalInterfacesContributor, typeImplementerMapping); - } - - // 4. plus special interfaces - var instance = new InterfaceProxyInstanceContributor(targetType, GeneratorType, interfaces); -#if FEATURE_SERIALIZATION - AddMappingForISerializable(typeImplementerMapping, instance); -#endif - try - { - AddMappingNoCheck(typeof(IProxyTargetAccessor), instance, typeImplementerMapping); - } - catch (ArgumentException) - { - HandleExplicitlyPassedProxyTargetAccessor(targetInterfaces); - } - - contributors = new List - { - target, - additionalInterfacesContributor, - mixins, - instance - }; - return typeImplementerMapping.Keys; - } - - protected virtual Type Init(string typeName, out ClassEmitter emitter, Type proxyTargetType, - out FieldReference interceptorsField, IEnumerable allInterfaces) - { - var baseType = ProxyGenerationOptions.BaseTypeForInterfaceProxy; - - emitter = BuildClassEmitter(typeName, baseType, allInterfaces); - - CreateFields(emitter, proxyTargetType); - CreateTypeAttributes(emitter); - - interceptorsField = emitter.GetField("__interceptors"); - return baseType; - } - - private void CreateFields(ClassEmitter emitter, Type proxyTargetType) - { - base.CreateFields(emitter); - targetField = emitter.CreateField("__target", proxyTargetType); -#if FEATURE_SERIALIZATION - emitter.DefineCustomAttributeFor(targetField); -#endif - } - - private void EnsureValidBaseType(Type type) - { - if (type == null) - { - throw new ArgumentException( - "Base type for proxy is null reference. Please set it to System.Object or some other valid type."); - } - - if (!type.IsClass) - { - ThrowInvalidBaseType(type, "it is not a class type"); - } - - if (type.IsSealed) - { - ThrowInvalidBaseType(type, "it is sealed"); - } - - var constructor = type.GetConstructor(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, - null, Type.EmptyTypes, null); - - if (constructor == null || constructor.IsPrivate) - { - ThrowInvalidBaseType(type, "it does not have accessible parameterless constructor"); - } } private bool ImplementedByTarget(ICollection targetInterfaces, Type @interface) { return targetInterfaces.Contains(@interface); } - - private void ThrowInvalidBaseType(Type type, string doesNotHaveAccessibleParameterlessConstructor) - { - var format = - "Type {0} is not valid base type for interface proxy, because {1}. Only a non-sealed class with non-private default constructor can be used as base type for interface proxy. Please use some other valid type."; - throw new ArgumentException(string.Format(format, type, doesNotHaveAccessibleParameterlessConstructor)); - } } -} \ No newline at end of file +} diff --git a/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithTargetInterfaceGenerator.cs b/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithTargetInterfaceGenerator.cs index 5b8f9a6683..77091c2052 100644 --- a/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithTargetInterfaceGenerator.cs +++ b/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithTargetInterfaceGenerator.cs @@ -24,7 +24,7 @@ namespace Castle.DynamicProxy.Generators using Castle.DynamicProxy.Internal; using Castle.DynamicProxy.Serialization; - internal class InterfaceProxyWithTargetInterfaceGenerator : InterfaceProxyWithTargetGenerator + internal sealed class InterfaceProxyWithTargetInterfaceGenerator : BaseInterfaceProxyGenerator { public InterfaceProxyWithTargetInterfaceGenerator(ModuleScope scope, Type targetType, Type[] interfaces, Type proxyTargetType, ProxyGenerationOptions options) @@ -32,31 +32,19 @@ public InterfaceProxyWithTargetInterfaceGenerator(ModuleScope scope, Type target { } - protected override bool AllowChangeTarget - { - get { return true; } - } + protected override bool AllowChangeTarget => true; + + protected override string GeneratorType => ProxyTypeConstants.InterfaceWithTargetInterface; - protected override string GeneratorType + protected override CompositeTypeContributor GetProxyTargetContributor(Type proxyTargetType, INamingScope namingScope) { - get { return ProxyTypeConstants.InterfaceWithTargetInterface; } + return new InterfaceProxyWithTargetInterfaceTargetContributor(proxyTargetType, AllowChangeTarget, namingScope) { Logger = Logger }; } - protected override ITypeContributor AddMappingForTargetType( - IDictionary typeImplementerMapping, Type proxyTargetType, ICollection targetInterfaces, - INamingScope namingScope) + protected override void AddMappingForAdditionalInterfaces(CompositeTypeContributor contributor, Type[] proxiedInterfaces, + IDictionary typeImplementerMapping, + ICollection targetInterfaces) { - var contributor = new InterfaceProxyWithTargetInterfaceTargetContributor( - proxyTargetType, - AllowChangeTarget, - namingScope) { Logger = Logger }; - foreach (var @interface in targetType.GetAllInterfaces()) - { - contributor.AddInterfaceToProxy(@interface); - AddMappingNoCheck(@interface, contributor, typeImplementerMapping); - } - - return contributor; } protected override InterfaceProxyWithoutTargetContributor GetContributorForAdditionalInterfaces( diff --git a/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithoutTargetGenerator.cs b/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithoutTargetGenerator.cs index 164c99b421..35fe2497fa 100644 --- a/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithoutTargetGenerator.cs +++ b/src/Castle.Core/DynamicProxy/Generators/InterfaceProxyWithoutTargetGenerator.cs @@ -18,12 +18,10 @@ namespace Castle.DynamicProxy.Generators using System.Collections.Generic; using Castle.DynamicProxy.Contributors; - using Castle.DynamicProxy.Generators.Emitters; using Castle.DynamicProxy.Generators.Emitters.SimpleAST; - using Castle.DynamicProxy.Internal; using Castle.DynamicProxy.Serialization; - internal class InterfaceProxyWithoutTargetGenerator : InterfaceProxyWithTargetGenerator + internal sealed class InterfaceProxyWithoutTargetGenerator : BaseInterfaceProxyGenerator { public InterfaceProxyWithoutTargetGenerator(ModuleScope scope, Type targetType, Type[] interfaces, Type proxyTargetType, ProxyGenerationOptions options) @@ -31,75 +29,24 @@ public InterfaceProxyWithoutTargetGenerator(ModuleScope scope, Type targetType, { } - protected override string GeneratorType + protected override bool AllowChangeTarget => false; + + protected override string GeneratorType => ProxyTypeConstants.InterfaceWithoutTarget; + + protected override CompositeTypeContributor GetProxyTargetContributor(Type proxyTargetType, INamingScope namingScope) { - get { return ProxyTypeConstants.InterfaceWithoutTarget; } + return new InterfaceProxyWithoutTargetContributor(namingScope, (c, m) => NullExpression.Instance) { Logger = Logger }; } - protected override ITypeContributor AddMappingForTargetType( - IDictionary interfaceTypeImplementerMapping, Type proxyTargetType, - ICollection targetInterfaces, INamingScope namingScope) + protected override void AddMappingForAdditionalInterfaces(CompositeTypeContributor contributor, Type[] proxiedInterfaces, + IDictionary typeImplementerMapping, + ICollection targetInterfaces) { - var contributor = new InterfaceProxyWithoutTargetContributor(namingScope, (c, m) => NullExpression.Instance) - { Logger = Logger }; - foreach (var @interface in targetType.GetAllInterfaces()) - { - contributor.AddInterfaceToProxy(@interface); - AddMappingNoCheck(@interface, contributor, interfaceTypeImplementerMapping); - } - return contributor; } - protected override Type GenerateType(string typeName, INamingScope namingScope) + protected override IEnumerable GetTypeImplementerMapping(Type _, out IEnumerable contributors, INamingScope namingScope) { - IEnumerable contributors; - var allInterfaces = GetTypeImplementerMapping(targetType, out contributors, namingScope); - var model = new MetaType(); - // collect elements - foreach (var contributor in contributors) - { - contributor.CollectElementsToProxy(ProxyGenerationOptions.Hook, model); - } - - ProxyGenerationOptions.Hook.MethodsInspected(); - - ClassEmitter emitter; - FieldReference interceptorsField; - var baseType = Init(typeName, out emitter, proxyTargetType, out interceptorsField, allInterfaces); - - // Constructor - - var cctor = GenerateStaticConstructor(emitter); - var mixinFieldsList = new List(); - - foreach (var contributor in contributors) - { - contributor.Generate(emitter); - - // TODO: redo it - if (contributor is MixinContributor) - { - mixinFieldsList.AddRange((contributor as MixinContributor).Fields); - } - } - - var ctorArguments = new List(mixinFieldsList) { interceptorsField, targetField }; - var selector = emitter.GetField("__selector"); - if (selector != null) - { - ctorArguments.Add(selector); - } - - GenerateConstructors(emitter, baseType, ctorArguments.ToArray()); - - // Complete type initializer code body - CompleteInitCacheMethod(cctor.CodeBuilder); - - // Crosses fingers and build type - var generatedType = emitter.BuildType(); - - InitializeStaticFields(generatedType); - return generatedType; + return base.GetTypeImplementerMapping(proxyTargetType: targetType, out contributors, namingScope); } } } \ No newline at end of file diff --git a/src/Castle.Core/DynamicProxy/Serialization/ProxyObjectReference.cs b/src/Castle.Core/DynamicProxy/Serialization/ProxyObjectReference.cs index 2ccfe81997..09f4acf3ef 100644 --- a/src/Castle.Core/DynamicProxy/Serialization/ProxyObjectReference.cs +++ b/src/Castle.Core/DynamicProxy/Serialization/ProxyObjectReference.cs @@ -141,7 +141,7 @@ public object RecreateInterfaceProxy(string generatorType) var @interface = DeserializeTypeFromString("__theInterface"); var targetType = DeserializeTypeFromString("__targetFieldType"); - InterfaceProxyWithTargetGenerator generator; + BaseInterfaceProxyGenerator generator; if (generatorType == ProxyTypeConstants.InterfaceWithTarget) { generator = new InterfaceProxyWithTargetGenerator(scope, @interface, interfaces, targetType, proxyGenerationOptions);