/// <summary> /// Adds new method to IL code stream and metadata. /// </summary> /// <param name="method">Interface describing method.</param> public void AddMethod(IMethod method) { uint RVA = (uint)dIL.Count + 4; MethodDefinition targtMet, emittedMehtod; targtMet = Manager.MetadataManager.FindMethod(Manager.ResourceManager.NewAssembly, Manager.ResourceManager.NewAssemblyName, method); if (targtMet == null) { throw new TranslatingException("Method " + method.ToString() + " could not be found in emitted module"); } MethodTranslator translator = new MethodTranslator(this); MethodDescriptor log = translator.TranslateNewMethod(targtMet, out emittedMehtod); Manager.MetadataManager.OldEmitter.CorMetaDataEmit.SetRVA(log.destToken, RVA); TypeDefinition typeDef = Manager.MetadataManager.FindTypeDefinition(Manager.ResourceManager.OldAssembly, Manager.ResourceManager.CurrentModule.Name, method.DeclaringType.FullyQualifiedName); if (typeDef != null) { typeDef.Methods.Add(emittedMehtod); } Manager.ResourceManager.CurrentModule.RemoveFromLoadedTypes(targtMet.DeclaringType.FullName); dIL.AddRange(log.codeIL); if (SymbolWriter != null) { List <SequencePoint> points = SymbolWriter.EmitMethod(log.destToken, log.srcToken); NewMethodsSequencePoints.Add(targtMet.MetadataToken.ToUInt32(), points); } }
/// <summary> /// Change IL code and metadata for property. /// </summary> /// <param name="property">Interaface with info abour property.</param> /// <param name="isGetter">Determines whether it is getter method for property.</param> public void ChangeProperty(IProperty property, bool isGetter) { // Method RVA is offset to start of byte buffer uint RVA = (uint)dIL.Count + 4; PropertyDefinition targtProp, targtPropOld; MethodDefinition targtMet, targtMetOld; // Find appropriete new version of method in new assembly. targtProp = Manager.MetadataManager.FindProperty(Manager.ResourceManager.NewAssembly, Manager.ResourceManager.NewAssemblyName, property); if (targtProp == null) { new TranslatingException("Property " + property.ToString() + " could not be found in emitted module"); } // Find appropriete original version of method in running assembly. targtPropOld = Manager.MetadataManager.FindProperty(Manager.ResourceManager.OldAssembly, Manager.ResourceManager.CurrentModule.Name, property); if (targtPropOld == null) { new TranslatingException("Property " + property.ToString() + " could not be found in debugged module"); } targtMet = (isGetter ? targtProp.GetMethod : targtProp.SetMethod); targtMetOld = (isGetter ? targtPropOld.GetMethod : targtPropOld.SetMethod); SequencePointRemapper remapper = genSequencePointRemapper(targtMetOld, targtMet); // Translate tokens in methods IL code. MethodTranslator translator = new MethodTranslator(this); Dictionary <int, int> placeholder; MethodDescriptor log = translator.TranslateMethod(targtMet, targtMetOld, remapper, out placeholder); log.newRva = RVA; // Set method RVA. Manager.MetadataManager.OldEmitter.CorMetaDataEmit.SetRVA(targtMetOld.MetadataToken.ToUInt32(), RVA); // Store methods IL to buffer dIL.AddRange(log.codeIL); if (SymbolWriter != null) { SymbolWriter.EmitMethod(log.destToken, log.srcToken, placeholder); } }