Exemplo n.º 1
0
 public void IsSubclassable()
 {
     Assert.That(SubclassFilterUtility.IsSubclassable(typeof(string)), Is.False);
     Assert.That(SubclassFilterUtility.IsSubclassable(typeof(IDisposable)), Is.False);
     Assert.That(SubclassFilterUtility.IsSubclassable(typeof(TypeWithoutVisibleCtor)), Is.False);
     Assert.That(SubclassFilterUtility.IsSubclassable(typeof(object)), Is.True);
 }
Exemplo n.º 2
0
        private MethodInfo GetBaseMethod(MutableType declaringType, string name, MethodSignature signature, bool isVirtual, bool isNewSlot)
        {
            if (declaringType.IsInterface || !isVirtual || isNewSlot)
            {
                return(null);
            }

            var baseMethod = _relatedMethodFinder.GetMostDerivedVirtualMethod(name, signature, declaringType.BaseType);

            if (baseMethod != null && baseMethod.IsFinal)
            {
                Assertion.IsNotNull(baseMethod.DeclaringType);
                var message = string.Format("Cannot override final method '{0}.{1}'.", baseMethod.DeclaringType.Name, baseMethod.Name);
                throw new NotSupportedException(message);
            }

            if (baseMethod != null && !SubclassFilterUtility.IsVisibleFromSubclass(baseMethod))
            {
                Assertion.IsNotNull(baseMethod.DeclaringType);
                var message = string.Format(
                    "Cannot override method '{0}.{1}' as it is not visible from the proxy.", baseMethod.DeclaringType.Name, baseMethod.Name);
                throw new NotSupportedException(message);
            }

            return(baseMethod);
        }
Exemplo n.º 3
0
 private void CheckVisibility(MethodInfo baseMethod)
 {
     if (!SubclassFilterUtility.IsVisibleFromSubclass(baseMethod))
     {
         Assertion.IsNotNull(baseMethod.DeclaringType);
         var message = string.Format("Base method '{0}.{1}' is not accessible from proxy type.", baseMethod.DeclaringType.Name, baseMethod.Name);
         throw new MemberAccessException(message);
     }
 }
Exemplo n.º 4
0
        public MutableMethodInfo GetOrCreateImplementation(MutableType declaringType, MethodInfo interfaceMethod, out bool isNewlyCreated)
        {
            ArgumentUtility.CheckNotNull("declaringType", declaringType);
            ArgumentUtility.CheckNotNull("interfaceMethod", interfaceMethod);
            Assertion.IsNotNull(interfaceMethod.DeclaringType);

            if (!interfaceMethod.DeclaringType.IsInterface)
            {
                throw new ArgumentException("The specified method is not an interface method.", "interfaceMethod");
            }

            CheckIsNotMethodInstantiation(interfaceMethod, "interfaceMethod");

            // ReSharper disable PossibleUnintendedReferenceComparison
            if (!interfaceMethod.DeclaringType.IsTypePipeAssignableFrom(declaringType))
            // ReSharper restore PossibleUnintendedReferenceComparison
            {
                Assertion.IsNotNull(interfaceMethod.DeclaringType);
                var message = string.Format(
                    "Method is declared by an interface that is not implemented by the proxy: '{0}'.", interfaceMethod.DeclaringType.Name);
                throw new ArgumentException(message, "interfaceMethod");
            }

            var baseImplementation = GetOrCreateImplementationMethod(declaringType, interfaceMethod, out isNewlyCreated);

            if (baseImplementation is MutableMethodInfo)
            {
                return((MutableMethodInfo)baseImplementation);
            }

            Assertion.IsTrue(baseImplementation.IsVirtual, "It is not possible to get an interface implementation that is not virtual (in verifiable code).");

            // Re-implement if final.
            if (baseImplementation.IsFinal)
            {
                if (!SubclassFilterUtility.IsVisibleFromSubclass(baseImplementation))
                {
                    Assertion.IsNotNull(baseImplementation.DeclaringType);
                    var message = string.Format(
                        "Cannot re-implement interface method '{0}' because its base implementation on '{1}' is not accessible.",
                        interfaceMethod.Name,
                        baseImplementation.DeclaringType.Name);
                    throw new NotSupportedException(message);
                }

                declaringType.AddInterface(interfaceMethod.DeclaringType, throwIfAlreadyImplemented: false);

                var attributes = interfaceMethod.Attributes.Unset(MethodAttributes.Abstract);
                Func <MethodBodyCreationContext, Expression> bodyProvider = ctx => ctx.DelegateToBase(baseImplementation);

                isNewlyCreated = true;
                return(CreateMethod(declaringType, interfaceMethod, interfaceMethod.Name, attributes, bodyProvider));
            }

            return(GetOrCreateOverride(declaringType, baseImplementation, out isNewlyCreated));
        }
Exemplo n.º 5
0
        private bool ShortCircuitTypeAssembly(Type requestedType)
        {
            var isNonSubclassable = !SubclassFilterUtility.IsSubclassable(requestedType);

            if (isNonSubclassable)
            {
                foreach (var participant in _participants)
                {
                    participant.HandleNonSubclassableType(requestedType);
                }
            }

            return(isNonSubclassable);
        }
        public MethodCallExpression CallBaseConstructor(IEnumerable <Expression> arguments)
        {
            ArgumentUtility.CheckNotNull("arguments", arguments);
            EnsureNotStatic();

            var args        = arguments.ToList();
            var constructor = GetConstructor(DeclaringType.BaseType, args);

            if (!SubclassFilterUtility.IsVisibleFromSubclass(constructor))
            {
                throw new MemberAccessException("The matching constructor is not visible from the proxy type.");
            }

            return(CallConstructor(constructor, args));
        }