void RoundTripCodeCopier(string assemblyName, string pdbName, bool allowCheckerFail) { PeVerifyResult expectedResult = PeVerify.VerifyAssembly(assemblyName); IAssembly assembly = LoadAssembly(assemblyName); if (pdbName != null) { using (var f = File.OpenRead(pdbName)) { using (var pdbReader = new PdbReader(f, host)) { var codeAssembly = Decompiler.GetCodeModelFromMetadataModel(this.host, assembly, pdbReader); CodeDeepCopier copier = new CodeDeepCopier(host); codeAssembly = copier.Copy(codeAssembly); Checker checker = new Checker(this.host); checker.Traverse(codeAssembly); Debug.Assert(checker.Errors.Count == 0); AssertWriteToPeFile(expectedResult, codeAssembly, pdbReader); } } } else { var codeAssembly = Decompiler.GetCodeModelFromMetadataModel(this.host, assembly, null); CodeDeepCopier copier = new CodeDeepCopier(host); codeAssembly = copier.Copy(codeAssembly); Checker checker = new Checker(this.host); checker.Traverse(codeAssembly); Debug.Assert(allowCheckerFail || checker.Errors.Count == 0); AssertWriteToPeFile(expectedResult, codeAssembly, null); } }
public CciModuleSource(ProjectFilesClone filesClone) : this() { foreach (var assembliesPath in filesClone.Assemblies) { var sss = new CodeDeepCopier(Host); var m = DecompileFile(assembliesPath.Path); var copied = sss.Copy(m.Module); m.Module = copied; _moduleInfoList.Add(m); } }
protected List <NamespaceTypeDefinition> WithMoreGenericParameters(List <INamespaceTypeDefinition> genericTypes) { var copier = new CodeDeepCopier(this.host); var copies = new List <NamespaceTypeDefinition>(); foreach (var genericType in genericTypes) { var copy = copier.Copy(genericType); copy.Name = this.host.NameTable.GetNameFor(genericType.Name.Value + "<<>>"); copies.Add(copy); this.AddToAllTypes(copy); this.AddGenericParamInPlace(copy); var fixer = new ReferenceFixer(this.host, copy); fixer.Rewrite(copy); } return(copies); }
void RoundTripAddGenericMethodParameter(string assemblyName, string pdbName) { PeVerifyResult expectedResult = PeVerify.VerifyAssembly(assemblyName); IAssembly assembly = LoadAssembly(assemblyName); using (var f = File.OpenRead(pdbName)) { using (var pdbReader = new PdbReader(f, host)) { var codeAssembly = Decompiler.GetCodeModelFromMetadataModel(this.host, assembly, pdbReader); var copier = new CodeDeepCopier(this.host); codeAssembly = copier.Copy(codeAssembly); var adder = new AddGenericMethodParameters(host); var rewrittenAssembly = adder.Rewrite(codeAssembly); Checker checker = new Checker(this.host); checker.Traverse(rewrittenAssembly); Debug.Assert(checker.Errors.Count == 0); AssertWriteToPeFile(expectedResult, rewrittenAssembly, pdbReader); } } }
private void WithMoreGenericParameters(List <IMethodDefinition> genericMethods, List <IMethodDefinition> result) { var copier = new CodeDeepCopier(this.host); var copies = new List <MethodDefinition>(); foreach (var method in genericMethods) { var copy = copier.Copy(method); copy.Name = this.host.NameTable.GetNameFor(method.Name.Value + "<<>>"); this.nameMapping[method.Name.UniqueKey] = copy.Name.UniqueKey; this.newMethods[copy.Name.UniqueKey] = copy; result.Add(copy); copies.Add(copy); } foreach (var copy in copies) { this.AddGenericParameter(copy); var fixer = new ReferenceFixer(this.host, copy, this.nameMapping, this.newMethods); fixer.Rewrite(copy); } }
void RoundTripCopyAndExecute(string assemblyName, string pdbName, bool verificationMayFail) { PeVerifyResult expectedResult = !verificationMayFail ? PeVerify.VerifyAssembly(assemblyName) : PeVerify.RunPeVerifyOnAssembly(assemblyName); string expectedOutput = Execute(assemblyName); IAssembly assembly = LoadAssembly(assemblyName); using (var f = File.OpenRead(pdbName)) { using (var pdbReader = new PdbReader(f, host)) { var codeAssembly = Decompiler.GetCodeModelFromMetadataModel(this.host, assembly, pdbReader); var copier = new CodeDeepCopier(host); codeAssembly = copier.Copy(codeAssembly); Checker checker = new Checker(this.host); checker.Traverse(codeAssembly); Debug.Assert(checker.Errors.Count == 0); AssertWriteToPeFile(expectedResult, codeAssembly, pdbReader); AssertExecute(expectedOutput, assemblyName); } } }
public void Test00() { const string code = @"using System; namespace Ns { public class Test { public int Method1(int a, int b) { return a + b; } } }"; var cci = new CciModuleSource(TestProjects.DsaPath); var cci2 = new CciModuleSource(TestProjects.DsaPath); var type = cci.Modules.Single().Module.GetAllTypes().Single(t => t.Name.Value == "Deque") as NamedTypeDefinition; var method = type.Methods.Single(m => m.Name.Value == "EnqueueFront"); var cci3 = MutationTestsHelper.CreateModuleFromCode(code); var choices = new MutationSessionChoices { Filter = new MutationFilter( new List <TypeIdentifier>(), new MethodIdentifier(method).InList()), //Filter = MutationFilter.AllowAll(), SelectedOperators = new AOR_ArithmeticOperatorReplacement().InList <IMutationOperator>(), }; // var type = cci.Modules.Single().Module.GetAllTypes().Single(t => t.Name.Value == "Test") as NamedTypeDefinition; // var method = type.Methods.Single(m => m.Name.Value == "Method1"); var exec = new MutationExecutor(null, choices, null); var container = new MutantsContainer(exec, new OriginalCodebase(cci.InList()), new OptionsModel()); IList <AssemblyNode> assemblies = container.InitMutantsForOperators(ProgressCounter.Inactive()); var mut = assemblies.Cast <CheckedNode>() .SelectManyRecursive(n => n.Children ?? new NotifyingCollection <CheckedNode>()) .OfType <Mutant>().ElementAt(4); MutationResult executeMutation = exec.ExecuteMutation(mut, cci2).Result; var c = new CodeDeepCopier(cci.Host); MethodDefinition methodDefinition = c.Copy(mut.MutationTarget.MethodRaw); var vis = new CodeVisualizer(null, null); var s = vis.Visualize(CodeLanguage.CSharp, cci2); var v = new MutantsCache.Viss(cci2.Host, methodDefinition); var modClean = v.Rewrite(cci2.Modules.Single().Module); cci2.ReplaceWith(modClean); var debug = new DebugOperatorCodeVisitor(); var debug2 = new DebugOperatorCodeVisitor(); new DebugCodeTraverser(debug).Traverse(cci.Modules.Single().Module); new DebugCodeTraverser(debug2).Traverse(cci2.Modules.Single().Module); File.WriteAllText(@"C:\PLIKI\tree1.txt", debug.ToString()); File.WriteAllText(@"C:\PLIKI\tree2.txt", debug2.ToString()); // Console.WriteLine(debug); // Console.WriteLine(debug2); // cci.ReplaceWith(executeMutation.MutatedModules.Modules.Single().Module); // var s2 = vis.Visualize(CodeLanguage.CSharp, cci2); // Console.WriteLine(s); // Console.WriteLine(s2); // var viss = new Viss(cci2.Host, sourceMethod); // IModule newMod = viss.Rewrite(executeMutation.MutatedModules.Modules.Single().Module); // cci2.ReplaceWith(executeMutation.MutatedModules.Modules.Single().Module); // MutationResult executeMutation2 = exec.ExecuteMutation(mut, cci2).Result; }
static void Main(string[] args) { if (args == null || args.Length == 0) { Console.WriteLine("usage: PeToPe [path]fileName.ext [noStack]"); return; } bool noStack = args.Length == 2; using (var host = new PeReader.DefaultHost()) { //Read the Metadata Model from the PE file var module = host.LoadUnitFrom(args[0]) as IModule; if (module == null || module == Dummy.Module || module == Dummy.Assembly) { Console.WriteLine(args[0] + " is not a PE file containing a CLR module or assembly."); return; } //Get a PDB reader if there is a PDB file. PdbReader /*?*/ pdbReader = null; string pdbFile = Path.ChangeExtension(module.Location, "pdb"); if (File.Exists(pdbFile)) { Stream pdbStream = File.OpenRead(pdbFile); pdbReader = new PdbReader(pdbStream, host); } using (pdbReader) { //Construct a Code Model from the Metadata model via decompilation var options = DecompilerOptions.None; if (noStack) { options |= DecompilerOptions.Unstack; } var decompiledModule = Decompiler.GetCodeModelFromMetadataModel(host, module, pdbReader, options); ISourceLocationProvider sourceLocationProvider = pdbReader; //The decompiler preserves the Locations from the IOperation values, so the PdbReader still works. //Recompiling the CodeModel to IL might change the IL offsets, so a new provider is needed. ILocalScopeProvider localScopeProvider = new Decompiler.LocalScopeProvider(pdbReader); //Get a mutable copy of the Code Model. The ISourceLocationProvider is needed to provide copied source method bodies with the //ability to find out where to mark sequence points when compiling themselves back into IL. //(ISourceMethodBody does not know about the Source Model, so this information must be provided explicitly.) var copier = new CodeDeepCopier(host, sourceLocationProvider); var mutableModule = copier.Copy(decompiledModule); //Traverse the mutable copy. In a real application the traversal will collect information to be used during rewriting. var traverser = new CodeTraverser() { PreorderVisitor = new CodeVisitor() }; traverser.Traverse(mutableModule); //Rewrite the mutable Code Model. In a real application CodeRewriter would be a subclass that actually does something. //(This is why decompiled source method bodies must recompile themselves, rather than just use the IL from which they were decompiled.) var rewriter = new CodeRewriter(host); var rewrittenModule = rewriter.Rewrite(mutableModule); //Write out the Code Model by traversing it as the Metadata Model that it also is. using (var peStream = File.Create(rewrittenModule.Location + ".pe")) { if (pdbReader == null) { PeWriter.WritePeToStream(rewrittenModule, host, peStream); } else { using (var pdbWriter = new PdbWriter(rewrittenModule.Location + ".pdb", pdbReader)) { PeWriter.WritePeToStream(rewrittenModule, host, peStream, sourceLocationProvider, localScopeProvider, pdbWriter); } } } } } }
public static Bpl.Program /*?*/ TranslateAssembly(List <string> assemblyNames, HeapFactory heapFactory, Options options, List <Regex> exemptionList, bool whiteList) { Contract.Requires(assemblyNames != null); Contract.Requires(heapFactory != null); var libPaths = options.libpaths; var wholeProgram = options.wholeProgram; var /*?*/ stubAssemblies = options.stub; var host = new CodeContractAwareHostEnvironment(libPaths != null ? libPaths : Enumerable <string> .Empty, true, true); Host = host; Bpl.CommandLineOptions.Install(new Bpl.CommandLineOptions()); #region Assemlies to translate (via cmd line) modules = new List <IModule>(); var contractExtractors = new Dictionary <IUnit, IContractProvider>(); var pdbReaders = new Dictionary <IUnit, PdbReader>(); #region Load *all* of the assemblies before doing anything else so that they can all vote on unification matters foreach (var a in assemblyNames) { var module = host.LoadUnitFrom(a) as IModule; if (module == null || module == Dummy.Module || module == Dummy.Assembly) { Console.WriteLine(a + " is not a PE file containing a CLR module or assembly, or an error occurred when loading it."); Console.WriteLine("Skipping it, continuing with other input assemblies"); continue; } modules.Add(module); } #endregion #region Decompile all of the assemblies var decompiledModules = new List <IModule>(); foreach (var m in modules) { PdbReader /*?*/ pdbReader = null; string pdbFile = Path.ChangeExtension(m.Location, "pdb"); if (File.Exists(pdbFile)) { Stream pdbStream = File.OpenRead(pdbFile); pdbReader = new PdbReader(pdbStream, host); } var m2 = Decompiler.GetCodeModelFromMetadataModel(host, m, pdbReader, DecompilerOptions.Unstack) as IModule; // The decompiler does not turn calls to Assert/Assume into Code Model nodes m2 = new Microsoft.Cci.MutableContracts.ContractExtractor.AssertAssumeExtractor(host, pdbReader).Rewrite(m2); decompiledModules.Add(m2); host.RegisterAsLatest(m2); contractExtractors.Add(m2, host.GetContractExtractor(m2.UnitIdentity)); pdbReaders.Add(m2, pdbReader); } modules = decompiledModules; #endregion #endregion #region Assemblies to translate (stubs) if (stubAssemblies != null) { foreach (var s in stubAssemblies) { var module = host.LoadUnitFrom(s) as IModule; if (module == null || module == Dummy.Module || module == Dummy.Assembly) { Console.WriteLine(s + " is not a PE file containing a CLR module or assembly, or an error occurred when loading it."); Console.WriteLine("Skipping it, continuing with other input assemblies"); } PdbReader /*?*/ pdbReader = null; string pdbFile = Path.ChangeExtension(module.Location, "pdb"); if (File.Exists(pdbFile)) { Stream pdbStream = File.OpenRead(pdbFile); pdbReader = new PdbReader(pdbStream, host); } module = Decompiler.GetCodeModelFromMetadataModel(host, module, pdbReader, DecompilerOptions.Unstack) as IModule; var copier = new CodeDeepCopier(host); var mutableModule = copier.Copy(module); var mscorlib = TypeHelper.GetDefiningUnit(host.PlatformType.SystemObject.ResolvedType); //var mutator = new ReparentModule(host, mscorlib, mutableModule); //module = mutator.Rewrite(mutableModule); //modules.Add(Tuple.Create(module, pdbReader)); RewriteUnitReferences renamer = new RewriteUnitReferences(host, mutableModule); var mscorlibAssembly = (IAssembly)mscorlib; renamer.targetAssembly = mscorlibAssembly; renamer.originalAssemblyIdentity = mscorlibAssembly.AssemblyIdentity; renamer.RewriteChildren(mutableModule); modules.Add((IModule)mutableModule); contractExtractors.Add(module, host.GetContractExtractor(module.UnitIdentity)); pdbReaders.Add(module, pdbReader); } } #endregion if (modules.Count == 0) { throw new TranslationException("No input assemblies to translate."); } //var primaryModule = modules[0]; Sink sink = new Sink(host, heapFactory, options, exemptionList, whiteList); TranslationHelper.tmpVarCounter = 0; // TODO move away, get all plugin and translators from a config file or alike #region Plugged translators List <Translator> translatorsPlugged = new List <Translator>(); ITranslationPlugin bctPlugin = new BytecodeTranslatorPlugin(wholeProgram); Translator bcTranslator = bctPlugin.getTranslator(sink, contractExtractors, pdbReaders); translatorsPlugged.Add(bcTranslator); #endregion sink.TranslationPlugins = translatorsPlugged; // TODO replace the whole translation by a translator initialization and an orchestrator calling back for each element // TODO for the current BC translator it will possibly just implement onMetadataElement(IModule) // TODO refactor this away, handle priorities between plugged translators IOrderedEnumerable <Translator> prioritizedTranslators = translatorsPlugged.OrderBy(t => t.getPriority()); foreach (Translator t in prioritizedTranslators) { t.initialize(); if (t.isOneShot()) { t.TranslateAssemblies(modules); } } foreach (var pair in sink.delegateTypeToDelegates.Values) { CreateDispatchMethod(sink, pair.Item1, pair.Item2); CreateDelegateCreateMethod(sink, pair.Item1, pair.Item2); CreateDelegateAddMethod(sink, pair.Item1, pair.Item2); CreateDelegateRemoveMethod(sink, pair.Item1, pair.Item2); } // Subtyping for extern types if (sink.Options.typeInfo > 0) { sink.DeclareExternTypeSubtyping(); } //sink.CreateIdentifierCorrespondenceTable(primaryModule.Name.Value); //var rc = new Bpl.ResolutionContext((Bpl.IErrorSink)null); //foreach (var decl in sink.TranslatedProgram.TopLevelDeclarations) { // decl.Register(rc); //} //sink.TranslatedProgram.Resolve(rc); //var goodDecls = new List<Bpl.Declaration>(); //var tc = new Bpl.TypecheckingContext(null); //foreach (var decl in sink.TranslatedProgram.TopLevelDeclarations) { // var impl = decl as Bpl.Implementation; // if (impl == null) { // goodDecls.Add(decl); // continue; // } // try { // //var tc = new Bpl.TypecheckingContext(null); // impl.Typecheck(tc); // goodDecls.Add(impl); // } catch { // Console.WriteLine("Deleting implementation for: " + impl.Name); // // nothing to do, just continue // } //} //sink.TranslatedProgram.TopLevelDeclarations = goodDecls; return(sink.TranslatedProgram); }