public void writeAllMethodKeys(NamedTypeDefinition classToWrite) { if (classToWrite.Methods != null) { foreach (MethodDefinition method in classToWrite.Methods) { this.writeLine(this.makeFuncSigString(method)); } } }
private void MutateType(INamedTypeDefinition iTypeDef, Element element) { NamedTypeDefinition typeDef = iTypeDef as NamedTypeDefinition; if (typeDef == null) { throw new Exception("Invalid namedType definition."); } if (_applyAnnotations) { SecurityTransparencyStatus currentStatus = GetMarkedSecurityAnnotation(typeDef.Attributes, typeDef); if (element.SecurityTransparencyStatus != SecurityTransparencyStatus.Undefined && element.SecurityTransparencyStatus != SecurityTransparencyStatus.Transparent && currentStatus != element.SecurityTransparencyStatus) { RemoveSecurityTransparencyAttributes(typeDef.Attributes, typeDef); AddSecurityTransparencyAttribute(typeDef.Attributes, element.SecurityTransparencyStatus, typeDef); } } AddFaaAttributeIfNeeded(element, typeDef.Attributes, typeDef); if (_changeVisibility && element.ShouldMakeInternal) { MakeInternal(typeDef); } }
private void PruneInterfacesAndExplicitImplementationOverrides(NamedTypeDefinition typeDefinition) { #region Prune the list of interfaces this type implements (if necessary) if (typeDefinition.Interfaces != null && 0 < typeDefinition.Interfaces.Count) { var newInterfaceList = new List <ITypeReference>(); foreach (var iface in typeDefinition.Interfaces) { if (!this.whackedTypes.ContainsKey(iface.InternedKey)) { newInterfaceList.Add(iface); } } typeDefinition.Interfaces = newInterfaceList; } #endregion Prune the list of interfaces this type implements (if necessary) #region Prune the list of explicit implementation overrides (as necessary) if (typeDefinition.ExplicitImplementationOverrides != null && 0 < typeDefinition.ExplicitImplementationOverrides.Count) { var newExplicitImplementationOverrides = new List <IMethodImplementation>(); foreach (IMethodImplementation methodImpl in typeDefinition.ExplicitImplementationOverrides) { if (!this.whackedMethods.ContainsKey(methodImpl.ImplementingMethod.InternedKey)) { newExplicitImplementationOverrides.Add(methodImpl); } } typeDefinition.ExplicitImplementationOverrides = newExplicitImplementationOverrides; } #endregion Prune the list of explicit implementation overrides (as necessary) }
public override IMethodBody Rewrite(IMethodBody methodBody) { this.cdfg = ControlAndDataFlowGraph<BasicBlock<Instruction>, Instruction>.GetControlAndDataFlowGraphFor(this.host, methodBody); this.ilGenerator = new ILGenerator(host, methodBody.MethodDefinition); var numberOfBlocks = this.cdfg.BlockFor.Count; this.labelFor = new Hashtable<ILGeneratorLabel>(numberOfBlocks); this.counterFieldsForCurrentMethod = new NestedTypeDefinition() { BaseClasses = new List<ITypeReference>(1) { this.host.PlatformType.SystemObject }, ContainingTypeDefinition = methodBody.MethodDefinition.ContainingTypeDefinition, Fields = new List<IFieldDefinition>((int)numberOfBlocks*2), Methods = new List<IMethodDefinition>(1), InternFactory = this.host.InternFactory, IsBeforeFieldInit = true, IsClass = true, IsSealed = true, IsAbstract = true, Name = this.host.NameTable.GetNameFor(methodBody.MethodDefinition.Name+"_Counters"+methodBody.MethodDefinition.InternedKey), Visibility = TypeMemberVisibility.Assembly, }; this.fieldOffsets = new List<uint>((int)numberOfBlocks*2); foreach (var exceptionInfo in methodBody.OperationExceptionInformation) { this.ilGenerator.AddExceptionHandlerInformation(exceptionInfo.HandlerKind, exceptionInfo.ExceptionType, this.GetLabelFor(exceptionInfo.TryStartOffset), this.GetLabelFor(exceptionInfo.TryEndOffset), this.GetLabelFor(exceptionInfo.HandlerStartOffset), this.GetLabelFor(exceptionInfo.HandlerEndOffset), exceptionInfo.HandlerKind == HandlerKind.Filter ? this.GetLabelFor(exceptionInfo.FilterDecisionStartOffset) : null); } if (this.pdbReader == null) { foreach (var localDef in methodBody.LocalVariables) this.ilGenerator.AddVariableToCurrentScope(localDef); } else { foreach (var ns in this.pdbReader.GetNamespaceScopes(methodBody)) { foreach (var uns in ns.UsedNamespaces) this.ilGenerator.UseNamespace(uns.NamespaceName.Value); } this.scopeEnumerator = this.pdbReader.GetLocalScopes(methodBody).GetEnumerator(); this.scopeEnumeratorIsValid = this.scopeEnumerator.MoveNext(); } foreach (var block in this.cdfg.AllBlocks) this.InstrumentBlock(block); while (this.scopeStack.Count > 0) { this.ilGenerator.EndScope(); this.scopeStack.Pop(); } this.ilGenerator.AdjustBranchSizesToBestFit(); this.InjectMethodToDumpCounters(); return new ILGeneratorMethodBody(this.ilGenerator, methodBody.LocalsAreZeroed, (ushort)(methodBody.MaxStack+2), methodBody.MethodDefinition, methodBody.LocalVariables, IteratorHelper.GetSingletonEnumerable((ITypeDefinition)this.counterFieldsForCurrentMethod)); }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { if (typeDefinition != null && (typeDefinition.IsClass)) { Console.WriteLine("Rewriting finalize method of " + typeDefinition); var finalizer = this.GetOrCreateFinalizer(typeDefinition); var finalizeWriter = new FinalizeWriter(base.host, finalizer.Body as MethodBody); finalizeWriter.Rewrite(); } base.RewriteChildren(typeDefinition); }
public override void TraverseChildren(IThisReference thisReference) { base.TraverseChildren(thisReference); var typeForThis = this.containingType.ResolvedType; if (typeForThis.IsValueType) { ((ThisReference)thisReference).Type = Immutable.ManagedPointerType.GetManagedPointerType(NamedTypeDefinition.SelfInstance(typeForThis, this.host.InternFactory), this.host.InternFactory); } else { ((ThisReference)thisReference).Type = NamedTypeDefinition.SelfInstance(typeForThis, this.host.InternFactory); } }
private void MakeInternal(NamedTypeDefinition nsType) { NestedTypeDefinition nestedTypeDef = nsType as NestedTypeDefinition; NamespaceTypeDefinition namespaceTypeDef = nsType as NamespaceTypeDefinition; if (namespaceTypeDef != null) { namespaceTypeDef.IsPublic = false; } else if (nestedTypeDef != null) { nestedTypeDef.Visibility = GetInternalVisibility(nestedTypeDef.Visibility); } }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { if (typeDefinition.Properties == null) { return; } var props = typeDefinition.Properties .Select(x => new { Property = x, Attributes = x.Attributes //.Select(y => (NamespaceTypeDefinition)y.Type) .Select(y => y.Type as NamespaceTypeDefinition) .Where(y => y != null && y.Name.Value == "PropertyChangedAttribute") }) .Where(x => x.Attributes.Any()); if (!props.Any()) { return; } foreach (var p in props.ToArray()) { if (p.Property.Setter == null) { throw new InvalidOperationException(); } var copier = new MetadataDeepCopier(host); var p2 = copier.Copy(p.Property); typeDefinition.Properties.Remove(p.Property); typeDefinition.Properties.Add(p2); var method = copier.Copy(p2.Setter.ResolvedMethod); _rewriter.PropertyName = p2.Name.Value; _rewriter.Type = method.ContainingTypeDefinition; method.Body = _rewriter.Rewrite(method.Body); method.ContainingTypeDefinition = typeDefinition; var m = typeDefinition.Methods.FirstOrDefault(x => x.Name == p2.Setter.ResolvedMethod.Name); typeDefinition.Methods.Remove(m); typeDefinition.Methods.Add(method); } }
public virtual void VisitType(NamedTypeDefinition typeDef) { if (typeDef.Methods != null) { for (int i = 0; i < typeDef.Methods.Count; i++) { VisitMethod(typeDef.Methods[i] as MethodDefinition, typeDef); } } if (typeDef.NestedTypes != null) { for (int i = 0; i < typeDef.NestedTypes.Count; i++) { VisitType(typeDef.NestedTypes[i] as NamedTypeDefinition); } } }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { List <IMethodDefinition> genericMethods = new List <IMethodDefinition>(); for (int i = 0, n = typeDefinition.Methods == null ? 0 : typeDefinition.Methods.Count; i < n; i++) { var member = typeDefinition.Methods[i]; if (member.IsGeneric) { genericMethods.Add(member); } } if (typeDefinition.Methods == null) { typeDefinition.Methods = new List <IMethodDefinition>(); } this.WithMoreGenericParameters(genericMethods, typeDefinition.Methods); base.RewriteChildren(typeDefinition); }
protected FieldDefinition CreateStateField(NamedTypeDefinition typeDefinition, TypeContract typeContract) { var host = CciHostEnvironment.GetInstance(); var field = new FieldDefinition { Name = host.NameTable.GetNameFor("$state"), Type = host.PlatformType.SystemInt32, Visibility = TypeMemberVisibility.Private, ContainingTypeDefinition = typeDefinition, InternFactory = typeDefinition.InternFactory, CompileTimeValue = new CompileTimeConstant { Type = host.PlatformType.SystemInt32, Value = 0 } }; // Como el $state es int, necesito el invariante ya que no puede ser negativo. // Se usa int en vez de uint, para que no haya problemas con la traduccion de BCT if (typeContract == null) { typeContract = new TypeContract(); } typeContract.Invariants.Add(new TypeInvariant { Condition = new GreaterThanOrEqual { LeftOperand = new BoundExpression { Definition = field, Instance = new ThisReference(), Type = field.Type }, RightOperand = new CompileTimeConstant { Type = host.PlatformType.SystemInt32, Value = 0 } } }); return(field); }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { var dict = new Dictionary <IModuleReference, IFieldDefinition>(); var moduleRefs = this.methodsProvider.RetrieveModuleRefs(typeDefinition); if (typeDefinition.Fields == null) { typeDefinition.Fields = new List <IFieldDefinition>(); } foreach (var moduleRef in moduleRefs) { var fieldDef = this.CreateFunctionPointerField(typeDefinition, "pl_" + moduleRef.Name.Value); var loadLibMethodDef = this.CreateLoadLibraryMethod(typeDefinition, moduleRef, fieldDef); typeDefinition.Fields.Add(fieldDef); typeDefinition.Methods.Add(loadLibMethodDef); dict.Add(moduleRef, fieldDef); } var methodDefinitions = this.methodsProvider.RetrieveMethodDefinitions(typeDefinition); foreach (var methodDefinition in methodDefinitions) { var fieldDef = this.CreateFunctionPointerField(typeDefinition, "p_" + methodDefinition.Name.Value); var initMethodDef = this.CreateInitMethod(methodDefinition, dict[methodDefinition.PlatformInvokeData.ImportModule], fieldDef, this.isLibraryInitialized, methodDefinition.PlatformInvokeData); var nativeMethodDef = this.CreateNativeMethod(methodDefinition); typeDefinition.Fields.Add(fieldDef); typeDefinition.Methods.Add(nativeMethodDef); typeDefinition.Methods.Add(initMethodDef); this.methodTransformationTable.Add(methodDefinition, new MethodTransformationMetadata(initMethodDef, fieldDef, nativeMethodDef)); } base.RewriteChildren(typeDefinition); }
delegate void Action(); //not defined in CLR v2. /// <summary> /// Saves the current closure fields. Allocates a new closure and updates the fields. Then calls the given delegate and /// restores the earlier state. /// </summary> private void AllocateClosureFor(object scope, List<IStatement> statements, Action rewriteScope) { Contract.Assume(!this.isInsideAnonymousMethod); var savedCurrentClosure = this.currentClosureClass; var savedCurrentClosureSelfInstance = this.currentClosureSelfInstance; var savedCurrentClosureInstance = this.currentClosureInstance; var savedCurrentClosureObject = this.currentClosureObject; var savedCurrentClosureLocal = this.currentClosureLocal; this.CreateClosureClass(); IFieldReference outerClosure = null; if (savedCurrentClosureLocal != null) { this.CreateClosureField(this.currentClosureSelfInstance, savedCurrentClosureSelfInstance, savedCurrentClosureInstance, savedCurrentClosureLocal.Name.Value); outerClosure = this.fieldReferencesForUseInsideThisMethod[this.currentClosureSelfInstance]; } var closureLocal = new LocalDefinition() { Type = this.currentClosureInstance, Name = this.host.NameTable.GetNameFor("CS$<>__locals"+this.closureClasses.Count) }; this.currentClosureObject = new BoundExpression() { Definition = closureLocal, Type = this.currentClosureInstance }; this.currentClosureLocal = closureLocal; if (this.closureLocalInstances == null) this.closureLocalInstances = new List<IExpression>(); this.closureLocalInstances.Add(this.currentClosureObject); rewriteScope(); Statement createClosure = new ExpressionStatement() { Expression = new Assignment() { Target = new TargetExpression() { Definition = closureLocal, Type = closureLocal.Type }, Source = new CreateObjectInstance() { MethodToCall = this.GetReferenceToDefaultConstructor(this.currentClosureInstance), Type = currentClosureSelfInstance, } } }; ILabeledStatement labeledStatement = null; for (int i = 0, n = statements.Count; i < n; i++) { labeledStatement = statements[i] as ILabeledStatement; if (labeledStatement != null) { createClosure = new LabeledStatement() { Label = labeledStatement.Label, Statement = createClosure }; createClosure.Locations.AddRange(labeledStatement.Locations); statements[i] = labeledStatement.Statement; break; } else if (statements[i] is IEmptyStatement) { continue; } else { var declSt = statements[i] as ILocalDeclarationStatement; if (declSt != null && declSt.InitialValue == null) continue; break; } } statements.Insert(0, createClosure); if (outerClosure != null) { statements.Insert(1, new ExpressionStatement() { Expression = new Assignment() { Target = new TargetExpression() { Instance = new BoundExpression() { Definition = closureLocal, Type = closureLocal.Type }, Definition = outerClosure, Type = closureLocal.Type }, Source = new BoundExpression() { Definition = savedCurrentClosureLocal, Type = savedCurrentClosureLocal.Type }, Type = closureLocal.Type, } }); } this.currentClosureClass = savedCurrentClosure; this.currentClosureSelfInstance = savedCurrentClosureSelfInstance; this.currentClosureInstance = savedCurrentClosureInstance; this.currentClosureObject = savedCurrentClosureObject; this.currentClosureLocal = savedCurrentClosureLocal; }
/// <summary> /// Creates a new nested type definition with a default constructor and no other members and adds it to this.closureClasses. /// If this.method is generic, then the closure class is generic as well, with the same /// number of type parameters (constrained in the same way) as the generic method. /// Initializes this.currentClosure, this.currentClosureInstance and this.currentClosureSelfInstance. /// </summary> private void CreateClosureClass() { if (this.closureClasses == null) this.closureClasses = new List<ITypeDefinition>(); NestedTypeDefinition closure = new NestedTypeDefinition(); var containingType = this.method.ContainingTypeDefinition; closure.Name = this.host.NameTable.GetNameFor("<"+this.method.Name+">c__DisplayClass"+closure.GetHashCode()); closure.Attributes = new List<ICustomAttribute>(1) { this.compilerGenerated }; closure.BaseClasses = new List<ITypeReference>(1) { this.host.PlatformType.SystemObject }; closure.ContainingTypeDefinition = containingType; closure.Fields = new List<IFieldDefinition>(); closure.InternFactory = this.host.InternFactory; closure.IsBeforeFieldInit = true; closure.IsClass = true; closure.IsSealed = true; closure.Layout = LayoutKind.Auto; closure.Methods = new List<IMethodDefinition>(); closure.StringFormat = StringFormatKind.Ansi; closure.Visibility = TypeMemberVisibility.Private; this.closureClasses.Add(closure); this.currentClosureClass = closure; //generics if (this.method.IsGeneric) { Dictionary<ushort, IGenericParameterReference> genericMethodParameterMap = new Dictionary<ushort, IGenericParameterReference>(); this.genericMethodParameterMap = genericMethodParameterMap; bool foundConstraints = false; var genericTypeParameters = new List<IGenericTypeParameter>(this.method.GenericParameterCount); closure.GenericParameters = genericTypeParameters; foreach (var genericMethodParameter in this.method.GenericParameters) { var copyOfGenericMethodParameter = this.copier.Copy(genericMethodParameter); //so that we have mutable constraints to rewrite var genericTypeParameter = new GenericTypeParameter(); genericTypeParameter.Copy(copyOfGenericMethodParameter, this.host.InternFactory); genericTypeParameter.DefiningType = closure; if (genericTypeParameter.Constraints != null && genericTypeParameter.Constraints.Count > 0) foundConstraints = true; genericTypeParameters.Add(genericTypeParameter); genericMethodParameterMap.Add(copyOfGenericMethodParameter.Index, genericTypeParameter); } if (foundConstraints) { //Fix up any self references that might lurk inside constraints. closure.GenericParameters = new GenericParameterRewriter(this.host, genericMethodParameterMap).Rewrite(genericTypeParameters); } var instanceType = closure.InstanceType; var genericArguments = IteratorHelper.GetConversionEnumerable<IGenericMethodParameter, ITypeReference>(this.method.GenericParameters); this.currentClosureInstance = new Immutable.GenericTypeInstanceReference(instanceType.GenericType, genericArguments, this.host.InternFactory); this.currentClosureSelfInstance = instanceType; } else { //if any of the containing types are generic, we need an instance or a specialized nested type. this.currentClosureInstance = NestedTypeDefinition.SelfInstance(closure, this.host.InternFactory); this.currentClosureSelfInstance = this.currentClosureInstance; } //default constructor var block = new BlockStatement(); block.Statements.Add( new ExpressionStatement() { Expression = new MethodCall() { ThisArgument = new ThisReference() { Type = this.currentClosureSelfInstance }, MethodToCall = this.objectCtor, Type = this.host.PlatformType.SystemVoid } } ); var constructorBody = new SourceMethodBody(this.host, this.sourceLocationProvider) { LocalsAreZeroed = true, IsNormalized = true, Block = block }; var defaultConstructor = new MethodDefinition() { Body = constructorBody, ContainingTypeDefinition = closure, CallingConvention = CallingConvention.HasThis, InternFactory = this.host.InternFactory, IsCil = true, IsHiddenBySignature = true, IsRuntimeSpecial = true, IsSpecialName = true, Name = this.host.NameTable.Ctor, Type = this.host.PlatformType.SystemVoid, Visibility = TypeMemberVisibility.Public, }; constructorBody.MethodDefinition = defaultConstructor; closure.Methods.Add(defaultConstructor); }
public override IMethodBody Rewrite(IMethodBody methodBody) { this.cdfg = ControlAndDataFlowGraph <BasicBlock <Instruction>, Instruction> .GetControlAndDataFlowGraphFor(this.host, methodBody); this.ilGenerator = new ILGenerator(host, methodBody.MethodDefinition); var numberOfBlocks = this.cdfg.BlockFor.Count; this.labelFor = new Hashtable <ILGeneratorLabel>(numberOfBlocks); this.counterFieldsForCurrentMethod = new NestedTypeDefinition() { BaseClasses = new List <ITypeReference>(1) { this.host.PlatformType.SystemObject }, ContainingTypeDefinition = methodBody.MethodDefinition.ContainingTypeDefinition, Fields = new List <IFieldDefinition>((int)numberOfBlocks * 2), Methods = new List <IMethodDefinition>(1), InternFactory = this.host.InternFactory, IsBeforeFieldInit = true, IsClass = true, IsSealed = true, IsAbstract = true, Name = this.host.NameTable.GetNameFor(methodBody.MethodDefinition.Name + "_Counters" + methodBody.MethodDefinition.InternedKey), Visibility = TypeMemberVisibility.Assembly, }; this.fieldOffsets = new List <uint>((int)numberOfBlocks * 2); foreach (var exceptionInfo in methodBody.OperationExceptionInformation) { this.ilGenerator.AddExceptionHandlerInformation(exceptionInfo.HandlerKind, exceptionInfo.ExceptionType, this.GetLabelFor(exceptionInfo.TryStartOffset), this.GetLabelFor(exceptionInfo.TryEndOffset), this.GetLabelFor(exceptionInfo.HandlerStartOffset), this.GetLabelFor(exceptionInfo.HandlerEndOffset), exceptionInfo.HandlerKind == HandlerKind.Filter ? this.GetLabelFor(exceptionInfo.FilterDecisionStartOffset) : null); } if (this.pdbReader == null) { foreach (var localDef in methodBody.LocalVariables) { this.ilGenerator.AddVariableToCurrentScope(localDef); } } else { foreach (var ns in this.pdbReader.GetNamespaceScopes(methodBody)) { foreach (var uns in ns.UsedNamespaces) { this.ilGenerator.UseNamespace(uns.NamespaceName.Value); } } this.scopeEnumerator = this.pdbReader.GetLocalScopes(methodBody).GetEnumerator(); this.scopeEnumeratorIsValid = this.scopeEnumerator.MoveNext(); } foreach (var block in this.cdfg.AllBlocks) { this.InstrumentBlock(block); } while (this.scopeStack.Count > 0) { this.ilGenerator.EndScope(); this.scopeStack.Pop(); } this.ilGenerator.AdjustBranchSizesToBestFit(); this.InjectMethodToDumpCounters(); return(new ILGeneratorMethodBody(this.ilGenerator, methodBody.LocalsAreZeroed, (ushort)(methodBody.MaxStack + 2), methodBody.MethodDefinition, methodBody.LocalVariables, IteratorHelper.GetSingletonEnumerable((ITypeDefinition)this.counterFieldsForCurrentMethod))); }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { // Remove interfaces List <ITypeReference> newList = new List <ITypeReference>(); if (typeDefinition.Interfaces != null) { foreach (ITypeReference iface in typeDefinition.Interfaces) { INamedTypeDefinition canonicalInterface = Util.CanonicalizeType(iface); // TODO: m_currentTrimAssembly is bad if we want to trim more than one assembly in one pass. // Keep implemented interfaces that are present in the include set, or defined in a different assembly. TypeElement element = _currentTrimAssembly.GetTypeElement(Util.FullyQualifiedTypeNameFromType(canonicalInterface)); if (element != null || !_includeSet.Assemblies.ContainsKey(Util.GetDefiningAssembly(canonicalInterface).Name.Value)) { // No need to visit iface here because base.Visit will do that newList.Add(iface); } } } typeDefinition.Interfaces = newList; // Remove SerializableAttribute if (_removeSerializabilityInfo) { typeDefinition.IsSerializable = false; } // Ensure we visit all children base.RewriteChildren(typeDefinition); // Adding this type to the flat list of types for this assembly. This is required because the MetadataRewriter doesn't update the AllTypes property of the assembly. if (_currentTrimAssembly.GetTypeElement(Util.GetTypeName(typeDefinition)) != null || _systemTypes.Contains(Util.GetTypeName(typeDefinition))) { _allTypesList.Add(typeDefinition); } if (typeDefinition.HasDeclarativeSecurity && typeDefinition.SecurityAttributes.Count == 0) { typeDefinition.HasDeclarativeSecurity = false; } // Add an empty constructor to constructor-less types if (_ensureConstructorsPresent) { bool hasConstructors = false; foreach (IMethodDefinition method in typeDefinition.Methods) { if (method.IsConstructor && !method.IsStatic) { hasConstructors = true; } } if (!hasConstructors && !_systemTypes.Contains(typeDefinition.Name.Value) && typeDefinition.IsClass && !typeDefinition.IsStatic) { MethodDefinition method = new MethodDefinition(); method.IsSpecialName = true; method.Name = this.host.NameTable.Ctor; method.CallingConvention = CallingConvention.HasThis; method.ContainingTypeDefinition = typeDefinition; method.Parameters = new List <IParameterDefinition>(); MethodBody methodBody = new MethodBody(); method.Body = methodBody; method.Type = typeDefinition.PlatformType.SystemVoid; method.Visibility = TypeMemberVisibility.Private; // To avoid warnings when round-tripping these through ildasm & ilasm, put 1 return instruction // in the method body. Unfortunately this doesn't seem to work. List <IOperation> instrs = new List <IOperation>(1); Operation o = new Operation(); o.OperationCode = OperationCode.Ret; o.Offset = 0; instrs.Add(o); methodBody.Operations = instrs; methodBody.MethodDefinition = method; //this.path.Push(typeDefinition); typeDefinition.Methods.Add(this.Rewrite(method)); //this.path.Pop(); } } }
//not defined in CLR v2. /// <summary> /// Saves the current closure fields. Allocates a new closure and updates the fields. Then calls the given delegate and /// restores the earlier state. /// </summary> private void AllocateClosureFor(object scope, List<IStatement> statements, Action rewriteScope) { Contract.Assume(!this.isInsideAnonymousMethod); var savedCurrentClosure = this.currentClosureClass; var savedCurrentClosureSelfInstance = this.currentClosureSelfInstance; var savedCurrentClosureInstance = this.currentClosureInstance; var savedCurrentClosureObject = this.currentClosureObject; var savedCurrentClosureLocal = this.currentClosureLocal; this.CreateClosureClass(); IFieldReference outerClosure = null; if (savedCurrentClosureLocal != null) { this.CreateClosureField(this.currentClosureSelfInstance, savedCurrentClosureSelfInstance, savedCurrentClosureInstance, savedCurrentClosureLocal.Name.Value); outerClosure = this.fieldReferencesForUseInsideThisMethod[this.currentClosureSelfInstance]; } var closureLocal = new LocalDefinition() { Type = this.currentClosureInstance, Name = this.host.NameTable.GetNameFor("CS$<>__locals"+this.closureClasses.Count) }; this.currentClosureObject = new BoundExpression() { Definition = closureLocal, Type = this.currentClosureInstance }; this.currentClosureLocal = closureLocal; if (this.closureLocalInstances == null) this.closureLocalInstances = new List<IExpression>(); this.closureLocalInstances.Add(this.currentClosureObject); rewriteScope(); statements.Insert(0, new ExpressionStatement() { Expression = new Assignment() { Target = new TargetExpression() { Definition = closureLocal, Type = closureLocal.Type }, Source = new CreateObjectInstance() { MethodToCall = this.GetReferenceToDefaultConstructor(this.currentClosureInstance), Type = currentClosureSelfInstance, } } }); if (outerClosure != null) { statements.Insert(1, new ExpressionStatement() { Expression = new Assignment() { Target = new TargetExpression() { Instance = new BoundExpression() { Definition = closureLocal }, Definition = outerClosure }, Source = new BoundExpression() { Definition = savedCurrentClosureLocal } } }); } this.currentClosureClass = savedCurrentClosure; this.currentClosureSelfInstance = savedCurrentClosureSelfInstance; this.currentClosureInstance = savedCurrentClosureInstance; this.currentClosureObject = savedCurrentClosureObject; this.currentClosureLocal = savedCurrentClosureLocal; }
protected TypeContract RemoveInvariantMethods(ITypeDefinition typeDefinition, NamedTypeDefinition cciTypeDefinition) { var tc = typeDefinition.TypeContract() as TypeContract; if (tc != null) { tc.Invariants.Clear(); var methods = ContractHelper.GetInvariantMethods(cciTypeDefinition).ToList(); foreach (var m in methods) { cciTypeDefinition.Methods.Remove(m); } } return(tc); }
private void PruneInterfacesAndExplicitImplementationOverrides(NamedTypeDefinition typeDefinition) { #region Prune the list of interfaces this type implements (if necessary) if (typeDefinition.Interfaces != null && 0 < typeDefinition.Interfaces.Count) { var newInterfaceList = new List<ITypeReference>(); foreach (var iface in typeDefinition.Interfaces) { if (!this.whackedTypes.ContainsKey(iface.InternedKey)) newInterfaceList.Add(iface); } typeDefinition.Interfaces = newInterfaceList; } #endregion Prune the list of interfaces this type implements (if necessary) #region Prune the list of explicit implementation overrides (as necessary) if (typeDefinition.ExplicitImplementationOverrides != null && 0 < typeDefinition.ExplicitImplementationOverrides.Count) { var newExplicitImplementationOverrides = new List<IMethodImplementation>(); foreach (IMethodImplementation methodImpl in typeDefinition.ExplicitImplementationOverrides) { if (!this.whackedMethods.ContainsKey(methodImpl.ImplementingMethod.InternedKey)) { newExplicitImplementationOverrides.Add(methodImpl); } } typeDefinition.ExplicitImplementationOverrides = newExplicitImplementationOverrides; } #endregion Prune the list of explicit implementation overrides (as necessary) }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { if (typeDefinition is IGenericParameter) return; if (TypeHelper.IsCompilerGenerated(typeDefinition)) return; Contract.Assume(this.copier.OriginalFor.ContainsKey(typeDefinition)); var origTypeDefinition = this.copier.OriginalFor[typeDefinition]; Contract.Assume(this.thingsToKeep.Contains(origTypeDefinition)); // Lists can only shrink. if (typeDefinition.Methods != null) { var methods_prime = new List<IMethodDefinition>(typeDefinition.Methods.Count); foreach (var m in typeDefinition.Methods) { Contract.Assume(this.copier.OriginalFor.ContainsKey(m)); var orig = (IMethodDefinition) this.copier.OriginalFor[m]; if (this.thingsToKeep.Any(ttk => { var m2 = ttk as IMethodReference; return m2 != null && m2.InternedKey == orig.InternedKey; })) { methods_prime.Add(m); this.Rewrite(m); } } typeDefinition.Methods = methods_prime; } if (typeDefinition.Fields != null) { var fields_prime = new List<IFieldDefinition>(typeDefinition.Fields.Count); foreach (var f in typeDefinition.Fields) { Contract.Assume(this.copier.OriginalFor.ContainsKey(f)); var orig = (IFieldDefinition) this.copier.OriginalFor[f]; if (this.thingsToKeep.Any(ttk => { var f2 = ttk as IFieldReference; return f2 != null && f2.InternedKey == orig.InternedKey; })) { fields_prime.Add(f); } } typeDefinition.Fields = fields_prime; } if (typeDefinition.NestedTypes != null) { var nestedTypes_prime = new List<INestedTypeDefinition>(typeDefinition.NestedTypes.Count); foreach (var nt in typeDefinition.NestedTypes) { Contract.Assume(this.copier.OriginalFor.ContainsKey(nt)); var orig = (INestedTypeDefinition) this.copier.OriginalFor[nt]; if (this.thingsToKeep.Any(ttk => { var nt2 = ttk as INestedTypeReference; return nt2 != null && nt2.InternedKey == orig.InternedKey; })) { nestedTypes_prime.Add(nt); this.Rewrite(nt); } } typeDefinition.NestedTypes = nestedTypes_prime; } if (typeDefinition.Properties != null) { var properties_prime = new List<IPropertyDefinition>(typeDefinition.Properties.Count); foreach (var p in typeDefinition.Properties) { Contract.Assume(this.copier.OriginalFor.ContainsKey(p)); var orig = this.copier.OriginalFor[p]; var keep = this.thingsToKeep.Contains(orig); // REVIEW: How to do this without relying on object identity? prop defs don't have interned keys. // Even if it isn't in the list, need to check if any of the accessors are being kept: if so, keep the property. // But need to check the accessors even if the property is in the list: might need to delete one of the accessors if that one isn't being kept. var originalProperty = (IPropertyDefinition)orig; var keepGetter = originalProperty.Getter != null && this.thingsToKeep.Any(ttk => { var m = ttk as IMethodReference; return m != null && m.InternedKey == originalProperty.Getter.InternedKey; }); var keepSetter = originalProperty.Setter != null && this.thingsToKeep.Any(ttk => { var m = ttk as IMethodReference; return m != null && m.InternedKey == originalProperty.Setter.InternedKey; }); if (keep || keepGetter || keepSetter) { properties_prime.Add(p); this.Rewrite(p); } } typeDefinition.Properties = properties_prime; } // TODO: Events. Anything else? }
public virtual void VisitMethod(MethodDefinition methodDef, NamedTypeDefinition typeDef) { }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { // Remove interfaces List<ITypeReference> newList = new List<ITypeReference>(); if (typeDefinition.Interfaces != null) { foreach (ITypeReference iface in typeDefinition.Interfaces) { INamedTypeDefinition canonicalInterface = Util.CanonicalizeType(iface); // TODO: m_currentTrimAssembly is bad if we want to trim more than one assembly in one pass. // Keep implemented interfaces that are present in the include set, or defined in a different assembly. TypeElement element = _currentTrimAssembly.GetTypeElement(Util.FullyQualifiedTypeNameFromType(canonicalInterface)); if (element != null || !_includeSet.Assemblies.ContainsKey(Util.GetDefiningAssembly(canonicalInterface).Name.Value)) { // No need to visit iface here because base.Visit will do that newList.Add(iface); } } } typeDefinition.Interfaces = newList; // Remove SerializableAttribute if (_removeSerializabilityInfo) { typeDefinition.IsSerializable = false; } // Ensure we visit all children base.RewriteChildren(typeDefinition); // Adding this type to the flat list of types for this assembly. This is required because the MetadataRewriter doesn't update the AllTypes property of the assembly. if (_currentTrimAssembly.GetTypeElement(Util.GetTypeName(typeDefinition)) != null || _systemTypes.Contains(Util.GetTypeName(typeDefinition))) _allTypesList.Add(typeDefinition); if (typeDefinition.HasDeclarativeSecurity && typeDefinition.SecurityAttributes.Count == 0) { typeDefinition.HasDeclarativeSecurity = false; } // Add an empty constructor to constructor-less types if (_ensureConstructorsPresent) { bool hasConstructors = false; foreach (IMethodDefinition method in typeDefinition.Methods) { if (method.IsConstructor && !method.IsStatic) { hasConstructors = true; } } if (!hasConstructors && !_systemTypes.Contains(typeDefinition.Name.Value) && typeDefinition.IsClass && !typeDefinition.IsStatic) { MethodDefinition method = new MethodDefinition(); method.IsSpecialName = true; method.Name = this.host.NameTable.Ctor; method.CallingConvention = CallingConvention.HasThis; method.ContainingTypeDefinition = typeDefinition; method.Parameters = new List<IParameterDefinition>(); MethodBody methodBody = new MethodBody(); method.Body = methodBody; method.Type = typeDefinition.PlatformType.SystemVoid; method.Visibility = TypeMemberVisibility.Private; // To avoid warnings when round-tripping these through ildasm & ilasm, put 1 return instruction // in the method body. Unfortunately this doesn't seem to work. List<IOperation> instrs = new List<IOperation>(1); Operation o = new Operation(); o.OperationCode = OperationCode.Ret; o.Offset = 0; instrs.Add(o); methodBody.Operations = instrs; methodBody.MethodDefinition = method; //this.path.Push(typeDefinition); typeDefinition.Methods.Add(this.Rewrite(method)); //this.path.Pop(); } } }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { List <IDefinition> methodsToDuplicate = new List <IDefinition>(); List <IMethodDefinition> newMethods = new List <IMethodDefinition>(); for (int i = 0, n = typeDefinition.Methods == null ? 0 : typeDefinition.Methods.Count; i < n; i++) { var member = typeDefinition.Methods[i]; if (Marked(member)) { methodsToDuplicate.Add(member); } else { newMethods.Add(member); } } this.deepCopier.Copy(methodsToDuplicate); foreach (IMethodDefinition m in methodsToDuplicate) { newMethods.Add(m); } typeDefinition.Methods = newMethods; List <IDefinition> fieldsToDuplicate = new List <IDefinition>(); var newFields = new List <IFieldDefinition>(); for (int i = 0, n = typeDefinition.Fields == null ? 0 : typeDefinition.Fields.Count; i < n; i++) { var member = typeDefinition.Fields[i]; if (Marked(member)) { fieldsToDuplicate.Add(member); } else { newFields.Add(member); } } this.deepCopier.Copy(fieldsToDuplicate); foreach (IFieldDefinition f in fieldsToDuplicate) { newFields.Add(f); } typeDefinition.Fields = newFields; List <IDefinition> propertiesToDuplicate = new List <IDefinition>(); var newProperties = new List <IPropertyDefinition>(); for (int i = 0, n = typeDefinition.Properties == null ? 0 : typeDefinition.Properties.Count; i < n; i++) { var member = typeDefinition.Properties[i]; if (Marked(member)) { propertiesToDuplicate.Add(member); } else { newProperties.Add(member); } } this.deepCopier.Copy(propertiesToDuplicate); foreach (IPropertyDefinition p in propertiesToDuplicate) { newProperties.Add(p); } typeDefinition.Properties = newProperties; }
public override void RewriteChildren(NamedTypeDefinition typeDefinition) { if (typeDefinition is IGenericParameter) { return; } if (TypeHelper.IsCompilerGenerated(typeDefinition)) { return; } Contract.Assume(this.copier.OriginalFor.ContainsKey(typeDefinition)); var origTypeDefinition = this.copier.OriginalFor[typeDefinition]; Contract.Assume(this.thingsToKeep.Contains(origTypeDefinition)); // Lists can only shrink. if (typeDefinition.Methods != null) { var methods_prime = new List <IMethodDefinition>(typeDefinition.Methods.Count); foreach (var m in typeDefinition.Methods) { Contract.Assume(this.copier.OriginalFor.ContainsKey(m)); var orig = (IMethodDefinition)this.copier.OriginalFor[m]; if (this.thingsToKeep.Any(ttk => { var m2 = ttk as IMethodReference; return(m2 != null && m2.InternedKey == orig.InternedKey); })) { methods_prime.Add(m); this.Rewrite(m); } } typeDefinition.Methods = methods_prime; } if (typeDefinition.Fields != null) { var fields_prime = new List <IFieldDefinition>(typeDefinition.Fields.Count); foreach (var f in typeDefinition.Fields) { Contract.Assume(this.copier.OriginalFor.ContainsKey(f)); var orig = (IFieldDefinition)this.copier.OriginalFor[f]; if (this.thingsToKeep.Any(ttk => { var f2 = ttk as IFieldReference; return(f2 != null && f2.InternedKey == orig.InternedKey); })) { fields_prime.Add(f); } } typeDefinition.Fields = fields_prime; } if (typeDefinition.NestedTypes != null) { var nestedTypes_prime = new List <INestedTypeDefinition>(typeDefinition.NestedTypes.Count); foreach (var nt in typeDefinition.NestedTypes) { Contract.Assume(this.copier.OriginalFor.ContainsKey(nt)); var orig = (INestedTypeDefinition)this.copier.OriginalFor[nt]; if (this.thingsToKeep.Any(ttk => { var nt2 = ttk as INestedTypeReference; return(nt2 != null && nt2.InternedKey == orig.InternedKey); })) { nestedTypes_prime.Add(nt); this.Rewrite(nt); } } typeDefinition.NestedTypes = nestedTypes_prime; } if (typeDefinition.Properties != null) { var properties_prime = new List <IPropertyDefinition>(typeDefinition.Properties.Count); foreach (var p in typeDefinition.Properties) { Contract.Assume(this.copier.OriginalFor.ContainsKey(p)); var orig = this.copier.OriginalFor[p]; var keep = this.thingsToKeep.Contains(orig); // REVIEW: How to do this without relying on object identity? prop defs don't have interned keys. // Even if it isn't in the list, need to check if any of the accessors are being kept: if so, keep the property. // But need to check the accessors even if the property is in the list: might need to delete one of the accessors if that one isn't being kept. var originalProperty = (IPropertyDefinition)orig; var keepGetter = originalProperty.Getter != null && this.thingsToKeep.Any(ttk => { var m = ttk as IMethodReference; return(m != null && m.InternedKey == originalProperty.Getter.InternedKey); }); var keepSetter = originalProperty.Setter != null && this.thingsToKeep.Any(ttk => { var m = ttk as IMethodReference; return(m != null && m.InternedKey == originalProperty.Setter.InternedKey); }); if (keep || keepGetter || keepSetter) { properties_prime.Add(p); this.Rewrite(p); } } typeDefinition.Properties = properties_prime; } // TODO: Events. Anything else? }