public MemoryVisitor(CodeContractAwareHostEnvironment host, PdbReader pdbReader, ContractProvider contractProvider, MemoryContractsInformation memoryContractsInformation, PointsToInformation pointsToInformation) { _host = host; _pdbReader = pdbReader; _contractProvider = contractProvider; _memoryContractsInformation = memoryContractsInformation; _errorReportItems = new List<ErrorReportItem>(); _pointsToInformation = pointsToInformation; }
private static MemoryContractsInformation ExtractMemoryContractsFromModule(CodeContractAwareHostEnvironment host, IModule module) { var memoryContractsInformation = new MemoryContractsInformation(); if (_visitedModules.Contains(module)) { return memoryContractsInformation; } _visitedModules.Add(module); if (module != null && module != Dummy.Module && module != Dummy.Assembly) { PdbReader pdbReader = null; string pdbFile = Path.ChangeExtension(module.Location, "pdb"); if (File.Exists(pdbFile)) { using (var pdbStream = File.OpenRead(pdbFile)) { pdbReader = new PdbReader(pdbStream, host); } } module = Decompiler.GetCodeModelFromMetadataModel(host, module, pdbReader); var extractor = new MemoryContractsExtractor(); extractor.Visit(module); memoryContractsInformation.MethodsTmpTypes = extractor.MethodsTmpTypes; memoryContractsInformation.MethodsTmpContracts = extractor.MethodsTmpContracts; memoryContractsInformation.MethodsTmpContractsWithConds = extractor.MethodsTmpContractsWithConds; memoryContractsInformation.MethodsRsdTypes = extractor.MethodsRsdTypes; memoryContractsInformation.MethodsRsdContracts = extractor.MethodsRsdContracts; memoryContractsInformation.MethodsRsdContractsWithConds = extractor.MethodsRsdContractsWithConds; memoryContractsInformation.MethodsRsdExprs = extractor.MethodsRsdExprs; //merge the contracts of the referenced assemblies foreach (var assemblyReference in module.AssemblyReferences) { //skip assemblies that we know don't have memory contracts if (!new List<string>() { "mscorlib", "Contracts", "System", "Microsoft" }.Exists(s => assemblyReference.Name.Value.StartsWith(s))) { var referencedAssembly = host.LoadAssembly(assemblyReference.AssemblyIdentity); var referencedModuleMemoryContractsInformation = ExtractMemoryContractsFromModule(host, referencedAssembly); if (referencedModuleMemoryContractsInformation.MethodsTmpTypes != null) { foreach (var methodName in referencedModuleMemoryContractsInformation.MethodsTmpTypes.Keys) { memoryContractsInformation.MethodsTmpTypes[methodName] = referencedModuleMemoryContractsInformation.MethodsTmpTypes[methodName]; } } if (referencedModuleMemoryContractsInformation.MethodsRsdTypes != null) { foreach (var methodName in referencedModuleMemoryContractsInformation.MethodsRsdTypes.Keys) { memoryContractsInformation.MethodsRsdTypes[methodName] = referencedModuleMemoryContractsInformation.MethodsRsdTypes[methodName]; } } } } } return memoryContractsInformation; }
private static List<ErrorReportItem> RewriteAssembly(CodeContractAwareHostEnvironment host, string assemblyFullPath, MemoryContractsInformation memoryContractsInformation, PointsToInformation pointsToInformation) { var module = host.LoadUnitFrom(assemblyFullPath) as IModule; PdbReader pdbReader = null; string pdbFile = Path.ChangeExtension(module.Location, "pdb"); if (File.Exists(pdbFile)) { using (var pdbStream = File.OpenRead(pdbFile)) { pdbReader = new PdbReader(pdbStream, host); } } if (module != null && module != Dummy.Module && module != Dummy.Assembly) { var mutableModule = Decompiler.GetCodeModelFromMetadataModel(host, module, pdbReader); using (pdbReader) { var contractProvider = Microsoft.Cci.MutableContracts.ContractHelper.ExtractContracts(host, mutableModule, pdbReader, pdbReader); var mutator = new MemoryVisitor(host, pdbReader, contractProvider, memoryContractsInformation, pointsToInformation); mutator.Visit(mutableModule); Microsoft.Cci.MutableContracts.ContractHelper.InjectContractCalls(host, mutableModule, contractProvider, pdbReader); Stream peStream = File.Create(Path.ChangeExtension(mutableModule.Location, ".mod.dll")); if (pdbReader == null) { PeWriter.WritePeToStream(mutableModule, host, peStream); } else { using (var pdbWriter = new PdbWriter(Path.ChangeExtension(pdbFile, ".mod.pdb"), pdbReader)) { PeWriter.WritePeToStream(mutableModule, host, peStream, pdbReader, pdbReader, pdbWriter); } } peStream.Close(); return mutator.ErrorReportItems; } } return null; }