static void WriteILOffset(ITextOutput output, uint offset) { // Offsets are always in hex if (offset <= ushort.MaxValue) output.Write(string.Format(GetHexFormatUInt16(), offset), TextTokenType.Number); else output.Write(string.Format(GetHexFormatUInt32(), offset), TextTokenType.Number); }
public static void WriteTo(this ExceptionHandler exceptionHandler, ITextOutput writer, MethodDef method) { writer.Write("Try", TextTokenType.Keyword); writer.WriteSpace(); WriteOffsetReference(writer, exceptionHandler.TryStart, method); writer.Write('-', TextTokenType.Operator); WriteOffsetReference(writer, exceptionHandler.TryEnd, method); writer.WriteSpace(); writer.Write(exceptionHandler.HandlerType.ToString(), TextTokenType.Keyword); if (exceptionHandler.FilterStart != null) { writer.WriteSpace(); WriteOffsetReference(writer, exceptionHandler.FilterStart, method); writer.WriteSpace(); writer.Write("handler", TextTokenType.Keyword); writer.WriteSpace(); } if (exceptionHandler.CatchType != null) { writer.WriteSpace(); exceptionHandler.CatchType.WriteTo(writer); } writer.WriteSpace(); WriteOffsetReference(writer, exceptionHandler.HandlerStart, method); writer.Write('-', TextTokenType.Operator); WriteOffsetReference(writer, exceptionHandler.HandlerEnd, method); }
public override void DecompileMethod(MethodDefinition method, ITextOutput output, DecompilationOptions options) { if (!method.HasBody) { return; } ILAstBuilder astBuilder = new ILAstBuilder(); ILBlock ilMethod = new ILBlock(); ilMethod.Body = astBuilder.Build(method, inlineVariables); if (abortBeforeStep != null) { DecompilerContext context = new DecompilerContext(method.Module) { CurrentType = method.DeclaringType, CurrentMethod = method }; new ILAstOptimizer().Optimize(context, ilMethod, abortBeforeStep.Value); } var allVariables = ilMethod.GetSelfAndChildrenRecursive<ILExpression>().Select(e => e.Operand as ILVariable) .Where(v => v != null && !v.IsParameter).Distinct(); foreach (ILVariable v in allVariables) { output.WriteDefinition(v.Name, v); if (v.Type != null) { output.Write(" : "); if (v.IsPinned) output.Write("pinned "); v.Type.WriteTo(output, ILNameSyntax.ShortTypeName); } output.WriteLine(); } output.WriteLine(); foreach (ILNode node in ilMethod.Body) { node.WriteTo(output); output.WriteLine(); } }
public override void DecompileMethod(MethodDef method, ITextOutput output, DecompilationOptions options) { WriteComment(output, "Method: "); output.WriteDefinition(IdentifierEscaper.Escape(method.FullName), method, TextTokenType.Comment, false); output.WriteLine(); if (!method.HasBody) { return; } StartKeywordBlock(output, ".body", method); ILAstBuilder astBuilder = new ILAstBuilder(); ILBlock ilMethod = new ILBlock(); DecompilerContext context = new DecompilerContext(method.Module) { CurrentType = method.DeclaringType, CurrentMethod = method }; ilMethod.Body = astBuilder.Build(method, inlineVariables, context); if (abortBeforeStep != null) { new ILAstOptimizer().Optimize(context, ilMethod, abortBeforeStep.Value); } if (context.CurrentMethodIsAsync) { output.Write("async", TextTokenType.Keyword); output.Write('/', TextTokenType.Operator); output.WriteLine("await", TextTokenType.Keyword); } var allVariables = ilMethod.GetSelfAndChildrenRecursive<ILExpression>().Select(e => e.Operand as ILVariable) .Where(v => v != null && !v.IsParameter).Distinct(); foreach (ILVariable v in allVariables) { output.WriteDefinition(IdentifierEscaper.Escape(v.Name), v, v.IsParameter ? TextTokenType.Parameter : TextTokenType.Local); if (v.Type != null) { output.WriteSpace(); output.Write(':', TextTokenType.Operator); output.WriteSpace(); if (v.IsPinned) { output.Write("pinned", TextTokenType.Keyword); output.WriteSpace(); } v.Type.WriteTo(output, ILNameSyntax.ShortTypeName); } if (v.IsGenerated) { output.WriteSpace(); output.Write('[', TextTokenType.Operator); output.Write("generated", TextTokenType.Keyword); output.Write(']', TextTokenType.Operator); } output.WriteLine(); } var memberMapping = new MemberMapping(method); foreach (ILNode node in ilMethod.Body) { node.WriteTo(output, memberMapping); if (!node.WritesNewLine) output.WriteLine(); } output.AddDebugSymbols(memberMapping); EndKeywordBlock(output); }
static void WriteLabelList(ITextOutput writer, Instruction[] instructions) { writer.Write("("); for(int i = 0; i < instructions.Length; i++) { if(i != 0) writer.Write(", "); WriteOffsetReference(writer, instructions[i]); } writer.Write(")"); }
protected override void Write(ITextOutput output) { output.Write(string.Format("{0}", index + 1), TextTokenType.Number); if (infoTuple != null) { output.WriteSpace(); output.Write('-', TextTokenType.Operator); output.WriteSpace(); infoTuple.Item2(output); } }
public static ITextOutput Write(ITextOutput output, FieldDef field, Language language) { output.Write(UIUtils.CleanUpIdentifier(field.Name), TextTokenHelper.GetTextTokenType(field)); output.WriteSpace(); output.Write(':', TextTokenType.Operator); output.WriteSpace(); language.TypeToString(output, field.FieldType.ToTypeDefOrRef(), false, field); field.MDToken.WriteSuffixString(output); return output; }
protected override void Write(ITextOutput output) { output.Write(string.Format("{0:X2}", (byte)tablesStreamVM.Table), TextTokenType.Number); output.WriteSpace(); output.Write(string.Format("{0}", tablesStreamVM.Table), TextTokenType.Type); output.WriteSpace(); output.Write('(', TextTokenType.Operator); output.Write(string.Format("{0}", tablesStreamVM.Rows), TextTokenType.Number); output.Write(')', TextTokenType.Operator); }
public static ITextOutput Write(ITextOutput output, EventDef ev, Language language) { output.Write(UIUtils.CleanUpIdentifier(ev.Name), TextTokenHelper.GetTextTokenType(ev)); output.WriteSpace(); output.Write(':', TextTokenType.Operator); output.WriteSpace(); language.TypeToString(output, ev.EventType, false, ev); ev.MDToken.WriteSuffixString(output); return output; }
protected override void Write(ITextOutput output) { output.Write("Section", TextTokenType.Keyword); output.WriteSpace(); output.Write('#', TextTokenType.Operator); output.Write(sectionNumber.ToString(), TextTokenType.Number); output.Write(':', TextTokenType.Operator); output.WriteSpace(); output.Write(string.Format("{0}", imageSectionHeaderVM.NameVM.String), TextTokenType.Type); }
public static void WriteTo(this Instruction instruction, ITextOutput writer) { writer.WriteDefinition(CecilExtensions.OffsetToString(instruction.Offset), instruction); writer.Write(": "); writer.WriteReference(instruction.OpCode.Name, instruction.OpCode); if(null != instruction.Operand) { writer.Write(' '); WriteOperand(writer, instruction.Operand); } }
protected override void Write(ITextOutput output, Language language) { if (hidesParent) { output.Write('(', TextTokenType.Operator); output.Write("hides", TextTokenType.Text); output.Write(')', TextTokenType.Operator); output.WriteSpace(); } Language.TypeToString(output, analyzedEvent.DeclaringType, true); output.Write('.', TextTokenType.Operator); EventTreeNode.Write(output, analyzedEvent, Language); }
public static ITextOutput Write(ITextOutput output, string name) { if (name.Length == 0) output.Write('-', TextTokenType.Operator); else { var parts = name.Split('.'); for (int i = 0; i < parts.Length; i++) { if (i > 0) output.Write('.', TextTokenType.Operator); output.Write(IdentifierEscaper.Escape(parts[i]), TextTokenType.NamespacePart); } } return output; }
public override void DecompileMethod(ilspy::Mono.Cecil.MethodDefinition method, ITextOutput output, DecompilationOptions options) { var xMethod = GetXMethodDefinition(method); var ilMethod = xMethod as XBuilder.ILMethodDefinition; CompiledMethod cmethod; if (ilMethod == null || !ilMethod.OriginalMethod.HasBody) { output.Write(""); output.WriteLine("// not an il method or method without body."); return; } var methodSource = new MethodSource(xMethod, ilMethod.OriginalMethod); var target = (DexTargetPackage) AssemblyCompiler.TargetPackage; var dMethod = (MethodDefinition)xMethod.GetReference(target); DexMethodBodyCompiler.TranslateToRL(AssemblyCompiler, target, methodSource, dMethod, GenerateSetNextInstructionCode, out cmethod); var rlBody = cmethod.RLBody; // Optimize RL code string lastApplied = RLTransformations.Transform(target.DexFile, rlBody, StopOptimizationAfter == -1?int.MaxValue:StopOptimizationAfter); if(lastApplied != null) output.WriteLine("// Stop after " + lastApplied); PrintMethod(cmethod, output, options); }
public static void WriteTo(this Instruction instruction, ITextOutput writer, Func<OpCode, string> getOpCodeDocumentation) { writer.WriteDefinition(DnlibExtensions.OffsetToString(instruction.GetOffset()), instruction, TextTokenType.Label, false); writer.Write(':', TextTokenType.Operator); writer.WriteSpace(); writer.WriteReference(instruction.OpCode.Name, instruction.OpCode, TextTokenType.OpCode); if (instruction.Operand != null) { writer.WriteSpace(); if (instruction.OpCode == OpCodes.Ldtoken) { var member = instruction.Operand as IMemberRef; if (member != null && member.IsMethod) { writer.Write("method", TextTokenType.Keyword); writer.WriteSpace(); } else if (member != null && member.IsField) { writer.Write("field", TextTokenType.Keyword); writer.WriteSpace(); } } WriteOperand(writer, instruction.Operand); } if (getOpCodeDocumentation != null) { var doc = getOpCodeDocumentation(instruction.OpCode); if (doc != null) { writer.Write("\t", TextTokenType.Text); writer.Write("// " + doc, TextTokenType.Comment); } } }
protected override void Write(ITextOutput output, Language language) { if (name != null) output.Write(name, TextTokenType.Keyword); else base.Write(output, language); }
protected override void Write(ITextOutput output, Language language) { var isExe = analyzedAssembly.Assembly != null && analyzedAssembly.IsManifestModule && (analyzedAssembly.Characteristics & dnlib.PE.Characteristics.Dll) == 0; output.Write(UIUtils.CleanUpIdentifier(analyzedAssembly.Name), isExe ? TextTokenType.AssemblyExe : TextTokenType.Assembly); }
public static void WriteTo(this Instruction instruction, ITextOutput writer) { writer.WriteDefinition(CecilExtensions.OffsetToString(instruction.Offset), instruction); writer.Write(": "); writer.WriteReference(instruction.OpCode.Name, instruction.OpCode); if (instruction.Operand != null) { writer.Write(' '); if (instruction.OpCode == OpCodes.Ldtoken) { if (instruction.Operand is MethodReference) writer.Write("method "); else if (instruction.Operand is FieldReference) writer.Write("field "); } WriteOperand(writer, instruction.Operand); } }
public override void DecompileType(TypeDefinition type, ITextOutput output, DecompilationOptions options) { var xType = GetXTypeDefinition(type); output.WriteLine("class " + type.Name); output.WriteLine("{"); foreach (var field in xType.Fields) { if (!field.IsReachable) continue; output.WriteLine("\t{0} {1};", field.FieldType.Name, field.Name); } output.WriteLine(); foreach (var method in xType.Methods) { var ilMethod = method as XBuilder.ILMethodDefinition; if (ilMethod != null && !ilMethod.OriginalMethod.IsReachable) continue; output.Write("\t{0} {1}(", method.ReturnType.Name, method.Name); List<string> parms = method.Parameters.Select(p => string.Format("{0}{1} {2}", KindToStringAndSpace(p.Kind), p.ParameterType.Name, p.Name)) .ToList(); if (method.NeedsGenericInstanceTypeParameter) parms.Add("Type[] git"); if (method.NeedsGenericInstanceMethodParameter) parms.Add("Type[] gim"); output.Write(string.Join(", ", parms)); output.WriteLine(")"); output.WriteLine("\t{"); DecompileMethod(method, output, 2); output.WriteLine("\t}"); output.WriteLine(); } output.WriteLine("}"); }
void Decompile(ModuleDef module, BamlDocument document, Language lang, ITextOutput output, out IHighlightingDefinition highlight, CancellationToken token) { var decompiler = new XamlDecompiler(); var xaml = decompiler.Decompile(module, document, token); output.Write(xaml.ToString(), TextTokenType.Text); highlight = HighlightingManager.Instance.GetDefinitionByExtension(".xml"); }
void Decompile(ModuleDef module, BamlDocument document, ILanguage lang, ITextOutput output, out string ext, CancellationToken token) { var decompiler = new XamlDecompiler(); var xaml = decompiler.Decompile(module, document, token, BamlDecompilerOptions.Create(lang), null); output.Write(xaml.ToString(), TextTokenKind.Text); ext = ".xml"; }
public override void DecompileAssembly(LoadedAssembly assembly, ITextOutput output, DecompilationOptions options) { if (options.FullDecompilation && options.SaveAsProjectDirectory != null) { HashSet<string> directories = new HashSet<string>(StringComparer.OrdinalIgnoreCase); var files = WriteCodeFilesInProject(assembly.AssemblyDefinition, options, directories).ToList(); files.AddRange(WriteResourceFilesInProject(assembly, options, directories)); WriteProjectFile(new TextOutputWriter(output), files, assembly.AssemblyDefinition.MainModule); } else { base.DecompileAssembly(assembly, output, options); output.WriteLine(); ModuleDefinition mainModule = assembly.AssemblyDefinition.MainModule; if (mainModule.EntryPoint != null) { output.Write("' Entry point: "); output.WriteReference(mainModule.EntryPoint.DeclaringType.FullName + "." + mainModule.EntryPoint.Name, mainModule.EntryPoint); output.WriteLine(); } switch (mainModule.Architecture) { case TargetArchitecture.I386: if ((mainModule.Attributes & ModuleAttributes.Required32Bit) == ModuleAttributes.Required32Bit) WriteCommentLine(output, "Architecture: x86"); else WriteCommentLine(output, "Architecture: AnyCPU"); break; case TargetArchitecture.AMD64: WriteCommentLine(output, "Architecture: x64"); break; case TargetArchitecture.IA64: WriteCommentLine(output, "Architecture: Itanium-64"); break; } if ((mainModule.Attributes & ModuleAttributes.ILOnly) == 0) { WriteCommentLine(output, "This assembly contains unmanaged code."); } switch (mainModule.Runtime) { case TargetRuntime.Net_1_0: WriteCommentLine(output, "Runtime: .NET 1.0"); break; case TargetRuntime.Net_1_1: WriteCommentLine(output, "Runtime: .NET 1.1"); break; case TargetRuntime.Net_2_0: WriteCommentLine(output, "Runtime: .NET 2.0"); break; case TargetRuntime.Net_4_0: WriteCommentLine(output, "Runtime: .NET 4.0"); break; } output.WriteLine(); // don't automatically load additional assemblies when an assembly node is selected in the tree view using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad()) { AstBuilder codeDomBuilder = CreateAstBuilder(options, currentModule: assembly.AssemblyDefinition.MainModule); codeDomBuilder.AddAssembly(assembly.AssemblyDefinition, onlyAssemblyLevel: !options.FullDecompilation); RunTransformsAndGenerateCode(codeDomBuilder, output, options); } } OnDecompilationFinished(null); }
private void PrintMethod(CompiledMethod cmethod, ITextOutput output, DecompilationOptions options) { if ((cmethod != null) && (cmethod.RLBody != null)) { var body = cmethod.RLBody; var basicBlocks = BasicBlock.Find(body); foreach (var block in basicBlocks) { output.Write(string.Format("D_{0:X4}:", block.Entry.Index)); output.WriteLine(); output.Indent(); foreach (var ins in block.Instructions) { if (ShowHasSeqPoint) { if (ins.SequencePoint != null) output.Write(ins.SequencePoint.IsSpecial ? "!" : "~"); } output.Write(ins.ToString()); output.WriteLine(); } output.Unindent(); } if (body.Exceptions.Any()) { output.WriteLine(); output.Write("Exception handlers:"); output.WriteLine(); output.Indent(); foreach (var handler in body.Exceptions) { output.Write(string.Format("{0:x4}-{1:x4}", handler.TryStart.Index, handler.TryEnd.Index)); output.WriteLine(); output.Indent(); foreach (var c in handler.Catches) { output.Write(string.Format("{0} => {1:x4}", c.Type, c.Instruction.Index)); output.WriteLine(); } if (handler.CatchAll != null) { output.Write(string.Format("{0} => {1:x4}", "<any>", handler.CatchAll.Index)); output.WriteLine(); } output.Unindent(); } output.Unindent(); } } else { output.Write("Method not found in dex"); output.WriteLine(); } }
public static ITextOutput Write(ITextOutput output, MethodDef method, Language language) { output.Write(UIUtils.CleanUpIdentifier(method.Name), TextTokenHelper.GetTextTokenType(method)); output.Write('(', TextTokenType.Operator); for (int i = 0; i < method.Parameters.Count; i++) { if (method.Parameters[i].IsHiddenThisParameter) continue; if (method.Parameters[i].MethodSigIndex > 0) { output.Write(',', TextTokenType.Operator); output.WriteSpace(); } language.TypeToString(output, method.Parameters[i].Type.ToTypeDefOrRef(), false, method.Parameters[i].ParamDef); } if (method.CallingConvention == CallingConvention.VarArg || method.CallingConvention == CallingConvention.NativeVarArg) { if (method.MethodSig.GetParamCount() > 0) { output.Write(',', TextTokenType.Operator); output.WriteSpace(); } output.Write("...", TextTokenType.Operator); } output.Write(')', TextTokenType.Operator); output.WriteSpace(); output.Write(':', TextTokenType.Operator); output.WriteSpace(); language.TypeToString(output, method.ReturnType.ToTypeDefOrRef(), false, method.Parameters.ReturnParameter.ParamDef); method.MDToken.WriteSuffixString(output); return output; }
public static ITextOutput Write(ITextOutput output, PropertyDef property, Language language, bool? isIndexer = null) { language.FormatPropertyName(output, property, isIndexer); output.WriteSpace(); output.Write(':', TextTokenType.Operator); output.WriteSpace(); language.TypeToString(output, property.PropertySig.GetRetType().ToTypeDefOrRef(), false, property); property.MDToken.WriteSuffixString(output); return output; }
public override void AcceptWriter(ITextOutput writer) { List<string> keyList = new List<string>(Values.Keys); int keyCount = keyList.Count; JsonValue jsonValue; bool isFirst = true; for (int i = 0; i < keyCount; i++) { if (isFirst) { writer.Write('{'); isFirst = false; } else { writer.Write(", "); } writer.Write('"'); writer.Write(keyList[i]); writer.Write('"'); writer.Write(':'); if (Values.TryGetValue(keyList[i], out jsonValue)) { jsonValue.AcceptWriter(writer); } } if (!isFirst) writer.Write('}'); }
public static void WriteTo(this Instruction instruction, MethodDef method, CilBody body, ITextOutput writer) { writer.WriteDefinition(dnlibExtensions.OffsetToString(instruction.Offset), instruction, true); writer.Write(": "); writer.WriteReference(instruction.OpCode.Name, instruction.OpCode, true); if (instruction.Operand != null) { writer.Write(' '); if (instruction.OpCode == OpCodes.Ldtoken) { if (dnlibExtensions.IsMethod(instruction.Operand)) writer.WriteKeyword("method "); else if (dnlibExtensions.IsField(instruction.Operand)) writer.WriteKeyword("field "); } WriteOperand(writer, instruction.Operand); } else if (method != null && body != null) { switch (instruction.OpCode.Code) { case Code.Ldloc_0: case Code.Ldloc_1: case Code.Ldloc_2: case Code.Ldloc_3: writer.WriteComment(" // "); var local = instruction.GetLocal(body.Variables); if (local != null) WriteOperand(writer, local); break; case Code.Ldarg_0: case Code.Ldarg_1: case Code.Ldarg_2: case Code.Ldarg_3: writer.WriteComment(" // "); var arg = instruction.GetParameter(method.Parameters); if (arg != null) WriteOperand(writer, arg); break; } } }
private static void FallbackFormatting(ITextOutput output, CompiledMethod cmethod) { var body = cmethod.DexMethod.Body; body.UpdateInstructionOffsets(); var targetInstructions = body.Instructions.Select(x => x.Operand).OfType<Instruction>().ToList(); targetInstructions.AddRange(body.Exceptions.Select(x => x.TryStart)); targetInstructions.AddRange(body.Exceptions.Select(x => x.TryEnd)); targetInstructions.AddRange(body.Exceptions.SelectMany(x => x.Catches, (h, y) => y.Instruction)); targetInstructions.AddRange(body.Exceptions.Select(x => x.CatchAll)); foreach (var ins in body.Instructions) { if (targetInstructions.Contains(ins) || (ins.Offset == 0)) { output.Write(string.Format("D_{0:X4}:", ins.Offset)); output.WriteLine(); } output.Indent(); output.Write(ins.ToString()); output.WriteLine(); output.Unindent(); } if (body.Exceptions.Any()) { output.WriteLine(); output.Write("Exception handlers:"); output.WriteLine(); output.Indent(); foreach (var handler in body.Exceptions) { output.Write(string.Format("{0:x4}-{1:x4}", handler.TryStart.Offset, handler.TryEnd.Offset)); output.WriteLine(); output.Indent(); foreach (var c in handler.Catches) { output.Write(string.Format("{0} => {1:x4}", c.Type, c.Instruction.Offset)); output.WriteLine(); } if (handler.CatchAll != null) { output.Write(string.Format("{0} => {1:x4}", "<any>", handler.CatchAll.Offset)); output.WriteLine(); } output.Unindent(); } output.Unindent(); } }
public override void DecompileAssembly(LoadedAssembly assembly, ITextOutput output, DecompilationOptions options) { if (options.FullDecompilation && options.SaveAsProjectDirectory != null) { var decompiler = new VBProjectDecompiler(); decompiler.Decompile(this, assembly, output, options); } else { base.DecompileAssembly(assembly, output, options); output.WriteLine(); ModuleDefinition mainModule = assembly.ModuleDefinition; if (mainModule.EntryPoint != null) { output.Write("' Entry point: "); output.WriteReference(mainModule.EntryPoint.DeclaringType.FullName + "." + mainModule.EntryPoint.Name, mainModule.EntryPoint); output.WriteLine(); } WriteCommentLine(output, "Architecture: " + CSharpLanguage.GetPlatformDisplayName(mainModule)); if ((mainModule.Attributes & ModuleAttributes.ILOnly) == 0) { WriteCommentLine(output, "This assembly contains unmanaged code."); } switch (mainModule.Runtime) { case TargetRuntime.Net_1_0: WriteCommentLine(output, "Runtime: .NET 1.0"); break; case TargetRuntime.Net_1_1: WriteCommentLine(output, "Runtime: .NET 1.1"); break; case TargetRuntime.Net_2_0: WriteCommentLine(output, "Runtime: .NET 2.0"); break; case TargetRuntime.Net_4_0: if (assembly.IsNet45()) { WriteCommentLine(output, "Runtime: .NET 4.5"); } else { WriteCommentLine(output, "Runtime: .NET 4.0"); } break; } output.WriteLine(); // don't automatically load additional assemblies when an assembly node is selected in the tree view using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad()) { AstBuilder codeDomBuilder = CreateAstBuilder(options, currentModule: assembly.ModuleDefinition); codeDomBuilder.AddAssembly(assembly.ModuleDefinition, onlyAssemblyLevel: !options.FullDecompilation); RunTransformsAndGenerateCode(codeDomBuilder, output, options, assembly.ModuleDefinition); } } }
public static void WriteTo(this ExceptionHandler exceptionHandler, ITextOutput writer) { writer.Write("Try "); WriteOffsetReference(writer, exceptionHandler.TryStart); writer.Write('-'); WriteOffsetReference(writer, exceptionHandler.TryEnd); writer.Write(' '); writer.Write(exceptionHandler.HandlerType.ToString()); if (exceptionHandler.FilterStart != null) { writer.Write(' '); WriteOffsetReference(writer, exceptionHandler.FilterStart); writer.Write(" handler "); } if (exceptionHandler.CatchType != null) { writer.Write(' '); exceptionHandler.CatchType.WriteTo(writer); } writer.Write(' '); WriteOffsetReference(writer, exceptionHandler.HandlerStart); writer.Write('-'); WriteOffsetReference(writer, exceptionHandler.HandlerEnd); }
public static void WriteOperand(ITextOutput writer, string operand) { writer.Write('"'); writer.Write(EscapeString(operand)); writer.Write('"'); }
public static void WriteOperand(ITextOutput writer, long val) { writer.Write(ToInvariantCultureString(val)); }
public void Disassemble(PEFile currentFile, int bitness, ulong address, bool showMetadataTokens, bool showMetadataTokensInBase10) { // TODO: Decorate the disassembly with GCInfo ReadyToRunMethod readyToRunMethod = runtimeFunction.Method; WriteCommentLine(readyToRunMethod.SignatureString); Dictionary <ulong, UnwindCode> unwindInfo = null; if (ReadyToRunOptions.GetIsShowUnwindInfo(null) && bitness == 64) { unwindInfo = WriteUnwindInfo(); } bool isShowDebugInfo = ReadyToRunOptions.GetIsShowDebugInfo(null); DebugInfoHelper debugInfo = null; if (isShowDebugInfo) { debugInfo = WriteDebugInfo(); } byte[] codeBytes = new byte[runtimeFunction.Size]; for (int i = 0; i < runtimeFunction.Size; i++) { codeBytes[i] = reader.Image[reader.GetOffset(runtimeFunction.StartAddress) + i]; } var codeReader = new ByteArrayCodeReader(codeBytes); var decoder = Decoder.Create(bitness, codeReader); decoder.IP = address; ulong endRip = decoder.IP + (uint)codeBytes.Length; var instructions = new InstructionList(); while (decoder.IP < endRip) { decoder.Decode(out instructions.AllocUninitializedElement()); } string disassemblyFormat = ReadyToRunOptions.GetDisassemblyFormat(null); Formatter formatter = null; if (disassemblyFormat.Equals(ReadyToRunOptions.intel)) { formatter = new NasmFormatter(); } else { Debug.Assert(disassemblyFormat.Equals(ReadyToRunOptions.gas)); formatter = new GasFormatter(); } formatter.Options.DigitSeparator = "`"; formatter.Options.FirstOperandCharIndex = 10; var tempOutput = new StringOutput(); ulong baseInstrIP = instructions[0].IP; foreach (var instr in instructions) { int byteBaseIndex = (int)(instr.IP - address); if (isShowDebugInfo && runtimeFunction.DebugInfo != null) { foreach (var bound in runtimeFunction.DebugInfo.BoundsList) { if (bound.NativeOffset == byteBaseIndex) { if (bound.ILOffset == (uint)DebugInfoBoundsType.Prolog) { WriteCommentLine("Prolog"); } else if (bound.ILOffset == (uint)DebugInfoBoundsType.Epilog) { WriteCommentLine("Epilog"); } else { WriteCommentLine($"IL_{bound.ILOffset:x4}"); } } } } formatter.Format(instr, tempOutput); output.Write(instr.IP.ToString("X16")); output.Write(" "); int instrLen = instr.Length; for (int i = 0; i < instrLen; i++) { output.Write(codeBytes[byteBaseIndex + i].ToString("X2")); } int missingBytes = 10 - instrLen; for (int i = 0; i < missingBytes; i++) { output.Write(" "); } output.Write(" "); output.Write(tempOutput.ToStringAndReset()); DecorateUnwindInfo(unwindInfo, baseInstrIP, instr); DecorateDebugInfo(instr, debugInfo, baseInstrIP); DecorateCallSite(currentFile, showMetadataTokens, showMetadataTokensInBase10, instr); } output.WriteLine(); }
protected override void Write(ITextOutput output, Language language) { output.Write(CleanUpName(assemblyList.ListName), TextTokenType.Text); }
public void Disassemble(MethodBody body, MethodDebugSymbols debugSymbols) { // start writing IL code MethodDefinition method = body.Method; output.WriteLine("// Method begins at RVA 0x{0:x4}", method.RVA); output.WriteLine("// Code size {0} (0x{0:x})", body.CodeSize); output.WriteLine(".maxstack {0}", body.MaxStackSize); if (method.DeclaringType.Module.Assembly.EntryPoint == method) { output.WriteLine(".entrypoint"); } if (method.Body.HasVariables) { output.Write(".locals "); if (method.Body.InitLocals) { output.Write("init "); } output.WriteLine("("); output.Indent(); foreach (var v in method.Body.Variables) { output.WriteDefinition("[" + v.Index + "] ", v); v.VariableType.WriteTo(output); if (!string.IsNullOrEmpty(v.Name)) { output.Write(' '); output.Write(DisassemblerHelpers.Escape(v.Name)); } if (v.Index + 1 < method.Body.Variables.Count) { output.Write(','); } output.WriteLine(); } output.Unindent(); output.WriteLine(")"); } output.WriteLine(); if (detectControlStructure && body.Instructions.Count > 0) { Instruction inst = body.Instructions[0]; HashSet <int> branchTargets = GetBranchTargets(body.Instructions); WriteStructureBody(new ILStructure(body), branchTargets, ref inst, debugSymbols, method.Body.CodeSize); } else { foreach (var inst in method.Body.Instructions) { var startLocation = output.Location; inst.WriteTo(output); if (debugSymbols != null) { // add IL code mappings - used in debugger debugSymbols.SequencePoints.Add( new SequencePoint() { StartLocation = output.Location, EndLocation = output.Location, ILRanges = new ILRange[] { new ILRange(inst.Offset, inst.Next == null ? method.Body.CodeSize : inst.Next.Offset) } }); } output.WriteLine(); } if (method.Body.HasExceptionHandlers) { output.WriteLine(); foreach (var eh in method.Body.ExceptionHandlers) { eh.WriteTo(output); output.WriteLine(); } } } }
void CreateUI(ITextOutput output, object o, bool includeNamespace) { var ns = o as NamespaceSearchResult; if (ns != null) { output.WriteNamespace(ns.Namespace); return; } var td = o as TypeDef; if (td != null) { Debug.Assert(Language != null); Language.TypeToString(output, td, includeNamespace); return; } var md = o as MethodDef; if (md != null) { output.Write(IdentifierEscaper.Escape(md.Name), TextTokenHelper.GetTextTokenType(md)); return; } var fd = o as FieldDef; if (fd != null) { output.Write(IdentifierEscaper.Escape(fd.Name), TextTokenHelper.GetTextTokenType(fd)); return; } var pd = o as PropertyDef; if (pd != null) { output.Write(IdentifierEscaper.Escape(pd.Name), TextTokenHelper.GetTextTokenType(pd)); return; } var ed = o as EventDef; if (ed != null) { output.Write(IdentifierEscaper.Escape(ed.Name), TextTokenHelper.GetTextTokenType(ed)); return; } var asm = o as AssemblyDef; if (asm != null) { output.Write(asm); return; } var mod = o as ModuleDef; if (mod != null) { output.WriteModule(mod.FullName); return; } var asmRef = o as AssemblyRef; if (asmRef != null) { output.Write(asmRef); return; } var modRef = o as ModuleRef; if (modRef != null) { output.WriteModule(modRef.FullName); return; } // non-.NET file var loadedAsm = o as LoadedAssembly; if (loadedAsm != null) { output.Write(loadedAsm.ShortName, TextTokenType.Text); return; } var resNode = o as ResourceTreeNode; if (resNode != null) { output.WriteFilename(resNode.Name); return; } var resElNode = o as ResourceElementTreeNode; if (resElNode != null) { output.WriteFilename(resElNode.Name); return; } var s = o as string; if (s != null) { output.Write(s, TextTokenType.Text); return; } Debug.Assert(s == null); }
public override void DecompileAssembly(LoadedAssembly assembly, ITextOutput output, DecompilationOptions options) { if (options.FullDecompilation && options.SaveAsProjectDirectory != null) { HashSet <string> directories = new HashSet <string>(StringComparer.OrdinalIgnoreCase); var nsList = new List <TNamespace>(); var dict = new Dictionary <string, TNamespace>(); ParserFilesInProject(assembly.ModuleDefinition, options, directories, nsList); var default_key = "NULL"; var default_ns = new TNamespace(); default_ns.name = default_key; dict.Add(default_ns.name, default_ns); foreach (var ns in nsList) { string key; if (ns.name == null) { key = default_key; } else { key = ns.name; } if (dict.ContainsKey(key)) { var mns = dict[key]; foreach (var c in ns.classes) { mns.classes.Add(c); } } else { dict[ns.name] = ns; } } ModuleTransform(dict["SmartQuant"]); WriteFilesInProject(assembly.ModuleDefinition, options, directories, dict["SmartQuant"]); } else { base.DecompileAssembly(assembly, output, options); output.WriteLine(); ModuleDefinition mainModule = assembly.ModuleDefinition; if (mainModule.EntryPoint != null) { output.Write("// Entry point: "); output.WriteReference(mainModule.EntryPoint.DeclaringType.FullName + "." + mainModule.EntryPoint.Name, mainModule.EntryPoint); output.WriteLine(); } output.WriteLine("// Architecture: " + GetPlatformDisplayName(mainModule)); if ((mainModule.Attributes & ModuleAttributes.ILOnly) == 0) { output.WriteLine("// This assembly contains unmanaged code."); } switch (mainModule.Runtime) { case TargetRuntime.Net_1_0: output.WriteLine("// Runtime: .NET 1.0"); break; case TargetRuntime.Net_1_1: output.WriteLine("// Runtime: .NET 1.1"); break; case TargetRuntime.Net_2_0: output.WriteLine("// Runtime: .NET 2.0"); break; case TargetRuntime.Net_4_0: output.WriteLine("// Runtime: .NET 4.0"); break; } output.WriteLine(); // don't automatically load additional assemblies when an assembly node is selected in the tree view using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad()) { AstBuilder codeDomBuilder = CreateAstBuilder(options, currentModule: assembly.ModuleDefinition); codeDomBuilder.AddAssembly(assembly.ModuleDefinition, onlyAssemblyLevel: !options.FullDecompilation); codeDomBuilder.RunTransformations(transformAbortCondition); GenerateCode(codeDomBuilder, output); } } }
public static void WriteTo(this Instruction instruction, ITextOutput writer, DisassemblerOptions options, uint baseRva, long baseOffs, IInstructionBytesReader byteReader, MethodDef method) { if (options != null && (options.ShowTokenAndRvaComments || options.ShowILBytes)) { writer.Write("/* ", TextTokenType.Comment); bool needSpace = false; if (options.ShowTokenAndRvaComments) { writer.Write(string.Format("0x{0:X8}", baseOffs + instruction.Offset), TextTokenType.Comment); needSpace = true; } if (options.ShowILBytes) { if (needSpace) { writer.Write(' ', TextTokenType.Comment); } if (byteReader == null) { writer.Write("??", TextTokenType.Comment); } else { int size = instruction.GetSize(); for (int i = 0; i < size; i++) { var b = byteReader.ReadByte(); if (b < 0) { writer.Write("??", TextTokenType.Comment); } else { writer.Write(string.Format("{0:X2}", b), TextTokenType.Comment); } } // Most instructions should be at most 5 bytes in length, but use 6 since // ldftn/ldvirtftn are 6 bytes long. The longest instructions are those with // 8 byte operands, ldc.i8 and ldc.r8: 9 bytes. const int MIN_BYTES = 6; for (int i = size; i < MIN_BYTES; i++) { writer.Write(" ", TextTokenType.Comment); } } } writer.Write(" */", TextTokenType.Comment); writer.WriteSpace(); } writer.WriteDefinition(DnlibExtensions.OffsetToString(instruction.GetOffset()), new InstructionReference(method, instruction), TextTokenType.Label, false); writer.Write(':', TextTokenType.Operator); writer.WriteSpace(); writer.WriteReference(instruction.OpCode.Name, instruction.OpCode, TextTokenType.OpCode); if (instruction.Operand != null) { int count = OPERAND_ALIGNMENT - instruction.OpCode.Name.Length; if (count <= 0) { count = 1; } writer.Write(spaces[count], TextTokenType.Text); if (instruction.OpCode == OpCodes.Ldtoken) { var member = instruction.Operand as IMemberRef; if (member != null && member.IsMethod) { writer.Write("method", TextTokenType.Keyword); writer.WriteSpace(); } else if (member != null && member.IsField) { writer.Write("field", TextTokenType.Keyword); writer.WriteSpace(); } } WriteOperand(writer, instruction.Operand, method); } if (options != null && options.GetOpCodeDocumentation != null) { var doc = options.GetOpCodeDocumentation(instruction.OpCode); if (doc != null) { writer.Write("\t", TextTokenType.Text); writer.Write("// " + doc, TextTokenType.Comment); } } }
public void Write(char ch) { actions.Add(target => target.Write(ch)); }
public override void WriteIdentifier(Identifier identifier) { if (identifier.IsVerbatim || CSharpOutputVisitor.IsKeyword(identifier.Name, identifier)) { output.Write('@'); } var definition = GetCurrentDefinition(); if (definition != null) { output.WriteDefinition(identifier.Name, definition, false); return; } var member = GetCurrentMemberReference(); if (member != null) { MemberReference cecil; if (member is IType type) { cecil = typeSystem.GetCecil(type.GetDefinition()); } else if (member is IMember) { cecil = typeSystem.GetCecil((IMember)member); } else { cecil = null; } if (cecil != null) { output.WriteReference(identifier.Name, cecil); return; } } definition = GetCurrentLocalDefinition(); if (definition != null) { output.WriteDefinition(identifier.Name, definition); return; } var memberRef = GetCurrentLocalReference(); if (memberRef != null) { output.WriteReference(identifier.Name, memberRef, true); return; } if (firstUsingDeclaration) { output.MarkFoldStart(defaultCollapsed: true); firstUsingDeclaration = false; } output.Write(identifier.Name); }
internal void WriteDefinitionTo(ITextOutput output) { if (IsRefReadOnly) { output.Write("readonly "); } switch (Kind) { case VariableKind.Local: output.Write("local "); break; case VariableKind.PinnedLocal: output.Write("pinned local "); break; case VariableKind.Parameter: output.Write("param "); break; case VariableKind.ExceptionLocal: output.Write("exception local "); break; case VariableKind.ExceptionStackSlot: output.Write("exception stack "); break; case VariableKind.StackSlot: output.Write("stack "); break; case VariableKind.InitializerTarget: output.Write("initializer "); break; case VariableKind.ForeachLocal: output.Write("foreach "); break; case VariableKind.UsingLocal: output.Write("using "); break; case VariableKind.NamedArgument: output.Write("named_arg "); break; case VariableKind.DisplayClassLocal: output.Write("display_class local "); break; default: throw new ArgumentOutOfRangeException(); } output.WriteLocalReference(this.Name, this, isDefinition: true); output.Write(" : "); Type.WriteTo(output); output.Write('('); if (Kind == VariableKind.Parameter || Kind == VariableKind.Local || Kind == VariableKind.PinnedLocal) { output.Write("Index={0}, ", Index); } output.Write("LoadCount={0}, AddressCount={1}, StoreCount={2})", LoadCount, AddressCount, StoreCount); if (hasInitialValue && Kind != VariableKind.Parameter) { output.Write(" init"); } if (CaptureScope != null) { output.Write(" captured in "); output.WriteLocalReference(CaptureScope.EntryPoint.Label, CaptureScope); } if (StateMachineField != null) { output.Write(" from state-machine"); } }
public static void WriteOperand(ITextOutput writer, object operand) { if (operand == null) { throw new ArgumentNullException(nameof(operand)); } Instruction targetInstruction = operand as Instruction; if (targetInstruction != null) { WriteOffsetReference(writer, targetInstruction); return; } Instruction[] targetInstructions = operand as Instruction[]; if (targetInstructions != null) { WriteLabelList(writer, targetInstructions); return; } VariableReference variableRef = operand as VariableReference; if (variableRef != null) { writer.WriteReference(variableRef.Index.ToString(), variableRef); return; } ParameterReference paramRef = operand as ParameterReference; if (paramRef != null) { if (string.IsNullOrEmpty(paramRef.Name)) { writer.WriteReference(paramRef.Index.ToString(), paramRef); } else { writer.WriteReference(Escape(paramRef.Name), paramRef); } return; } MethodReference methodRef = operand as MethodReference; if (methodRef != null) { methodRef.WriteTo(writer); return; } TypeReference typeRef = operand as TypeReference; if (typeRef != null) { typeRef.WriteTo(writer, ILNameSyntax.TypeName); return; } FieldReference fieldRef = operand as FieldReference; if (fieldRef != null) { fieldRef.WriteTo(writer); return; } string s = operand as string; if (s != null) { WriteOperand(writer, s); } else if (operand is char) { writer.Write(((int)(char)operand).ToString()); } else if (operand is float) { WriteOperand(writer, (float)operand); } else if (operand is double) { WriteOperand(writer, (double)operand); } else if (operand is bool) { writer.Write((bool)operand ? "true" : "false"); } else { s = ToInvariantCultureString(operand); writer.Write(s); } }
public static void WriteTo(this TypeReference type, ITextOutput writer, ILNameSyntax syntax = ILNameSyntax.Signature) { ILNameSyntax syntaxForElementTypes = syntax == ILNameSyntax.SignatureNoNamedTypeParameters ? syntax : ILNameSyntax.Signature; if (type is PinnedType) { ((PinnedType)type).ElementType.WriteTo(writer, syntaxForElementTypes); writer.Write(" pinned"); } else if (type is ArrayType) { ArrayType at = (ArrayType)type; at.ElementType.WriteTo(writer, syntaxForElementTypes); writer.Write('['); writer.Write(string.Join(", ", at.Dimensions)); writer.Write(']'); } else if (type is GenericParameter) { writer.Write('!'); if (((GenericParameter)type).Owner.GenericParameterType == GenericParameterType.Method) { writer.Write('!'); } if (string.IsNullOrEmpty(type.Name) || type.Name[0] == '!' || syntax == ILNameSyntax.SignatureNoNamedTypeParameters) { writer.Write(((GenericParameter)type).Position.ToString()); } else { writer.Write(Escape(type.Name)); } } else if (type is ByReferenceType) { ((ByReferenceType)type).ElementType.WriteTo(writer, syntaxForElementTypes); writer.Write('&'); } else if (type is PointerType) { ((PointerType)type).ElementType.WriteTo(writer, syntaxForElementTypes); writer.Write('*'); } else if (type is GenericInstanceType) { type.GetElementType().WriteTo(writer, syntaxForElementTypes); writer.Write('<'); var arguments = ((GenericInstanceType)type).GenericArguments; for (int i = 0; i < arguments.Count; i++) { if (i > 0) { writer.Write(", "); } arguments[i].WriteTo(writer, syntaxForElementTypes); } writer.Write('>'); } else if (type is OptionalModifierType) { ((OptionalModifierType)type).ElementType.WriteTo(writer, syntax); writer.Write(" modopt("); ((OptionalModifierType)type).ModifierType.WriteTo(writer, ILNameSyntax.TypeName); writer.Write(") "); } else if (type is RequiredModifierType) { ((RequiredModifierType)type).ElementType.WriteTo(writer, syntax); writer.Write(" modreq("); ((RequiredModifierType)type).ModifierType.WriteTo(writer, ILNameSyntax.TypeName); writer.Write(") "); } else if (type is SentinelType) { writer.Write("..., "); ((SentinelType)type).ElementType.WriteTo(writer, syntax); } else { string name = PrimitiveTypeName(type.FullName); if (syntax == ILNameSyntax.ShortTypeName) { if (name != null) { writer.Write(name); } else { writer.WriteReference(Escape(type.Name), type); } } else if ((syntax == ILNameSyntax.Signature || syntax == ILNameSyntax.SignatureNoNamedTypeParameters) && name != null) { writer.Write(name); } else { if (syntax == ILNameSyntax.Signature || syntax == ILNameSyntax.SignatureNoNamedTypeParameters) { writer.Write(type.IsValueType ? "valuetype " : "class "); } if (type.DeclaringType != null) { type.DeclaringType.WriteTo(writer, ILNameSyntax.TypeName); writer.Write('/'); writer.WriteReference(Escape(type.Name), type); } else { if (!type.IsDefinition && type.Scope != null && !(type is TypeSpecification)) { writer.Write("[{0}]", Escape(type.Scope.Name)); } writer.WriteReference(Escape(type.FullName), type); } } } }
public override void DecompileAssembly(LoadedAssembly assembly, ITextOutput output, DecompilationOptions options) { var module = assembly.GetPEFileOrNull(); if (options.FullDecompilation && options.SaveAsProjectDirectory != null) { var decompiler = new ILSpyWholeProjectDecompiler(assembly, options); decompiler.DecompileProject(module, options.SaveAsProjectDirectory, new TextOutputWriter(output), options.CancellationToken); } else { AddReferenceAssemblyWarningMessage(module, output); AddReferenceWarningMessage(module, output); output.WriteLine(); base.DecompileAssembly(assembly, output, options); // don't automatically load additional assemblies when an assembly node is selected in the tree view using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad()) { IAssemblyResolver assemblyResolver = assembly.GetAssemblyResolver(); var typeSystem = new DecompilerTypeSystem(module, assemblyResolver, options.DecompilerSettings); var globalType = typeSystem.MainModule.TypeDefinitions.FirstOrDefault(); if (globalType != null) { output.Write("// Global type: "); output.WriteReference(globalType, globalType.FullName); output.WriteLine(); } var metadata = module.Metadata; var corHeader = module.Reader.PEHeaders.CorHeader; var entrypointHandle = MetadataTokenHelpers.EntityHandleOrNil(corHeader.EntryPointTokenOrRelativeVirtualAddress); if (!entrypointHandle.IsNil && entrypointHandle.Kind == HandleKind.MethodDefinition) { var entrypoint = typeSystem.MainModule.ResolveMethod(entrypointHandle, new Decompiler.TypeSystem.GenericContext()); if (entrypoint != null) { output.Write("// Entry point: "); output.WriteReference(entrypoint, entrypoint.DeclaringType.FullName + "." + entrypoint.Name); output.WriteLine(); } } output.WriteLine("// Architecture: " + GetPlatformDisplayName(module)); if ((corHeader.Flags & System.Reflection.PortableExecutable.CorFlags.ILOnly) == 0) { output.WriteLine("// This assembly contains unmanaged code."); } string runtimeName = GetRuntimeDisplayName(module); if (runtimeName != null) { output.WriteLine("// Runtime: " + runtimeName); } var debugInfo = assembly.GetDebugInfoOrNull(); if (debugInfo != null) { output.WriteLine("// Debug info: " + debugInfo.Description); } output.WriteLine(); CSharpDecompiler decompiler = new CSharpDecompiler(typeSystem, options.DecompilerSettings); decompiler.CancellationToken = options.CancellationToken; SyntaxTree st; if (options.FullDecompilation) { st = decompiler.DecompileWholeModuleAsSingleFile(); } else { st = decompiler.DecompileModuleAndAssemblyAttributes(); } WriteCode(output, options.DecompilerSettings, st, decompiler.TypeSystem); } } }
public override ProjectId DecompileAssembly(LoadedAssembly assembly, ITextOutput output, DecompilationOptions options) { var module = assembly.GetPEFileOrNull(); if (module == null) { return(null); } if (options.FullDecompilation && options.SaveAsProjectDirectory != null) { var decompiler = new ILSpyWholeProjectDecompiler(assembly, options); return(decompiler.DecompileProject(module, options.SaveAsProjectDirectory, new TextOutputWriter(output), options.CancellationToken)); } else { AddReferenceAssemblyWarningMessage(module, output); AddReferenceWarningMessage(module, output); output.WriteLine(); base.DecompileAssembly(assembly, output, options); // don't automatically load additional assemblies when an assembly node is selected in the tree view using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad(assembly.AssemblyList)) { IAssemblyResolver assemblyResolver = assembly.GetAssemblyResolver(); var typeSystem = new DecompilerTypeSystem(module, assemblyResolver, options.DecompilerSettings); var globalType = typeSystem.MainModule.TypeDefinitions.FirstOrDefault(); if (globalType != null) { output.Write("// Global type: "); output.WriteReference(globalType, globalType.FullName); output.WriteLine(); } var metadata = module.Metadata; var corHeader = module.Reader.PEHeaders.CorHeader; var entrypointHandle = MetadataTokenHelpers.EntityHandleOrNil(corHeader.EntryPointTokenOrRelativeVirtualAddress); if (!entrypointHandle.IsNil && entrypointHandle.Kind == HandleKind.MethodDefinition) { var entrypoint = typeSystem.MainModule.ResolveMethod(entrypointHandle, new Decompiler.TypeSystem.GenericContext()); if (entrypoint != null) { output.Write("// Entry point: "); output.WriteReference(entrypoint, entrypoint.DeclaringType.FullName + "." + entrypoint.Name); output.WriteLine(); } } output.WriteLine("// Architecture: " + GetPlatformDisplayName(module)); if ((corHeader.Flags & System.Reflection.PortableExecutable.CorFlags.ILOnly) == 0) { output.WriteLine("// This assembly contains unmanaged code."); } string runtimeName = GetRuntimeDisplayName(module); if (runtimeName != null) { output.WriteLine("// Runtime: " + runtimeName); } if ((corHeader.Flags & System.Reflection.PortableExecutable.CorFlags.StrongNameSigned) != 0) { output.WriteLine("// This assembly is signed with a strong name key."); } if (metadata.IsAssembly) { var asm = metadata.GetAssemblyDefinition(); if (asm.HashAlgorithm != AssemblyHashAlgorithm.None) { output.WriteLine("// Hash algorithm: " + asm.HashAlgorithm.ToString().ToUpper()); } if (!asm.PublicKey.IsNil) { output.Write("// Public key: "); var reader = metadata.GetBlobReader(asm.PublicKey); while (reader.RemainingBytes > 0) { output.Write(reader.ReadByte().ToString("x2")); } output.WriteLine(); } } var debugInfo = assembly.GetDebugInfoOrNull(); if (debugInfo != null) { output.WriteLine("// Debug info: " + debugInfo.Description); } output.WriteLine(); CSharpDecompiler decompiler = new CSharpDecompiler(typeSystem, options.DecompilerSettings); decompiler.CancellationToken = options.CancellationToken; if (options.EscapeInvalidIdentifiers) { decompiler.AstTransforms.Add(new EscapeInvalidIdentifiers()); } SyntaxTree st; if (options.FullDecompilation) { st = decompiler.DecompileWholeModuleAsSingleFile(); } else { st = decompiler.DecompileModuleAndAssemblyAttributes(); } WriteCode(output, options.DecompilerSettings, st, decompiler.TypeSystem); } return(null); } }
public void WriteOrder(ModuleVM vm) { output.Write(string.Format("{0}", vm.Module.ModuleOrder), TextTokenType.Number); }
public static void WriteOperand(ITextOutput writer, object operand, MethodDef method = null) { Instruction targetInstruction = operand as Instruction; if (targetInstruction != null) { WriteOffsetReference(writer, targetInstruction, method); return; } IList <Instruction> targetInstructions = operand as IList <Instruction>; if (targetInstructions != null) { WriteLabelList(writer, targetInstructions, method); return; } Local variable = operand as Local; if (variable != null) { if (string.IsNullOrEmpty(variable.Name)) { writer.WriteReference(variable.Index.ToString(), variable, TextTokenType.Number); } else { writer.WriteReference(Escape(variable.Name), variable, TextTokenType.Local); } return; } Parameter paramRef = operand as Parameter; if (paramRef != null) { if (string.IsNullOrEmpty(paramRef.Name)) { if (paramRef.IsHiddenThisParameter) { writer.WriteReference("<hidden-this>", paramRef, TextTokenType.Parameter); } else { writer.WriteReference(paramRef.MethodSigIndex.ToString(), paramRef, TextTokenType.Parameter); } } else { writer.WriteReference(Escape(paramRef.Name), paramRef, TextTokenType.Parameter); } return; } MemberRef memberRef = operand as MemberRef; if (memberRef != null) { if (memberRef.IsMethodRef) { memberRef.WriteMethodTo(writer); } else { memberRef.WriteFieldTo(writer); } return; } MethodDef methodDef = operand as MethodDef; if (methodDef != null) { methodDef.WriteMethodTo(writer); return; } FieldDef fieldDef = operand as FieldDef; if (fieldDef != null) { fieldDef.WriteFieldTo(writer); return; } ITypeDefOrRef typeRef = operand as ITypeDefOrRef; if (typeRef != null) { typeRef.WriteTo(writer, ILNameSyntax.TypeName); return; } IMethod m = operand as IMethod; if (m != null) { m.WriteMethodTo(writer); return; } MethodSig sig = operand as MethodSig; if (sig != null) { sig.WriteTo(writer); return; } string s = operand as string; if (s != null) { writer.Write("\"" + NRefactory.CSharp.TextWriterTokenWriter.ConvertString(s) + "\"", TextTokenType.String); } else if (operand is char) { writer.Write(((int)(char)operand).ToString(), TextTokenType.Number); } else if (operand is float) { float val = (float)operand; if (val == 0) { if (1 / val == float.NegativeInfinity) { // negative zero is a special case writer.Write("-0.0", TextTokenType.Number); } else { writer.Write("0.0", TextTokenType.Number); } } else if (float.IsInfinity(val) || float.IsNaN(val)) { byte[] data = BitConverter.GetBytes(val); writer.Write('(', TextTokenType.Operator); for (int i = 0; i < data.Length; i++) { if (i > 0) { writer.WriteSpace(); } writer.Write(data[i].ToString("X2"), TextTokenType.Number); } writer.Write(')', TextTokenType.Operator); } else { writer.Write(val.ToString("R", System.Globalization.CultureInfo.InvariantCulture), TextTokenType.Number); } } else if (operand is double) { double val = (double)operand; if (val == 0) { if (1 / val == double.NegativeInfinity) { // negative zero is a special case writer.Write("-0.0", TextTokenType.Number); } else { writer.Write("0.0", TextTokenType.Number); } } else if (double.IsInfinity(val) || double.IsNaN(val)) { byte[] data = BitConverter.GetBytes(val); writer.Write('(', TextTokenType.Operator); for (int i = 0; i < data.Length; i++) { if (i > 0) { writer.WriteSpace(); } writer.Write(data[i].ToString("X2"), TextTokenType.Number); } writer.Write(')', TextTokenType.Operator); } else { writer.Write(val.ToString("R", System.Globalization.CultureInfo.InvariantCulture), TextTokenType.Number); } } else if (operand is bool) { writer.Write((bool)operand ? "true" : "false", TextTokenType.Keyword); } else { s = ToInvariantCultureString(operand); writer.Write(s, TextTokenHelper.GetTextTokenType(operand)); } }
public void WriteIdentifier(string identifier) { var definition = GetCurrentDefinition(); if (definition != null) { output.WriteDefinition(identifier, definition, false); return; } object memberRef = GetCurrentMemberReference(); if (memberRef != null) { output.WriteReference(identifier, memberRef); return; } definition = GetCurrentLocalDefinition(); if (definition != null) { output.WriteDefinition(identifier, definition); return; } memberRef = GetCurrentLocalReference(); if (memberRef != null) { output.WriteReference(identifier, memberRef, true); return; } if (firstUsingDeclaration) { output.MarkFoldStart(defaultCollapsed: true); firstUsingDeclaration = false; } output.Write(identifier); }
protected override void Write(ITextOutput output, Language language) { output.Write(CleanUpName(this.key), TextTokenType.Text); }
public override void WriteTo(ITextOutput output) { if (Operand is ILVariable && ((ILVariable)Operand).IsGenerated) { if (Code == ILCode.Stloc && this.InferredType == null) { output.Write(((ILVariable)Operand).Name); output.Write(" = "); Arguments.First().WriteTo(output); return; } else if (Code == ILCode.Ldloc) { output.Write(((ILVariable)Operand).Name); if (this.InferredType != null) { output.Write(':'); this.InferredType.WriteTo(output, ILNameSyntax.ShortTypeName); if (this.ExpectedType != null && this.ExpectedType.FullName != this.InferredType.FullName) { output.Write("[exp:"); this.ExpectedType.WriteTo(output, ILNameSyntax.ShortTypeName); output.Write(']'); } } return; } } if (this.Prefixes != null) { foreach (var prefix in this.Prefixes) { output.Write(prefix.Code.GetName()); output.Write(". "); } } output.Write(Code.GetName()); if (this.InferredType != null) { output.Write(':'); this.InferredType.WriteTo(output, ILNameSyntax.ShortTypeName); if (this.ExpectedType != null && this.ExpectedType.FullName != this.InferredType.FullName) { output.Write("[exp:"); this.ExpectedType.WriteTo(output, ILNameSyntax.ShortTypeName); output.Write(']'); } } else if (this.ExpectedType != null) { output.Write("[exp:"); this.ExpectedType.WriteTo(output, ILNameSyntax.ShortTypeName); output.Write(']'); } output.Write('('); bool first = true; if (Operand != null) { if (Operand is ILLabel) { output.WriteReference(((ILLabel)Operand).Name, Operand); } else if (Operand is ILLabel[]) { ILLabel[] labels = (ILLabel[])Operand; for (int i = 0; i < labels.Length; i++) { if (i > 0) { output.Write(", "); } output.WriteReference(labels[i].Name, labels[i]); } } else if (Operand is MethodReference) { MethodReference method = (MethodReference)Operand; if (method.DeclaringType != null) { method.DeclaringType.WriteTo(output, ILNameSyntax.ShortTypeName); output.Write("::"); } output.WriteReference(method.Name, method); } else if (Operand is FieldReference) { FieldReference field = (FieldReference)Operand; field.DeclaringType.WriteTo(output, ILNameSyntax.ShortTypeName); output.Write("::"); output.WriteReference(field.Name, field); } else { DisassemblerHelpers.WriteOperand(output, Operand); } first = false; } foreach (ILExpression arg in this.Arguments) { if (!first) { output.Write(", "); } arg.WriteTo(output); first = false; } output.Write(')'); }
public override void DecompileAssembly(LoadedAssembly assembly, ITextOutput output, DecompilationOptions options) { if (options.FullDecompilation && options.SaveAsProjectDirectory != null) { HashSet <string> directories = new HashSet <string>(StringComparer.OrdinalIgnoreCase); var files = WriteCodeFilesInProject(assembly.AssemblyDefinition, options, directories).ToList(); files.AddRange(WriteResourceFilesInProject(assembly, options, directories)); WriteProjectFile(new TextOutputWriter(output), files, assembly.AssemblyDefinition.MainModule); } else { base.DecompileAssembly(assembly, output, options); output.WriteLine(); ModuleDefinition mainModule = assembly.AssemblyDefinition.MainModule; if (mainModule.EntryPoint != null) { output.Write("' Entry point: "); output.WriteReference(mainModule.EntryPoint.DeclaringType.FullName + "." + mainModule.EntryPoint.Name, mainModule.EntryPoint); output.WriteLine(); } switch (mainModule.Architecture) { case TargetArchitecture.I386: if ((mainModule.Attributes & ModuleAttributes.Required32Bit) == ModuleAttributes.Required32Bit) { WriteCommentLine(output, "Architecture: x86"); } else { WriteCommentLine(output, "Architecture: AnyCPU"); } break; case TargetArchitecture.AMD64: WriteCommentLine(output, "Architecture: x64"); break; case TargetArchitecture.IA64: WriteCommentLine(output, "Architecture: Itanium-64"); break; } if ((mainModule.Attributes & ModuleAttributes.ILOnly) == 0) { WriteCommentLine(output, "This assembly contains unmanaged code."); } switch (mainModule.Runtime) { case TargetRuntime.Net_1_0: WriteCommentLine(output, "Runtime: .NET 1.0"); break; case TargetRuntime.Net_1_1: WriteCommentLine(output, "Runtime: .NET 1.1"); break; case TargetRuntime.Net_2_0: WriteCommentLine(output, "Runtime: .NET 2.0"); break; case TargetRuntime.Net_4_0: WriteCommentLine(output, "Runtime: .NET 4.0"); break; } output.WriteLine(); // don't automatically load additional assemblies when an assembly node is selected in the tree view using (options.FullDecompilation ? null : LoadedAssembly.DisableAssemblyLoad()) { AstBuilder codeDomBuilder = CreateAstBuilder(options, currentModule: assembly.AssemblyDefinition.MainModule); codeDomBuilder.AddAssembly(assembly.AssemblyDefinition, onlyAssemblyLevel: !options.FullDecompilation); RunTransformsAndGenerateCode(codeDomBuilder, output, options, assembly.AssemblyDefinition.MainModule); } } }
protected override void Write(ITextOutput output, Language language) { Language.TypeToString(output, analyzedField.DeclaringType, true); output.Write('.', TextTokenType.Operator); FieldTreeNode.Write(output, analyzedField, Language); }
public override void WriteIdentifier(Identifier identifier) { if (identifier.IsVerbatim || CSharpOutputVisitor.IsKeyword(identifier.Name, identifier)) { output.Write('@'); } var definition = GetCurrentDefinition(); string name = TextWriterTokenWriter.EscapeIdentifier(identifier.Name); switch (definition) { case IType t: output.WriteReference(t, name, true); return; case IMember m: output.WriteReference(m, name, true); return; } var member = GetCurrentMemberReference(); switch (member) { case IType t: output.WriteReference(t, name, false); return; case IMember m: output.WriteReference(m, name, false); return; } var localDefinition = GetCurrentLocalDefinition(); if (localDefinition != null) { output.WriteLocalReference(name, localDefinition, isDefinition: true); return; } var localRef = GetCurrentLocalReference(); if (localRef != null) { output.WriteLocalReference(name, localRef); return; } if (firstUsingDeclaration) { output.MarkFoldStart(defaultCollapsed: !settings.ExpandUsingDeclarations); firstUsingDeclaration = false; } output.Write(name); }
protected override void Write(ITextOutput output, Language language) { output.Write("Overridden By", TextTokenType.Text); }
public static void Write(this ITextOutput output, string format, params object[] args) { output.Write(string.Format(format, args)); }
public override void WriteTo(ITextOutput output, ILAstWritingOptions options) { output.Write(OpCode); // the non-custom WriteTo would add useless parentheses }
public static void WriteLine(this ITextOutput output, string text) { output.Write(text); output.WriteLine(); }
public void Disassemble(MethodDef method, MemberMapping debugSymbols) { // start writing IL code CilBody body = method.Body; uint codeSize = (uint)body.GetCodeSize(); output.WriteLine(string.Format("// RVA 0x{0:x8} - 0x{1:x8} ({2} (0x{2:x}) bytes)", (uint)method.RVA, (uint)method.RVA + codeSize, codeSize), TextTokenType.Comment); output.WriteLine(string.Format("// Metadata token 0x{0:x8} (RID {1})", method.MDToken.ToInt32(), method.Rid), TextTokenType.Comment); if (body.LocalVarSigTok != 0) { output.WriteLine(string.Format("// LocalVarSig token 0x{0:x8} (RID {1})", body.LocalVarSigTok, body.LocalVarSigTok & 0xFFFFFF), TextTokenType.Comment); } output.Write(".maxstack", TextTokenType.ILDirective); output.WriteSpace(); output.WriteLine(string.Format("{0}", body.MaxStack), TextTokenType.Number); if (method.DeclaringType.Module.EntryPoint == method) { output.WriteLine(".entrypoint", TextTokenType.ILDirective); } if (method.Body.HasVariables) { output.Write(".locals", TextTokenType.ILDirective); output.WriteSpace(); if (method.Body.InitLocals) { output.Write("init", TextTokenType.Keyword); output.WriteSpace(); } output.WriteLine("(", TextTokenType.Operator); output.Indent(); foreach (var v in method.Body.Variables) { output.Write('[', TextTokenType.Operator); output.WriteDefinition(v.Index.ToString(), v, TextTokenType.Number); output.Write(']', TextTokenType.Operator); output.WriteSpace(); v.Type.WriteTo(output); if (!string.IsNullOrEmpty(v.Name)) { output.WriteSpace(); output.Write(DisassemblerHelpers.Escape(v.Name), TextTokenType.Local); } if (v.Index + 1 < method.Body.Variables.Count) { output.Write(',', TextTokenType.Operator); } output.WriteLine(); } output.Unindent(); output.WriteLine(")", TextTokenType.Operator); } output.WriteLine(); if (detectControlStructure && body.Instructions.Count > 0) { int index = 0; HashSet <uint> branchTargets = GetBranchTargets(body.Instructions); WriteStructureBody(body, new ILStructure(body), branchTargets, ref index, debugSymbols, method.Body.GetCodeSize()); } else { var instructions = method.Body.Instructions; for (int i = 0; i < instructions.Count; i++) { var inst = instructions[i]; var startLocation = output.Location; inst.WriteTo(output, options.GetOpCodeDocumentation); if (debugSymbols != null) { // add IL code mappings - used in debugger var next = i + 1 < instructions.Count ? instructions[i + 1] : null; debugSymbols.MemberCodeMappings.Add( new SourceCodeMapping() { StartLocation = output.Location, EndLocation = output.Location, ILInstructionOffset = new ILRange(inst.Offset, next == null ? (uint)method.Body.GetCodeSize() : next.Offset), MemberMapping = debugSymbols }); } output.WriteLine(); } if (method.Body.HasExceptionHandlers) { output.WriteLine(); foreach (var eh in method.Body.ExceptionHandlers) { eh.WriteTo(output); output.WriteLine(); } } } }
public static void WriteTo(this MethodReference method, ITextOutput writer) { if (method.ExplicitThis) { writer.Write("instance explicit "); } else if (method.HasThis) { writer.Write("instance "); } if (method.CallingConvention == MethodCallingConvention.VarArg) { writer.Write("vararg "); } method.ReturnType.WriteTo(writer, ILNameSyntax.SignatureNoNamedTypeParameters); writer.Write(' '); if (method.DeclaringType != null) { method.DeclaringType.WriteTo(writer, ILNameSyntax.TypeName); writer.Write("::"); } MethodDefinition md = method as MethodDefinition; if (md != null && md.IsCompilerControlled) { writer.WriteReference(Escape(method.Name + "$PST" + method.MetadataToken.ToInt32().ToString("X8")), method); } else { writer.WriteReference(Escape(method.Name), method); } GenericInstanceMethod gim = method as GenericInstanceMethod; if (gim != null) { writer.Write('<'); for (int i = 0; i < gim.GenericArguments.Count; i++) { if (i > 0) { writer.Write(", "); } gim.GenericArguments[i].WriteTo(writer); } writer.Write('>'); } writer.Write("("); var parameters = method.Parameters; for (int i = 0; i < parameters.Count; ++i) { if (i > 0) { writer.Write(", "); } parameters[i].ParameterType.WriteTo(writer, ILNameSyntax.SignatureNoNamedTypeParameters); } writer.Write(")"); }
protected override void Write(ITextOutput output, Language language) { output.Write(showWrites ? "Assigned By" : "Read By", TextTokenType.Text); }