public override void Weave(
     TypeDefinition typeDef,
     AssemblyDefinition assemblyDefinition,
     MapDefinition mapDefinition,
     Dictionary<string, List<MapDefinition>> assemblyMapDefinitions,
     Dictionary<string, AssemblyDefinition> assemblyDefinitions) {
     var constructors = typeDef.GetConstructors().ToArray();
     foreach (var oneToManyColumnDefinition in mapDefinition.ColumnDefinitions.Where(c => c.Relationship == RelationshipType.OneToMany)) {
         var propDef = this.GetProperty(typeDef, oneToManyColumnDefinition.Name);
         if (propDef.SetMethod.CustomAttributes.Any(c => c.AttributeType.FullName == typeof(CompilerGeneratedAttribute).FullName)) {
             // auto prop - see if the prop set method is called in any of the constructors
             if (!constructors.Any(c => c.Body.Instructions.Any(i => i.Operand != null && i.Operand.Equals(propDef.SetMethod)))) {
                 this.InstantiateCollection(typeDef, constructors, propDef);
             }
         }
         else {
             // not an auto prop
             var backingField = this.GetBackingField(propDef);
             if (
                 !constructors.Any(
                     c =>
                     c.Body.Instructions.Any(i => i.Operand != null && (i.Operand.Equals(propDef.SetMethod) || i.Operand.Equals(backingField))))) {
                 this.InstantiateCollection(typeDef, constructors, propDef);
             }
         }
     }
 }
Example #2
0
        public TypeDefinition CreateProxyType(string nameBase,
                                              IEnumerable<TypeDefinition> interfacesToImplement,
                                              TypeDefinition proxyBase)
        {
            proxyBase = proxyBase ?? this.proxySuperBaseTypeDef.Resolve();
            MethodReference proxyBaseCtor = proxyBase.GetConstructors().First(x => x.Parameters.Count == 0);
            proxyBaseCtor = Module.Import(proxyBaseCtor);

            var proxyTypeName = string.Format(this.proxyNameFormat, nameBase);

            var typeAttributes = this.isPublic
                ? TypeAttributes.Public
                : TypeAttributes.NotPublic;

            var proxyType = new TypeDefinition(this.proxyNamespace,
                                               proxyTypeName,
                                               typeAttributes,
                                               this.module.Import(proxyBase));
            Module.Types.Add(proxyType);

            foreach (var interfaceDef in interfacesToImplement)
                proxyType.Interfaces.Add(this.module.Import(interfaceDef));

            // Empty public constructor
            var ctor = new MethodDefinition(
                ".ctor",
                MethodAttributes.HideBySig | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName
                | MethodAttributes.Public,
                Module.TypeSystem.Void);

            ctor.Body.MaxStackSize = 8;
            var ctorIlProcessor = ctor.Body.GetILProcessor();
            ctorIlProcessor.Append(Instruction.Create(OpCodes.Ldarg_0));
            ctorIlProcessor.Append(Instruction.Create(OpCodes.Call, proxyBaseCtor));
            ctorIlProcessor.Append(Instruction.Create(OpCodes.Ret));

            proxyType.Methods.Add(ctor);

            var interfaces =
                interfacesToImplement.SelectMany(GetAllInterfacesRecursive)
                                     .Except(proxyBase.Interfaces.SelectMany(x => GetAllInterfacesRecursive(x.Resolve())))
                                     .Distinct()
                                     .ToList();

            var propertiesToCreate = interfaces.SelectMany(x => x.Properties).ToList();
            foreach (var targetProp in propertiesToCreate)
            {
                var proxyPropDef = AddProperty(proxyType, targetProp.Name, this.module.Import(targetProp.PropertyType));
                OnGeneratePropertyMethods(
                    targetProp,
                    proxyPropDef,
                    this.proxySuperBaseTypeDef,
                    this.module.Import(targetProp.DeclaringType),
                    interfacesToImplement.First());
            }

            return proxyType;
        }
		static bool CanInstantiateType (TypeDefinition type)
		{
			// type is static (>= 2.0)
			if (type.IsStatic ())
				return false;

			if (type.IsSealed && type.HasMethods) {
				foreach (MethodDefinition ctor in type.GetConstructors ()) {
					if (ctor.IsVisible ())
						return true;
				}
				return false;
			}
			return true;
		}
		public RuleResult CheckType (TypeDefinition type)
		{
			// rule apply only on abstract types
			if (!type.IsAbstract)
				return RuleResult.DoesNotApply;

			// rule applies!

			foreach (MethodDefinition ctor in type.GetConstructors ()) {
				if (ctor.IsPublic) {
					Runner.Report (ctor, Severity.Low, Confidence.Total);
				}
			}

			return Runner.CurrentRuleResult;
		}
        public FieldDefinition ExtendConstructorWithDynamicInterceptorManager(TypeDefinition typeToProxy, bool requiresInterceptor)
        {
            FieldDefinition field = AddPrivateReadonlyField(typeToProxy, this.interceptorManagerReference);

            MethodDefinition constructor = typeToProxy.GetConstructors().Single();
            constructor.Body.InitLocals = true;

            ParameterDefinition parameter = AddParameter(constructor, this.interceptorManagerReference);

            Instruction firstInstruction = FindFirstInstruction(constructor);

            ILProcessor processor = constructor.Body.GetILProcessor();

            processor.InsertBefore(firstInstruction, InstructionHelper.CallMethodAndPassParameter(this.ensureDynamicInterceptorManagerNotNull, parameter));
            processor.InsertBefore(firstInstruction, InstructionHelper.SetInstanceFieldToMethodParameter(field, parameter));
            processor.InsertBefore(firstInstruction, InstructionHelper.CallMethodAndPassThisAndBoolean(field, this.managerInitializeMethodReference, requiresInterceptor));

            return field;
        }
		static bool IsAllStatic (TypeDefinition type)
		{
			if (type.HasMethods) {
				foreach (MethodDefinition ctor in type.GetConstructors ()) {
					// let's the default ctor pass (since it's always here for 1.x code)
					if (!ctor.IsStatic && ctor.HasParameters)
						return false;
				}

				foreach (MethodDefinition method in type.GetMethods ()) {
					if (!method.IsStatic)
						return false;
				}
			}
			if (type.HasFields) {
				foreach (FieldDefinition field in type.Fields) {
					if (!field.IsStatic)
						return false;
				}
			}
			return true;
		}
 private static bool HasMultipleConstructors(TypeDefinition typeDefinition)
 {
     return typeDefinition.GetConstructors().Count() > 1;
 }
        /// <summary>
        /// Weaves a new method into a hosting type with an attribute of specified type being
        /// installed as a method decorator.
        /// </summary>
        /// <param name="hostType">The type of object to weave the new method into.</param>
        /// <param name="attributeType">The type of attribute to decorate the method with.</param>
        private void WeaveAttributeDecoratedMethod(TypeDefinition hostType, TypeDefinition attributeType)
        {
            var attribs =
            Mono.Cecil.MethodAttributes.Public |
            Mono.Cecil.MethodAttributes.Final |
            Mono.Cecil.MethodAttributes.HideBySig |
            Mono.Cecil.MethodAttributes.NewSlot |
            Mono.Cecil.MethodAttributes.Virtual;

             var methodDefinition =
            new MethodDefinition("Db" + Guid.NewGuid().ToString().Replace("-", ""), attribs, ModuleDefinition.TypeSystem.Void);

             // Empty method shell that only returns void.
             methodDefinition.Body.Instructions.Add(Instruction.Create(OpCodes.Nop));
             methodDefinition.Body.Instructions.Add(Instruction.Create(OpCodes.Ret));

             // First we need to get the constructor of the attribute.
             MethodReference attributeConstructor = ModuleDefinition.ImportReference(
            attributeType.GetConstructors().First(c => c.Parameters.Count == 0));

             // Once we have the constructor, the custom attribute can be assembled and added.
             CustomAttribute customAttrib = new CustomAttribute(attributeConstructor);

             methodDefinition.CustomAttributes.Add(customAttrib);

             hostType.Methods.Add(methodDefinition);
        }
Example #9
0
        void Rewrite(TypeDefinition type, IEnumerable<string> options)
        {
            var entry_points = type.Fields.FirstOrDefault(f => f.Name == "EntryPoints");
            if (entry_points != null)
            {
                // Build list of entry point signatures (one per entry point) 
                var entry_signatures = new List<MethodDefinition>();
                entry_signatures.AddRange(type.Methods
                    .Where(t => t.CustomAttributes.Any(a => a.AttributeType.Name == "SlotAttribute")));

                Rewrite(type, entry_points, entry_signatures, options);

                RemoveNativeSignatures(type, entry_signatures);
            }

            if (type.Name == "RewrittenAttribute")
            {
                var rewritten_constructor = type.GetConstructors().First();
                var rewritten = new CustomAttribute(rewritten_constructor);
                rewritten.ConstructorArguments.Add(new CustomAttributeArgument(
                    type.Module.Import(mscorlib.MainModule.GetType("System.Boolean")), true));
                type.Module.Assembly.CustomAttributes.Add(rewritten);
            }
        }
Example #10
0
 /// <summary>
 /// Checks if a given <paramref name="type"/> is injectable.
 /// </summary>
 /// <remarks>
 /// To be "injectable", a type needs to have at least one property
 /// or constructor decorated with an [Inject] attribute.
 /// </remarks>
 /// <param name="type">
 /// The possibly-injectable type.
 /// </param>
 /// <returns>
 /// Returns <see langword="true"/> if the given <paramref name="type"/>
 /// is injectable, and <see langword="false"/> otherwise.
 /// </returns>
 private static bool IsInject(TypeDefinition type)
 {
     return type.GetConstructors().Any(c => c.CustomAttributes.Any(Attributes.IsInjectAttribute))
         || type.Properties.Any(p => p.CustomAttributes.Any(Attributes.IsInjectAttribute));
 }
		public RuleResult CheckType (TypeDefinition type)
		{
			// rule applies only if the type isn't: an enum, an interface, a struct, a delegate or compiler generated
			if (type.IsEnum || type.IsInterface || type.IsValueType || type.IsDelegate () || type.IsGeneratedCode ())
				return RuleResult.DoesNotApply;

			// it also does not apply if the type is static (2.0+ only)
			if (type.IsStatic ())
				return RuleResult.DoesNotApply;

			if (!IsAllStatic (type))
				return RuleResult.Success;

			// rule applies!

			foreach (MethodDefinition ctor in type.GetConstructors ()) {
				if (!ctor.IsStatic && ctor.IsVisible ()) {
					Runner.Report (ctor, Severity.Low, Confidence.High);
				}
			}

			return Runner.CurrentRuleResult;
		}
		public RuleResult CheckType (TypeDefinition type)
		{
			// rule apply only to type that inherits from System.Exception
			if (!type.Inherits (Exception))
				return RuleResult.DoesNotApply;

			// rule applies, only Success or Failure from the point on

			// check if the type implements all the needed exception constructors

			bool empty_ctor = false;		// MyException ()
			bool string_ctor = false;		// MyException (string message)
			bool inner_exception_ctor = false;	// MyException (string message, Exception innerException)
			bool serialization_ctor = false;	// MyException (SerializationInfo info, StreamingContext context)

			foreach (MethodDefinition ctor in type.GetConstructors ()) {
				// skip cctor
				if (ctor.IsStatic)
					continue;

				if (!ctor.HasParameters) {
					// there can be only one so only it's visibility matters
					empty_ctor = ctor.IsPublic;
					continue;
				}

				switch (ctor.Parameters.Count) {
				case 1:
					string_ctor |= CheckForStringConstructor (ctor);
					break;
				case 2:
					if (ctor.IsPublic) {
						if (!inner_exception_ctor) {
							inner_exception_ctor = CheckForInnerExceptionConstructor (ctor);
							if (inner_exception_ctor)
								break;
						}

						string_ctor |= CheckForStringConstructor (ctor);
					} else {
						serialization_ctor |= CheckForSerializationConstructor (ctor);
					}
					break;
				default:
					inner_exception_ctor |= CheckForInnerExceptionConstructor (ctor);
					break;
				}
			}

			if (!empty_ctor) {
				string s = String.Format (MissingConstructor, "public", type.Name, "()");
				Runner.Report (type, Severity.High, Confidence.Total, s);
			}
			if (!string_ctor) {
				string s = String.Format (MissingConstructor, "public", type.Name, "(string message)");
				Runner.Report (type, Severity.High, Confidence.Total, s);
			}
			if (!inner_exception_ctor) {
				string s = String.Format (MissingConstructor, "public", type.Name,
					"(string message, Exception innerException)");
				Runner.Report (type, Severity.High, Confidence.Total, s);
			}
			if (!serialization_ctor) {
				string s = String.Format (MissingConstructor, (type.IsSealed) ? "private" : "protected",
					type.Name, "(SerializationInfo info, StreamingContext context)");
				Runner.Report (type, Severity.High, Confidence.Total, s);
			}

			return Runner.CurrentRuleResult;
		}
Example #13
0
        /// <summary>
        /// Injects code for initialising database state and connections prior to test execution.
        /// </summary>
        /// <param name="type">The type of object which is currently the weaving target.</param>
        private void InjectDatabaseSetupInConstructor(TypeDefinition type)
        {
            LogInfo("Beginning to inject database set up into the constructor of type " + type.Name);

             if (type.GetConstructors().Count(m => m.IsInstanceConstructor()) > 1)
             {
            throw new WeavingException(
               "Class " + type.FullName + " has multiple constructors which is not currently supported. Please remove additional constructors.");
             }

             foreach (var ctor in type.GetConstructors().Where(m => m.IsInstanceConstructor()))
             {
            Instruction firstInstruction = ctor.Body.Instructions.FirstOrDefault(i => i.InstructionCallsConstructor());

            var firstInstructionAfterBaseCtorCall =
               firstInstruction == null ?
               firstInstruction.Next :
               ctor.Body.Instructions.First();

            LogInfo("Ensuring that the constructor has an ITestOutputHelper dependency.");

            // Ensure the class constructor has a ITestHelperOutput parameter.
            if (!ctor.Parameters.Any(p => p.ParameterType.FullName == "Xunit.Abstractions.ITestOutputHelper"))
            {
               ctor.Parameters.Add(
                  new ParameterDefinition(
                     type.Module.ImportReference(GetTestOutputHelperDefinition())));
            }

            LogInfo("Preparing to wire up ClassDatabaseFixture dependency.");

            // Wire up ClassDatabaseFixture dependency.
            EnsureClassHasClassDatabaseFixtureDependency(type, ctor, firstInstructionAfterBaseCtorCall);

            LogInfo("Preparing to wire up CollectionDatabaseFixture dependency.");

            // Wire up CollectionDatabaseFixture dependency.
            EnsureClassHasCollectionDatabaseFixtureDependency(type, ctor, firstInstructionAfterBaseCtorCall);

            LogInfo("About to inject BeforeTest logic.");

            /*
             * Below instructions create the following line of code:
             *    DbController.BeforeTest(this, MethodBase.GetCurrentMethod(), new Action<string>(testOutputHelper.WriteLine));
             * */

            ctor.Body.Instructions.InsertBefore(
               firstInstructionAfterBaseCtorCall,
               Instruction.Create(OpCodes.Ldarg_0));

            ctor.Body.Instructions.InsertBefore(
               firstInstructionAfterBaseCtorCall,
               Instruction.Create(
                  OpCodes.Call,
                  ctor.Module.ImportReference(typeof(MethodBase).GetMethod("GetCurrentMethod"))));

            // Load the ITestOutputHelper instance onto the stack.
            ctor.Body.Instructions.InsertBefore(
               firstInstructionAfterBaseCtorCall,
               Instruction.Create(
                  OpCodes.Ldarg_S,
                  ctor.Parameters.First(p => p.ParameterType.FullName == "Xunit.Abstractions.ITestOutputHelper")));

            // Duplicate the instruction on top of the evaluation stack.
            ctor.Body.Instructions.InsertBefore(
               firstInstructionAfterBaseCtorCall,
               Instruction.Create(OpCodes.Dup));

            // Load the virtual function ITestOutputHelper.WriteLine onto the evaluation stack.
            ctor.Body.Instructions.InsertBefore(
               firstInstructionAfterBaseCtorCall,
               Instruction.Create(
                  OpCodes.Ldvirtftn,
                  ctor.Module.ImportReference(
                     GetTestOutputHelperDefinition().Methods.First(m => m.Name == "WriteLine" && m.Parameters.Count == 1))));

            // Wrap a new action delegate around the ITestOutputHelper.WriteLine delegate call.
            ctor.Body.Instructions.InsertBefore(
               firstInstructionAfterBaseCtorCall,
               Instruction.Create(
                  OpCodes.Newobj,
                  ctor.Module.ImportReference(typeof(Action<string>).GetConstructors().First())));

            ctor.Body.Instructions.InsertBefore(
               firstInstructionAfterBaseCtorCall,
               Instruction.Create(
                  OpCodes.Call,
                  ctor.Module.ImportReference(
                     GetDbControllerDefinition().GetMethods().First(m => m.Name == "BeforeTest"))));
             }
        }
Example #14
0
		void Preserve (TypeDefinition marker, TypeDefinition implementation)
		{
			foreach (var constructor in implementation.GetConstructors ())
				annotations.AddPreservedMethod (marker, constructor);
		}
Example #15
0
		void ProcessConstructors (TypeDefinition type, List<ExportedMethod> exported)
		{
			foreach (MethodDefinition ctor in type.GetConstructors ()) {
				if (!ctor.HasParameters && !ctor.IsStatic) {
					exported.Add (new ExportedMethod (null, ctor));
					continue;
				}

				CustomAttribute export;
				if (!TryGetExportAttribute (ctor, out export))
					continue;

				exported.Add (new ExportedMethod (export, ctor));
			}
		}
		public RuleResult CheckType (TypeDefinition type)
		{
			// rule applies only to attributes
			if (!type.IsAttribute ())
				return RuleResult.DoesNotApply;

			// look through getters
			allProperties.Clear ();
			foreach (PropertyDefinition property in type.Properties) {
				if (property.GetMethod != null) {
					allProperties.Add (property.Name);
				}
			}

			// look through parameters
			foreach (MethodDefinition constructor in type.GetConstructors ()) {
				foreach (ParameterDefinition param in constructor.Parameters) {
					 // pascal case it
					string correspondingPropertyName = Char.ToUpper (param.Name [0]).ToString () + param.Name.Substring (1);
					if (!allProperties.Contains (correspondingPropertyName)) {
						string s = String.Format ("Add '{0}' property to the attribute class.", correspondingPropertyName);
						Runner.Report (param, Severity.Medium, Confidence.High, s);
						allProperties.Add (correspondingPropertyName); // to avoid double catching same property (e.g. from different constructors)
					}
				}
			}
			return Runner.CurrentRuleResult;
		}
		static bool IsAllStatic (TypeDefinition type)
		{
			if (type == null)
				return false;

			if (type.HasMethods) {
				foreach (MethodDefinition ctor in type.GetConstructors ()) {
					// let's the default ctor pass (since it's always here for 1.x code)
					if (!ctor.IsStatic && ctor.HasParameters)
						return false;
				}

				foreach (MethodDefinition method in type.GetMethods ()) {
					if (!method.IsStatic)
						return false;
				}
			}

			if (type.HasFields) {
				foreach (FieldDefinition field in type.Fields) {
					if (!field.IsStatic)
						return false;
				}
			}

			if (type.BaseType.FullName == "System.Object")
				return true;

			return IsAllStatic (type.BaseType.Resolve ());
		}
		static bool HasSinglePrivateConstructor (TypeDefinition type)
		{
			if (!type.HasMethods)
				return false;

			var ctors = type.GetConstructors ().ToList ();
			if (ctors.Count != 1)
				return false;

			var constructor = ctors [0];
			return (constructor.IsPrivate && !constructor.HasParameters);
		}
Example #19
0
		void PreserveIntPtrConstructor (TypeDefinition type)
		{
			if (!type.HasMethods)
				return;

			foreach (MethodDefinition constructor in type.GetConstructors ()) {
				if (!constructor.HasParameters)
					continue;

				if (constructor.Parameters.Count != 1 || constructor.Parameters [0].ParameterType.FullName != "System.IntPtr")
					continue;

				PreserveMethod (type, constructor);
				break; // only one .ctor can match this
			}
		}
Example #20
0
		void Preserve (TypeDefinition marker, TypeDefinition implementation)
		{
			if (marker == null || implementation == null)
				return;
			foreach (var constructor in implementation.GetConstructors ())
				annotations.AddPreservedMethod (marker, constructor);
		}
		public RuleResult CheckType (TypeDefinition type)
		{
			// sealed classes are ok
			if (type.IsSealed)
				return RuleResult.DoesNotApply;

			// check each constructor
			foreach (MethodDefinition constructor in type.GetConstructors ()) {
				// early checks to avoid stack creation
				if (constructor.IsStatic || !constructor.HasBody)
					continue;

				CheckConstructor (constructor);
			}
			return Runner.CurrentRuleResult;
		}