Пример #1
0
		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);
				}
			}
		}
Пример #2
0
		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);
		}
		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);
			}
		}
Пример #4
0
		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);
				}
			}
		}
Пример #5
0
 public override void WriteTo(ITextOutput output)
 {
     output.Write("catch ");
     output.WriteReference(ExceptionType.FullName, ExceptionType);
     if (ExceptionVariable != null)
     {
         output.Write(' ');
         output.Write(ExceptionVariable.Name);
     }
     output.WriteLine(" {");
     output.Indent();
     base.WriteTo(output);
     output.Unindent();
     output.WriteLine("}");
 }
Пример #6
0
		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);
			}
		}
Пример #7
0
        public static void WriteTo(this XMethodReference method, ITextOutput writer)
        {
            if (method.HasThis)
            {
                writer.Write("instance ");
            }
            method.ReturnType.WriteTo(writer, AstNameSyntax.SignatureNoNamedTypeParameters);
            writer.Write(' ');
            if (method.DeclaringType != null)
            {
                method.DeclaringType.WriteTo(writer, AstNameSyntax.TypeName);
                writer.Write("::");
            }
            writer.WriteReference(Escape(method.Name), method);
            var gim = method as XGenericInstanceMethod;

            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, AstNameSyntax.SignatureNoNamedTypeParameters);
            }
            writer.Write(")");
        }
Пример #8
0
        internal static void WriteKeyword(ITextOutput writer, string name, ITypeDefOrRef tdr)
        {
            var parts = name.Split(' ');

            for (int i = 0; i < parts.Length; i++)
            {
                if (i > 0)
                {
                    writer.WriteSpace();
                }
                if (tdr != null)
                {
                    writer.WriteReference(parts[i], tdr, TextTokenType.Keyword);
                }
                else
                {
                    writer.Write(parts[i], TextTokenType.Keyword);
                }
            }
        }
Пример #9
0
        public static void WriteOffsetComment(this ITextOutput output, IResourceNode node)
        {
            if (!DecompilerSettingsPanel.CurrentDecompilerSettings.ShowTokenAndRvaComments)
            {
                return;
            }

            ulong fo = node.FileOffset;

            if (fo == 0)
            {
                return;
            }

            var mod      = ILSpyTreeNode.GetModule((SharpTreeNode)node);
            var filename = mod == null ? null : mod.Location;

            output.WriteReference(string.Format("0x{0:X8}", fo), new AddressReference(filename, false, fo, node.Length), TextTokenType.Comment);
            output.Write(": ", TextTokenType.Comment);
        }
Пример #10
0
        public static void WriteOffsetComment(this ITextOutput output, IResourceDataProvider node, bool showOffsetComment)
        {
            if (!showOffsetComment)
            {
                return;
            }

            ulong fo = node.FileOffset;

            if (fo == 0)
            {
                return;
            }

            var mod      = (node as IFileTreeNodeData).GetModule();
            var filename = mod == null ? null : mod.Location;

            output.WriteReference(string.Format("0x{0:X8}", fo), new AddressReference(filename, false, fo, node.Length), TextTokenKind.Comment);
            output.Write(": ", TextTokenKind.Comment);
        }
Пример #11
0
        public override void Decompile(TypeDef type, ITextOutput output, DecompilationContext ctx)
        {
            this.WriteCommentLine(output, string.Format("Type: {0}", type.FullName));
            if (type.BaseType != null)
            {
                WriteCommentBegin(output, true);
                output.Write("Base type: ", TextTokenKind.Comment);
                output.WriteReference(IdentifierEscaper.Escape(type.BaseType.FullName), type.BaseType, TextTokenKind.Comment);
                WriteCommentEnd(output, true);
                output.WriteLine();
            }
            foreach (var nested in type.NestedTypes)
            {
                Decompile(nested, output, ctx);
                output.WriteLine();
            }

            foreach (var field in type.Fields)
            {
                Decompile(field, output, ctx);
                output.WriteLine();
            }

            foreach (var property in type.Properties)
            {
                Decompile(property, output, ctx);
                output.WriteLine();
            }

            foreach (var @event in type.Events)
            {
                Decompile(@event, output, ctx);
                output.WriteLine();
            }

            foreach (var method in type.Methods)
            {
                Decompile(method, output, ctx);
                output.WriteLine();
            }
        }
Пример #12
0
        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.ModuleDefinition, options, directories).ToList();
                files.AddRange(WriteResourceFilesInProject(assembly, options, directories));
                WriteProjectFile(new TextOutputWriter(output), files, assembly.ModuleDefinition);
            }
            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.");
                }
                string runtimeName = GetRuntimeDisplayName(mainModule);
                if (runtimeName != null)
                {
                    output.WriteLine("// Runtime: " + runtimeName);
                }
                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);
                    codeDomBuilder.GenerateCode(output);
                }
            }
        }
Пример #13
0
        public override void DecompileType(TypeDef type, ITextOutput output, DecompilationOptions options)
        {
            WriteCommentLine(output, string.Format("Type: {0}", type.FullName));
            if (type.BaseType != null)
            {
                WriteComment(output, string.Format("Base type: "));
                output.WriteReference(IdentifierEscaper.Escape(type.BaseType.FullName), type.BaseType, TextTokenType.Comment);
                output.WriteLine();
            }
            foreach (var nested in type.NestedTypes)
            {
                DecompileType(nested, output, options);
                output.WriteLine();
            }

            foreach (var field in type.Fields)
            {
                DecompileField(field, output, options);
                output.WriteLine();
            }

            foreach (var property in type.Properties)
            {
                DecompileProperty(property, output, options);
                output.WriteLine();
            }

            foreach (var @event in type.Events)
            {
                DecompileEvent(@event, output, options);
                output.WriteLine();
            }

            foreach (var method in type.Methods)
            {
                DecompileMethod(method, output, options);
                output.WriteLine();
            }
        }
		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;
				}
			}
		}
 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 static void WriteTo(this Instruction instruction, MethodDef method, ITextOutput writer)
 {
     writer.WriteDefinition(DnlibExtensions.OffsetToString(instruction.Offset), instruction);
     writer.Write(": ");
     writer.WriteReference(instruction.OpCode.Name, instruction.OpCode);
     if (instruction.Operand != null)
     {
         writer.Write(' ');
         if (instruction.OpCode == OpCodes.Ldtoken)
         {
             MemberRef member = instruction.Operand as MemberRef;
             if ((member != null && member.IsMethodRef) || instruction.Operand is MethodDef || instruction.Operand is MethodSpec)
             {
                 writer.Write("method ");
             }
             else if ((member != null && member.IsFieldRef) || instruction.Operand is FieldDef)
             {
                 writer.Write("field ");
             }
         }
         WriteOperand(writer, instruction.Operand.ResolveGenericParams(method));
     }
 }
Пример #17
0
        public static void WriteTo(this MethodReference method, ITextOutput writer)
        {
            if (method.ExplicitThis)
            {
                writer.Write("instance explicit ");
            }
            else if (method.HasThis)
            {
                writer.Write("instance ");
            }

            method.ReturnType.WriteTo(writer, ILNameSyntax.SignatureNoNamedTypeParameters);
            writer.Write(' ');
            if (method.DeclaringType != null)
            {
                method.DeclaringType.WriteTo(writer, ILNameSyntax.TypeName);
                writer.Write("::");
            }

            if (method is MethodDefinition md && md.IsCompilerControlled)
            {
                writer.WriteReference(Escape(method.Name + "$PST" + method.MetadataToken.ToInt32().ToString("X8")), method);
            }
Пример #18
0
        protected void WriteModule(ModuleDef mod, ITextOutput output, DecompilationContext ctx)
        {
            DecompileInternal(mod, output, ctx);
            output.WriteLine();
            if (mod.Types.Count > 0)
            {
                this.WriteCommentBegin(output, true);
                output.Write(Languages_Resources.Decompile_GlobalType + " ", TextTokenKind.Comment);
                output.WriteReference(IdentifierEscaper.Escape(mod.GlobalType.FullName), mod.GlobalType, TextTokenKind.Comment);
                output.WriteLine();
            }
            this.PrintEntryPoint(mod, output);
            this.WriteCommentLine(output, Languages_Resources.Decompile_Architecture + " " + GetPlatformDisplayName(mod));
            if (!mod.IsILOnly)
            {
                this.WriteCommentLine(output, Languages_Resources.Decompile_ThisAssemblyContainsUnmanagedCode);
            }
            string runtimeName = GetRuntimeDisplayName(mod);

            if (runtimeName != null)
            {
                this.WriteCommentLine(output, Languages_Resources.Decompile_Runtime + " " + runtimeName);
            }
            var peImage = TryGetPEImage(mod);

            if (peImage != null)
            {
                this.WriteCommentBegin(output, true);
                uint ts         = peImage.ImageNTHeaders.FileHeader.TimeDateStamp;
                var  date       = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc).AddSeconds(ts);
                var  dateString = date.ToString(CultureInfo.CurrentUICulture.DateTimeFormat);
                output.Write(string.Format(Languages_Resources.Decompile_Timestamp, ts, dateString), TextTokenKind.Comment);
                this.WriteCommentEnd(output, true);
                output.WriteLine();
            }
            output.WriteLine();
        }
Пример #19
0
        public static void WriteTo(this MethodReference method, ITextOutput writer)
        {
            if (method.HasThis)
            {
                writer.Write("instance ");
            }
            method.ReturnType.WriteTo(writer);
            writer.Write(' ');
            method.DeclaringType.WriteTo(writer, true);
            writer.Write("::");
            writer.WriteReference(method.Name, method);
            writer.Write("(");
            var parameters = method.Parameters;

            for (int i = 0; i < parameters.Count; ++i)
            {
                if (i > 0)
                {
                    writer.Write(", ");
                }
                parameters[i].ParameterType.WriteTo(writer);
            }
            writer.Write(")");
        }
		public static void WriteTo(this ITypeDefOrRef type, ITextOutput writer, ILNameSyntax syntax = ILNameSyntax.Signature)
		{
			if (type is TypeSpec) {
				((TypeSpec)type).TypeSig.WriteTo(writer, syntax);
				return;
			}

			string name = PrimitiveTypeName(type.FullName);
			if (syntax == ILNameSyntax.ShortTypeName) {
				if (name != null)
					writer.WriteKeyword(name);
				else
					writer.WriteReference(Escape(type.Name), type);
			}
			else if ((syntax == ILNameSyntax.Signature || syntax == ILNameSyntax.SignatureNoNamedTypeParameters) && name != null) {
				writer.WriteKeyword(name);
			}
			else {
				if (syntax == ILNameSyntax.Signature || syntax == ILNameSyntax.SignatureNoNamedTypeParameters)
					writer.WriteKeyword(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 is TypeDef) && type.Scope != null) {
						IAssembly assembly;
						if (type.Scope is IAssembly)
							assembly = (IAssembly)type.Scope;
						else if (type.Scope is ModuleRef)
							assembly = ((ModuleRef)type.Scope).DefinitionAssembly;
						else if (type.Scope is ModuleDef)
							assembly = ((ModuleDef)type.Scope).Assembly;
						else
							throw new NotSupportedException();
						writer.Write("[");
						writer.WriteReference(Escape(assembly.Name), assembly);
						writer.Write("]");
					}
					writer.WriteReference(Escape(type.FullName), type);
				}
			}
		}
		public static void WriteTo(this MethodSig signature, IMethod method, ITextOutput writer)
		{
			if (signature.ExplicitThis) {
				writer.WriteKeyword("instance explicit ");
			}
			else if (signature.HasThis) {
				writer.WriteKeyword("instance ");
			}
			signature.RetType.WriteTo(writer, ILNameSyntax.SignatureNoNamedTypeParameters);
			writer.Write(' ');
			if (method != null && method.DeclaringType != null) {
				method.DeclaringType.WriteTo(writer, ILNameSyntax.TypeName);
				writer.Write("::");
			}
			MethodDef md = method as MethodDef;
			if (md != null && md.IsCompilerControlled) {
				writer.WriteReference(Escape(method.Name + "$PST" + method.MDToken.Raw.ToString("X8")), method);
			} else if (method != null) {
				writer.WriteReference(Escape(method.Name), method);
			} else {
				writer.Write("(*)");
			}
			MethodSpec methodSpec = method as MethodSpec;
			if (methodSpec != null) {
				writer.Write('<');
				var genArgs = methodSpec.GenericInstMethodSig.GenericArguments;
				for (int i = 0; i < genArgs.Count; i++) {
					if (i > 0)
						writer.Write(", ");
					genArgs[i].WriteTo(writer);
				}
				writer.Write('>');
			}
			writer.Write("(");
			for (int i = 0; i < signature.Params.Count; ++i) {
				if (i > 0) writer.Write(", ");
				signature.Params[i].WriteTo(writer, ILNameSyntax.SignatureNoNamedTypeParameters);
			}
			if (signature.ParamsAfterSentinel != null && signature.ParamsAfterSentinel.Count > 0) {
				if (signature.Params.Count > 0)
					writer.Write(", ");

				writer.Write("...");
				for (int i = 0; i < signature.ParamsAfterSentinel.Count; ++i) {
					if (i > 0) writer.Write(", ");
					signature.ParamsAfterSentinel[i].WriteTo(writer, ILNameSyntax.SignatureNoNamedTypeParameters);
				}
			}
			writer.Write(")");
		}
Пример #22
0
        public static void WriteTo(this ITypeDefOrRef type, ITextOutput writer, ILNameSyntax syntax, int depth)
        {
            if (depth++ > MAX_CONVERTTYPE_DEPTH || type == null)
                return;
            var ts = type as TypeSpec;
            if (ts != null && !(ts.TypeSig is FnPtrSig)) {
                WriteTo(((TypeSpec)type).TypeSig, writer, syntax, depth);
                return;
            }
            string typeFullName = type.FullName;
            string typeName = type.Name.String;
            if (ts != null) {
                var fnPtrSig = ts.TypeSig as FnPtrSig;
                typeFullName = DnlibExtensions.GetFnPtrFullName(fnPtrSig);
                typeName = DnlibExtensions.GetFnPtrName(fnPtrSig);
            }
            TypeSig typeSig = null;
            string name = type.DefinitionAssembly.IsCorLib() ? PrimitiveTypeName(typeFullName, type.Module, out typeSig) : null;
            if (syntax == ILNameSyntax.ShortTypeName) {
                if (name != null)
                    WriteKeyword(writer, name, typeSig.ToTypeDefOrRef());
                else
                    writer.WriteReference(Escape(typeName), type, TextTokenHelper.GetTextTokenType(type));
            } else if ((syntax == ILNameSyntax.Signature || syntax == ILNameSyntax.SignatureNoNamedTypeParameters) && name != null) {
                WriteKeyword(writer, name, typeSig.ToTypeDefOrRef());
            } else {
                if (syntax == ILNameSyntax.Signature || syntax == ILNameSyntax.SignatureNoNamedTypeParameters) {
                    writer.Write(DnlibExtensions.IsValueType(type) ? "valuetype" : "class", TextTokenType.Keyword);
                    writer.WriteSpace();
                }

                if (type.DeclaringType != null) {
                    type.DeclaringType.WriteTo(writer, ILNameSyntax.TypeName, depth);
                    writer.Write('/', TextTokenType.Operator);
                    writer.WriteReference(Escape(typeName), type, TextTokenHelper.GetTextTokenType(type));
                } else {
                    if (!(type is TypeDef) && type.Scope != null && !(type is TypeSpec)) {
                        writer.Write('[', TextTokenType.Operator);
                        writer.Write(Escape(type.Scope.GetScopeName()), TextTokenType.ILModule);
                        writer.Write(']', TextTokenType.Operator);
                    }
                    if (ts != null || MustEscape(typeFullName))
                        writer.WriteReference(Escape(typeFullName), type, TextTokenHelper.GetTextTokenType(type));
                    else {
                        WriteNamespace(writer, type.Namespace);
                        if (!string.IsNullOrEmpty(type.Namespace))
                            writer.Write('.', TextTokenType.Operator);
                        writer.WriteReference(IdentifierEscaper.Escape(type.Name), type, TextTokenHelper.GetTextTokenType(type));
                    }
                }
            }
        }
Пример #23
0
        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));
            }
        }
Пример #24
0
 public static void WriteFieldTo(this IField field, ITextOutput writer)
 {
     if (field == null || field.FieldSig == null)
         return;
     field.FieldSig.Type.WriteTo(writer, ILNameSyntax.SignatureNoNamedTypeParameters);
     writer.WriteSpace();
     field.DeclaringType.WriteTo(writer, ILNameSyntax.TypeName);
     writer.Write("::", TextTokenType.Operator);
     writer.WriteReference(Escape(field.Name), field, TextTokenHelper.GetTextTokenType(field));
 }
Пример #25
0
		public static void WriteOperand(ITextOutput writer, object operand)
		{
			if (operand == null)
				throw new ArgumentNullException("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) {
				if (string.IsNullOrEmpty(variableRef.Name))
					writer.WriteReference(variableRef.Index.ToString(), variableRef);
				else
					writer.WriteReference(Escape(variableRef.Name), 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) {
				writer.Write("\"" + NRefactory.CSharp.TextWriterTokenWriter.ConvertString(s) + "\"");
			} else if (operand is char) {
				writer.Write(((int)(char)operand).ToString());
			} else if (operand is float) {
				float val = (float)operand;
				if (val == 0) {
					writer.Write("0.0");
				} else if (float.IsInfinity(val) || float.IsNaN(val)) {
					byte[] data = BitConverter.GetBytes(val);
					writer.Write('(');
					for (int i = 0; i < data.Length; i++) {
						if (i > 0)
							writer.Write(' ');
						writer.Write(data[i].ToString("X2"));
					}
					writer.Write(')');
				} else {
					writer.Write(val.ToString("R", System.Globalization.CultureInfo.InvariantCulture));
				}
			} else if (operand is double) {
				double val = (double)operand;
				if (val == 0) {
					writer.Write("0.0");
				} else if (double.IsInfinity(val) || double.IsNaN(val)) {
					byte[] data = BitConverter.GetBytes(val);
					writer.Write('(');
					for (int i = 0; i < data.Length; i++) {
						if (i > 0)
							writer.Write(' ');
						writer.Write(data[i].ToString("X2"));
					}
					writer.Write(')');
				} else {
					writer.Write(val.ToString("R", System.Globalization.CultureInfo.InvariantCulture));
				}
			} else if (operand is bool) {
				writer.Write((bool)operand ? "true" : "false");
			} else {
				s = ToInvariantCultureString(operand);
				writer.Write(s);
			}
		}
 public static void WriteOffsetReference(ITextOutput writer, Instruction instruction)
 {
     writer.WriteReference(CecilExtensions.OffsetToString(instruction.Offset), instruction);
 }
 public static void WriteTo(this IMember member, ITextOutput output)
 {
     if (member is IMethod method && method.IsConstructor)
     {
         output.WriteReference(member, method.DeclaringType?.Name + "." + method.Name);
     }
 public static void WriteTo(this IType type, ITextOutput output, ILNameSyntax nameSyntax = ILNameSyntax.ShortTypeName)
 {
     output.WriteReference(type, type.ReflectionName);
 }
Пример #29
0
        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.ModuleDefinition, options, directories).ToList();
                files.AddRange(WriteResourceFilesInProject(assembly, options, directories));
                WriteProjectFile(new TextOutputWriter(output), files, assembly.ModuleDefinition);
            } else {
                base.DecompileAssembly(assembly, output, options);
                output.WriteLine();
                ModuleDefinition mainModule = assembly.ModuleDefinition;
                if (mainModule.Types.Count > 0) {
                    output.Write("// Global type: ");
                    output.WriteReference(mainModule.Types[0].FullName, mainModule.Types[0]);
                    output.WriteLine();
                }
                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.");
                }
                string runtimeName = GetRuntimeDisplayName(mainModule);
                if (runtimeName != null) {
                    output.WriteLine("// Runtime: " + runtimeName);
                }
                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);
                    codeDomBuilder.GenerateCode(output);
                }
            }
        }
Пример #30
0
        public override void WriteTo(ITextOutput output, MemberMapping memberMapping)
        {
            var startLoc = output.Location;

            if (Operand is ILVariable && ((ILVariable)Operand).GeneratedByDecompiler)
            {
                if (Code == ILCode.Stloc && this.InferredType == null)
                {
                    output.WriteReference(((ILVariable)Operand).Name, Operand, ((ILVariable)Operand).IsParameter ? TextTokenKind.Parameter : TextTokenKind.Local);
                    output.WriteSpace();
                    output.Write("=", TextTokenKind.Operator);
                    output.WriteSpace();
                    Arguments.First().WriteTo(output, null);
                    UpdateMemberMapping(memberMapping, startLoc, output.Location, this.GetSelfAndChildrenRecursiveILRanges());
                    return;
                }
                else if (Code == ILCode.Ldloc)
                {
                    output.WriteReference(((ILVariable)Operand).Name, Operand, ((ILVariable)Operand).IsParameter ? TextTokenKind.Parameter : TextTokenKind.Local);
                    if (this.InferredType != null)
                    {
                        output.Write(":", TextTokenKind.Operator);
                        this.InferredType.WriteTo(output, ILNameSyntax.ShortTypeName);
                        if (this.ExpectedType != null && this.ExpectedType.FullName != this.InferredType.FullName)
                        {
                            output.Write("[", TextTokenKind.Operator);
                            output.Write("exp", TextTokenKind.Keyword);
                            output.Write(":", TextTokenKind.Operator);
                            this.ExpectedType.WriteTo(output, ILNameSyntax.ShortTypeName);
                            output.Write("]", TextTokenKind.Operator);
                        }
                    }
                    UpdateMemberMapping(memberMapping, startLoc, output.Location, this.GetSelfAndChildrenRecursiveILRanges());
                    return;
                }
            }

            if (this.Prefixes != null)
            {
                foreach (var prefix in this.Prefixes)
                {
                    output.Write(prefix.Code.GetName() + ".", TextTokenKind.OpCode);
                    output.WriteSpace();
                }
            }

            output.Write(Code.GetName(), TextTokenKind.OpCode);
            if (this.InferredType != null)
            {
                output.Write(":", TextTokenKind.Operator);
                this.InferredType.WriteTo(output, ILNameSyntax.ShortTypeName);
                if (this.ExpectedType != null && this.ExpectedType.FullName != this.InferredType.FullName)
                {
                    output.Write("[", TextTokenKind.Operator);
                    output.Write("exp", TextTokenKind.Keyword);
                    output.Write(":", TextTokenKind.Operator);
                    this.ExpectedType.WriteTo(output, ILNameSyntax.ShortTypeName);
                    output.Write("]", TextTokenKind.Operator);
                }
            }
            else if (this.ExpectedType != null)
            {
                output.Write("[", TextTokenKind.Operator);
                output.Write("exp", TextTokenKind.Keyword);
                output.Write(":", TextTokenKind.Operator);
                this.ExpectedType.WriteTo(output, ILNameSyntax.ShortTypeName);
                output.Write("]", TextTokenKind.Operator);
            }
            output.Write("(", TextTokenKind.Operator);
            bool first = true;

            if (Operand != null)
            {
                if (Operand is ILLabel)
                {
                    output.WriteReference(((ILLabel)Operand).Name, Operand, TextTokenKind.Label);
                }
                else if (Operand is ILLabel[])
                {
                    ILLabel[] labels = (ILLabel[])Operand;
                    for (int i = 0; i < labels.Length; i++)
                    {
                        if (i > 0)
                        {
                            output.Write(",", TextTokenKind.Operator);
                            output.WriteSpace();
                        }
                        output.WriteReference(labels[i].Name, labels[i], TextTokenKind.Label);
                    }
                }
                else if (Operand is IMethod && (Operand as IMethod).MethodSig != null)
                {
                    IMethod method = (IMethod)Operand;
                    if (method.DeclaringType != null)
                    {
                        method.DeclaringType.WriteTo(output, ILNameSyntax.ShortTypeName);
                        output.Write("::", TextTokenKind.Operator);
                    }
                    output.WriteReference(method.Name, method, TextTokenKindUtils.GetTextTokenType(method));
                }
                else if (Operand is IField)
                {
                    IField field = (IField)Operand;
                    field.DeclaringType.WriteTo(output, ILNameSyntax.ShortTypeName);
                    output.Write("::", TextTokenKind.Operator);
                    output.WriteReference(field.Name, field, TextTokenKindUtils.GetTextTokenType(field));
                }
                else if (Operand is ILVariable)
                {
                    var ilvar = (ILVariable)Operand;
                    output.WriteReference(ilvar.Name, Operand, ilvar.IsParameter ? TextTokenKind.Parameter : TextTokenKind.Local);
                }
                else
                {
                    DisassemblerHelpers.WriteOperand(output, Operand);
                }
                first = false;
            }
            foreach (ILExpression arg in this.Arguments)
            {
                if (!first)
                {
                    output.Write(",", TextTokenKind.Operator);
                    output.WriteSpace();
                }
                arg.WriteTo(output, null);
                first = false;
            }
            output.Write(")", TextTokenKind.Operator);
            UpdateMemberMapping(memberMapping, startLoc, output.Location, this.GetSelfAndChildrenRecursiveILRanges());
        }
Пример #31
0
        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);
                }
            }
        }
Пример #32
0
        public static void WriteTo(this ITypeDefOrRef type, ITextOutput writer, ILNameSyntax syntax, int depth)
        {
            if (depth++ > MAX_CONVERTTYPE_DEPTH || type == null)
            {
                return;
            }
            var ts = type as TypeSpec;

            if (ts != null && !(ts.TypeSig is FnPtrSig))
            {
                WriteTo(((TypeSpec)type).TypeSig, writer, syntax, depth);
                return;
            }
            string typeFullName = type.FullName;
            string typeName     = type.Name.String;

            if (ts != null)
            {
                var fnPtrSig = ts.TypeSig as FnPtrSig;
                typeFullName = DnlibExtensions.GetFnPtrFullName(fnPtrSig);
                typeName     = DnlibExtensions.GetFnPtrName(fnPtrSig);
            }
            TypeSig typeSig = null;
            string  name    = type.DefinitionAssembly.IsCorLib() ? PrimitiveTypeName(typeFullName, type.Module, out typeSig) : null;

            if (syntax == ILNameSyntax.ShortTypeName)
            {
                if (name != null)
                {
                    WriteKeyword(writer, name, typeSig.ToTypeDefOrRef());
                }
                else
                {
                    writer.WriteReference(Escape(typeName), type, TextTokenHelper.GetTextTokenType(type));
                }
            }
            else if ((syntax == ILNameSyntax.Signature || syntax == ILNameSyntax.SignatureNoNamedTypeParameters) && name != null)
            {
                WriteKeyword(writer, name, typeSig.ToTypeDefOrRef());
            }
            else
            {
                if (syntax == ILNameSyntax.Signature || syntax == ILNameSyntax.SignatureNoNamedTypeParameters)
                {
                    writer.Write(DnlibExtensions.IsValueType(type) ? "valuetype" : "class", TextTokenType.Keyword);
                    writer.WriteSpace();
                }

                if (type.DeclaringType != null)
                {
                    type.DeclaringType.WriteTo(writer, ILNameSyntax.TypeName, depth);
                    writer.Write('/', TextTokenType.Operator);
                    writer.WriteReference(Escape(typeName), type, TextTokenHelper.GetTextTokenType(type));
                }
                else
                {
                    if (!(type is TypeDef) && type.Scope != null && !(type is TypeSpec))
                    {
                        writer.Write('[', TextTokenType.Operator);
                        writer.Write(Escape(type.Scope.GetScopeName()), TextTokenType.ILModule);
                        writer.Write(']', TextTokenType.Operator);
                    }
                    if (ts != null || MustEscape(typeFullName))
                    {
                        writer.WriteReference(Escape(typeFullName), type, TextTokenHelper.GetTextTokenType(type));
                    }
                    else
                    {
                        WriteNamespace(writer, type.Namespace);
                        if (!string.IsNullOrEmpty(type.Namespace))
                        {
                            writer.Write('.', TextTokenType.Operator);
                        }
                        writer.WriteReference(IdentifierEscaper.Escape(type.Name), type, TextTokenHelper.GetTextTokenType(type));
                    }
                }
            }
        }
Пример #33
0
        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)
                {
                    ulong fileOffset = (ulong)baseOffs + instruction.Offset;
                    writer.WriteReference(string.Format("0x{0:X8}", fileOffset), new AddressReference(options.OwnerModule == null ? null : options.OwnerModule.Location, false, fileOffset, (ulong)instruction.GetSize()), TextTokenType.Comment, false);
                    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 static void WriteOffsetReference(ITextOutput writer, Instruction instruction)
		{
			writer.WriteReference(dnlibExtensions.OffsetToString(instruction.Offset), instruction, true);
		}
        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
            {
                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);
                    }
                }
            }
        }
Пример #36
0
 public static void WriteTo(this XMethodReference method, ITextOutput writer)
 {
     if (method.HasThis)
     {
         writer.Write("instance ");
     }
     method.ReturnType.WriteTo(writer, AstNameSyntax.SignatureNoNamedTypeParameters);
     writer.Write(' ');
     if (method.DeclaringType != null)
     {
         method.DeclaringType.WriteTo(writer, AstNameSyntax.TypeName);
         writer.Write("::");
     }
         writer.WriteReference(Escape(method.Name), method);
     var gim = method as XGenericInstanceMethod;
     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, AstNameSyntax.SignatureNoNamedTypeParameters);
     }
     writer.Write(")");
 }
Пример #37
0
        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));
            }
        }
Пример #38
0
        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(')');
        }
Пример #39
0
		public static void WriteTo(this TypeReference type, ITextOutput writer, bool onlyName = false, bool shortName = false)
		{
			if (type is PinnedType) {
				writer.Write("pinned ");
				((PinnedType)type).ElementType.WriteTo(writer, onlyName, shortName);
			} else if (type is ArrayType) {
				ArrayType at = (ArrayType)type;
				at.ElementType.WriteTo(writer, onlyName, shortName);
				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('!');
				writer.Write(type.Name);
			} else if (type is ByReferenceType) {
				((ByReferenceType)type).ElementType.WriteTo(writer, onlyName, shortName);
				writer.Write('&');
			} else if (type is PointerType) {
				((PointerType)type).ElementType.WriteTo(writer, onlyName, shortName);
				writer.Write('*');
			} else if (type is GenericInstanceType) {
				type.GetElementType().WriteTo(writer, onlyName, shortName);
				writer.Write('<');
				var arguments = ((GenericInstanceType)type).GenericArguments;
				for (int i = 0; i < arguments.Count; i++) {
					if (i > 0)
						writer.Write(", ");
					arguments[i].WriteTo(writer, onlyName, shortName);
				}
				writer.Write('>');
			} else if (type is OptionalModifierType) {
				writer.Write("modopt(");
				((OptionalModifierType)type).ModifierType.WriteTo(writer, true, shortName);
				writer.Write(") ");
				((OptionalModifierType)type).ElementType.WriteTo(writer, onlyName, shortName);
			} else if (type is RequiredModifierType) {
				writer.Write("modreq(");
				((RequiredModifierType)type).ModifierType.WriteTo(writer, true, shortName);
				writer.Write(") ");
				((RequiredModifierType)type).ElementType.WriteTo(writer, onlyName, shortName);
			} else {
				string name = PrimitiveTypeName(type);
				if (name != null) {
					writer.Write(name);
				} else {
					if (!onlyName)
						writer.Write(type.IsValueType ? "valuetype " : "class ");
					
					if (type.DeclaringType != null) {
						type.DeclaringType.WriteTo(writer, true, shortName);
						writer.Write('/');
						writer.WriteReference(Escape(type.Name), type);
					} else {
						if (!type.IsDefinition && type.Scope != null && !shortName && !(type is TypeSpecification))
							writer.Write("[{0}]", Escape(type.Scope.Name));
						writer.WriteReference(shortName ? type.Name : type.FullName, type);
					}
				}
			}
		}
Пример #40
0
		public override void DecompileField(FieldDef field, ITextOutput output, DecompilationOptions options)
		{
			output.WriteReference(IdentifierEscaper.Escape(field.FieldType.GetFullName()), field.FieldType.ToTypeDefOrRef(), TextTokenHelper.GetTextTokenType(field.FieldType));
			output.WriteSpace();
			output.WriteDefinition(IdentifierEscaper.Escape(field.Name), field, TextTokenHelper.GetTextTokenType(field), false);
			var c = field.Constant;
			if (c != null) {
				output.WriteSpace();
				output.Write('=', TextTokenType.Operator);
				output.WriteSpace();
				if (c.Value == null)
					output.Write("null", TextTokenType.Keyword);
				else {
					switch (c.Type) {
					case ElementType.Boolean:
						if (c.Value is bool)
							output.Write((bool)c.Value ? "true" : "false", TextTokenType.Keyword);
						else
							goto default;
						break;

					case ElementType.Char:
						output.Write(string.Format("'{0}'", c.Value), TextTokenType.Char);
						break;

					case ElementType.I1:
					case ElementType.U1:
					case ElementType.I2:
					case ElementType.U2:
					case ElementType.I4:
					case ElementType.U4:
					case ElementType.I8:
					case ElementType.U8:
					case ElementType.R4:
					case ElementType.R8:
					case ElementType.I:
					case ElementType.U:
						output.Write(string.Format("{0}", c.Value), TextTokenType.Number);
						break;

					case ElementType.String:
						output.Write(string.Format("{0}", c.Value), TextTokenType.String);
						break;

					default:
						output.Write(string.Format("{0}", c.Value), TextTokenType.Text);
						break;
					}
				}
			}
		}
Пример #41
0
 public static void WriteOffsetReference(ITextOutput writer, Instruction instruction, MethodDef method, TextTokenType tokenType = TextTokenType.Label)
 {
     var r = instruction == null ? null : method == null ? (object)instruction : new InstructionReference(method, instruction);
     writer.WriteReference(DnlibExtensions.OffsetToString(instruction.GetOffset()), r, tokenType);
 }
Пример #42
0
		public static void WriteTo(this MethodReference method, ITextOutput writer)
		{
			if (method.HasThis)
				writer.Write("instance ");
			method.ReturnType.WriteTo(writer);
			writer.Write(' ');
			if (method.DeclaringType != null) {
				method.DeclaringType.WriteTo(writer, true);
				writer.Write("::");
			}
			writer.WriteReference(method.Name, method);
			writer.Write("(");
			var parameters = method.Parameters;
			for(int i = 0; i < parameters.Count; ++i) {
				if (i > 0) writer.Write(", ");
				parameters[i].ParameterType.WriteTo(writer);
			}
			writer.Write(")");
		}
Пример #43
0
        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) {
                    ulong fileOffset = (ulong)baseOffs + instruction.Offset;
                    writer.WriteReference(string.Format("0x{0:X8}", fileOffset), new AddressReference(options.OwnerModule == null ? null : options.OwnerModule.Location, false, fileOffset, (ulong)instruction.GetSize()), TextTokenType.Comment, false);
                    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);
                }
            }
        }
Пример #44
0
        protected virtual void WriteInstruction(ITextOutput output, MetadataReader metadata, MethodDefinitionHandle methodDefinition, ref BlobReader blob)
        {
            int offset = blob.Offset;

            if (ShowSequencePoints && nextSequencePointIndex < sequencePoints?.Count)
            {
                var sp = sequencePoints[nextSequencePointIndex];
                if (sp.Offset <= offset)
                {
                    output.Write("// sequence point: ");
                    if (sp.Offset != offset)
                    {
                        output.Write("!! at " + DisassemblerHelpers.OffsetToString(sp.Offset) + " !!");
                    }
                    if (sp.IsHidden)
                    {
                        output.WriteLine("hidden");
                    }
                    else
                    {
                        output.WriteLine($"(line {sp.StartLine}, col {sp.StartColumn}) to (line {sp.EndLine}, col {sp.EndColumn}) in {sp.DocumentUrl}");
                    }
                    nextSequencePointIndex++;
                }
            }
            ILOpCode opCode = ILParser.DecodeOpCode(ref blob);

            output.WriteLocalReference(DisassemblerHelpers.OffsetToString(offset), offset, isDefinition: true);
            output.Write(": ");
            if (opCode.IsDefined())
            {
                output.WriteReference(new OpCodeInfo(opCode, opCode.GetDisplayName()));
                switch (opCode.GetOperandType())
                {
                case OperandType.BrTarget:
                case OperandType.ShortBrTarget:
                    output.Write(' ');
                    int targetOffset = ILParser.DecodeBranchTarget(ref blob, opCode);
                    output.WriteLocalReference($"IL_{targetOffset:x4}", targetOffset);
                    break;

                case OperandType.Field:
                case OperandType.Method:
                case OperandType.Sig:
                case OperandType.Type:
                    output.Write(' ');
                    int          metadataToken = blob.ReadInt32();
                    EntityHandle?handle        = MetadataTokenHelpers.TryAsEntityHandle(metadataToken);
                    try {
                        handle?.WriteTo(module, output, genericContext);
                    } catch (BadImageFormatException) {
                        handle = null;
                    }
                    WriteMetadataToken(handle, metadataToken, spaceBefore: true);
                    break;

                case OperandType.Tok:
                    output.Write(' ');
                    metadataToken = blob.ReadInt32();
                    handle        = MetadataTokenHelpers.TryAsEntityHandle(metadataToken);
                    switch (handle?.Kind)
                    {
                    case HandleKind.MemberReference:
                        switch (metadata.GetMemberReference((MemberReferenceHandle)handle).GetKind())
                        {
                        case MemberReferenceKind.Method:
                            output.Write("method ");
                            break;

                        case MemberReferenceKind.Field:
                            output.Write("field ");
                            break;
                        }
                        break;

                    case HandleKind.FieldDefinition:
                        output.Write("field ");
                        break;

                    case HandleKind.MethodDefinition:
                        output.Write("method ");
                        break;
                    }
                    try {
                        handle?.WriteTo(module, output, genericContext);
                    } catch (BadImageFormatException) {
                        handle = null;
                    }
                    WriteMetadataToken(handle, metadataToken, spaceBefore: true);
                    break;

                case OperandType.ShortI:
                    output.Write(' ');
                    DisassemblerHelpers.WriteOperand(output, blob.ReadSByte());
                    break;

                case OperandType.I:
                    output.Write(' ');
                    DisassemblerHelpers.WriteOperand(output, blob.ReadInt32());
                    break;

                case OperandType.I8:
                    output.Write(' ');
                    DisassemblerHelpers.WriteOperand(output, blob.ReadInt64());
                    break;

                case OperandType.ShortR:
                    output.Write(' ');
                    DisassemblerHelpers.WriteOperand(output, blob.ReadSingle());
                    break;

                case OperandType.R:
                    output.Write(' ');
                    DisassemblerHelpers.WriteOperand(output, blob.ReadDouble());
                    break;

                case OperandType.String:
                    metadataToken = blob.ReadInt32();
                    output.Write(' ');
                    UserStringHandle?userString;
                    string           text;
                    try {
                        userString = MetadataTokens.UserStringHandle(metadataToken);
                        text       = metadata.GetUserString(userString.Value);
                    } catch (BadImageFormatException) {
                        userString = null;
                        text       = null;
                    }
                    if (userString != null)
                    {
                        DisassemblerHelpers.WriteOperand(output, text);
                    }
                    WriteMetadataToken(userString, metadataToken, spaceBefore: true);
                    break;

                case OperandType.Switch:
                    int[] targets = ILParser.DecodeSwitchTargets(ref blob);
                    output.Write(" (");
                    for (int i = 0; i < targets.Length; i++)
                    {
                        if (i > 0)
                        {
                            output.Write(", ");
                        }
                        output.WriteLocalReference($"IL_{targets[i]:x4}", targets[i]);
                    }
                    output.Write(")");
                    break;

                case OperandType.Variable:
                    output.Write(' ');
                    int index = blob.ReadUInt16();
                    if (opCode == ILOpCode.Ldloc || opCode == ILOpCode.Ldloca || opCode == ILOpCode.Stloc)
                    {
                        DisassemblerHelpers.WriteVariableReference(output, metadata, methodDefinition, index);
                    }
                    else
                    {
                        DisassemblerHelpers.WriteParameterReference(output, metadata, methodDefinition, index);
                    }
                    break;

                case OperandType.ShortVariable:
                    output.Write(' ');
                    index = blob.ReadByte();
                    if (opCode == ILOpCode.Ldloc_s || opCode == ILOpCode.Ldloca_s || opCode == ILOpCode.Stloc_s)
                    {
                        DisassemblerHelpers.WriteVariableReference(output, metadata, methodDefinition, index);
                    }
                    else
                    {
                        DisassemblerHelpers.WriteParameterReference(output, metadata, methodDefinition, index);
                    }
                    break;
                }
            }
            else
            {
                ushort opCodeValue = (ushort)opCode;
                if (opCodeValue > 0xFF)
                {
                    // split 16-bit value into two emitbyte directives
                    output.WriteLine($".emitbyte 0x{(byte)(opCodeValue >> 8):x}");
                    // add label
                    output.WriteLocalReference(DisassemblerHelpers.OffsetToString(offset + 1), offset + 1, isDefinition: true);
                    output.Write(": ");
                    output.Write($".emitbyte 0x{(byte)(opCodeValue & 0xFF):x}");
                }
                else
                {
                    output.Write($".emitbyte 0x{(byte)opCodeValue:x}");
                }
            }
            output.WriteLine();
        }
Пример #45
0
 internal static void WriteKeyword(ITextOutput writer, string name, ITypeDefOrRef tdr)
 {
     var parts = name.Split(' ');
     for (int i = 0; i < parts.Length; i++) {
         if (i > 0)
             writer.WriteSpace();
         if (tdr != null)
             writer.WriteReference(parts[i], tdr, TextTokenType.Keyword);
         else
             writer.Write(parts[i], TextTokenType.Keyword);
     }
 }
Пример #46
0
        public override void Decompile(FieldDef field, ITextOutput output, DecompilationContext ctx)
        {
            output.WriteReference(IdentifierEscaper.Escape(field.FieldType.GetFullName()), field.FieldType.ToTypeDefOrRef(), TextTokenKindUtils.GetTextTokenType(field.FieldType));
            output.WriteSpace();
            output.WriteDefinition(IdentifierEscaper.Escape(field.Name), field, TextTokenKindUtils.GetTextTokenType(field), false);
            var c = field.Constant;

            if (c != null)
            {
                output.WriteSpace();
                output.Write("=", TextTokenKind.Operator);
                output.WriteSpace();
                if (c.Value == null)
                {
                    output.Write("null", TextTokenKind.Keyword);
                }
                else
                {
                    switch (c.Type)
                    {
                    case ElementType.Boolean:
                        if (c.Value is bool)
                        {
                            output.Write((bool)c.Value ? "true" : "false", TextTokenKind.Keyword);
                        }
                        else
                        {
                            goto default;
                        }
                        break;

                    case ElementType.Char:
                        output.Write(string.Format("'{0}'", c.Value), TextTokenKind.Char);
                        break;

                    case ElementType.I1:
                    case ElementType.U1:
                    case ElementType.I2:
                    case ElementType.U2:
                    case ElementType.I4:
                    case ElementType.U4:
                    case ElementType.I8:
                    case ElementType.U8:
                    case ElementType.R4:
                    case ElementType.R8:
                    case ElementType.I:
                    case ElementType.U:
                        output.Write(string.Format("{0}", c.Value), TextTokenKind.Number);
                        break;

                    case ElementType.String:
                        output.Write(string.Format("{0}", c.Value), TextTokenKind.String);
                        break;

                    default:
                        output.Write(string.Format("{0}", c.Value), TextTokenKind.Text);
                        break;
                    }
                }
            }
        }
		static void WriteTo(this IField field, ITextOutput writer)
		{
			var signature = field.FieldSig;
			signature.Type.WriteTo(writer, ILNameSyntax.SignatureNoNamedTypeParameters);
			writer.Write(' ');
			field.DeclaringType.WriteTo(writer, ILNameSyntax.TypeName);
			writer.Write("::");
			writer.WriteReference(Escape(field.Name), field);
		}
Пример #48
0
		public static void WriteOperand(ITextOutput writer, object operand)
		{
			if (operand == null)
				throw new ArgumentNullException("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;
			}
			
			MethodReference methodRef = operand as MethodReference;
			if (methodRef != null) {
				methodRef.WriteTo(writer);
				return;
			}
			
			TypeReference typeRef = operand as TypeReference;
			if (typeRef != null) {
				typeRef.WriteTo(writer);
				return;
			}
			
			FieldReference fieldRef = operand as FieldReference;
			if (fieldRef != null) {
				fieldRef.WriteTo(writer);
				return;
			}
			
			string s = operand as string;
			if (s != null) {
				writer.Write("\"" + s.Replace("\\", "\\\\").Replace("\"", "\\\"") + "\"");
				return;
			}
			
			s = ToInvariantCultureString(operand);
			writer.Write(s);
		}
		public static void WriteOperand(ITextOutput writer, object operand)
		{
			if (operand == null)
				throw new ArgumentNullException("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;
			}
			
			Local local = operand as Local;
			if (local != null) {
				if (string.IsNullOrEmpty(local.Name))
					writer.WriteReference("[" + local.Index.ToString() + "]", local, true);
				else
					writer.WriteReference(Escape(local.Name), local, true);
				return;
			}
			
			Parameter param = operand as Parameter;
			if (param != null) {
				if (string.IsNullOrEmpty(param.Name))
					writer.WriteReference("[" + param.Index.ToString() + "]", param, true);
				else
					writer.WriteReference(Escape(param.Name), param, true);
				return;
			}
			
			IMethod methodRef = operand as IMethod;
			if (methodRef != null && dnlibExtensions.IsMethod(methodRef)) {
				methodRef.WriteTo(writer);
				writer.WriteComment(" // 0x" + methodRef.MDToken.Raw.ToString("x8"));
				return;
			}
			
			ITypeDefOrRef typeRef = operand as ITypeDefOrRef;
			if (typeRef != null) {
				typeRef.WriteTo(writer, ILNameSyntax.TypeName);
				writer.WriteComment(" // 0x" + typeRef.MDToken.Raw.ToString("x8"));
				return;
			}

			IField fieldRef = operand as IField;
			if (fieldRef != null && dnlibExtensions.IsField(fieldRef)) {
				fieldRef.WriteTo(writer);
				writer.WriteComment(" // 0x" + fieldRef.MDToken.Raw.ToString("x8"));
				return;
			}
			
			string s = operand as string;
			if (s != null) {
				writer.WriteLiteral("\"" + NRefactory.CSharp.CSharpOutputVisitor.ConvertString(s) + "\"");
			} else if (operand is char) {
				writer.WriteLiteral(((int)(char)operand).ToString());
			} else if (operand is float) {
				float val = (float)operand;
				if (val == 0) {
					if (1 / val == float.NegativeInfinity) {
						// negative zero is a special case
						writer.WriteLiteral("-");
					}
					writer.WriteLiteral("0.0");
				} else if (float.IsInfinity(val) || float.IsNaN(val)) {
					byte[] data = BitConverter.GetBytes(val);
					writer.Write('(');
					for (int i = 0; i < data.Length; i++) {
						if (i > 0)
							writer.WriteLiteral(" ");
						writer.WriteLiteral(data[i].ToString("X2"));
					}
					writer.Write(')');
				} else {
					writer.WriteLiteral(val.ToString("R", System.Globalization.CultureInfo.InvariantCulture));
				}
			} else if (operand is double) {
				double val = (double)operand;
				if (val == 0) {
					if (1 / val == double.NegativeInfinity) {
						// negative zero is a special case
						writer.WriteLiteral("-");
					}
					writer.WriteLiteral("0.0");
				} else if (double.IsInfinity(val) || double.IsNaN(val)) {
					byte[] data = BitConverter.GetBytes(val);
					writer.Write('(');
					for (int i = 0; i < data.Length; i++) {
						if (i > 0)
							writer.WriteLiteral(" ");
						writer.WriteLiteral(data[i].ToString("X2"));
					}
					writer.Write(')');
				} else {
					writer.WriteLiteral(val.ToString("R", System.Globalization.CultureInfo.InvariantCulture));
				}
			} else if (operand is bool) {
				writer.WriteLiteral((bool)operand ? "true" : "false");
			} else {
				s = ToInvariantCultureString(operand);
				writer.WriteLiteral(s);
			}
		}
Пример #50
0
        public static void WriteTo(this TypeReference type, ITextOutput writer, bool onlyName = false, bool shortName = false)
        {
            if (type is PinnedType)
            {
                writer.Write("pinned ");
                ((PinnedType)type).ElementType.WriteTo(writer, onlyName, shortName);
            }
            else if (type is ArrayType)
            {
                ArrayType at = (ArrayType)type;
                at.ElementType.WriteTo(writer, onlyName, shortName);
                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('!');
                }
                writer.Write(type.Name);
            }
            else if (type is ByReferenceType)
            {
                ((ByReferenceType)type).ElementType.WriteTo(writer, onlyName, shortName);
                writer.Write('&');
            }
            else if (type is PointerType)
            {
                ((PointerType)type).ElementType.WriteTo(writer, onlyName, shortName);
                writer.Write('*');
            }
            else if (type is GenericInstanceType)
            {
                type.GetElementType().WriteTo(writer, onlyName, shortName);
                writer.Write('<');
                var arguments = ((GenericInstanceType)type).GenericArguments;
                for (int i = 0; i < arguments.Count; i++)
                {
                    if (i > 0)
                    {
                        writer.Write(", ");
                    }
                    arguments[i].WriteTo(writer, onlyName, shortName);
                }
                writer.Write('>');
            }
            else if (type is OptionalModifierType)
            {
                writer.Write("modopt(");
                ((OptionalModifierType)type).ModifierType.WriteTo(writer, true, shortName);
                writer.Write(") ");
                ((OptionalModifierType)type).ElementType.WriteTo(writer, onlyName, shortName);
            }
            else if (type is RequiredModifierType)
            {
                writer.Write("modreq(");
                ((RequiredModifierType)type).ModifierType.WriteTo(writer, true, shortName);
                writer.Write(") ");
                ((RequiredModifierType)type).ElementType.WriteTo(writer, onlyName, shortName);
            }
            else
            {
                string name = PrimitiveTypeName(type);
                if (name != null)
                {
                    writer.Write(name);
                }
                else
                {
                    if (!onlyName)
                    {
                        writer.Write(type.IsValueType ? "valuetype " : "class ");
                    }

                    if (type.DeclaringType != null)
                    {
                        type.DeclaringType.WriteTo(writer, true, shortName);
                        writer.Write('/');
                        writer.WriteReference(Escape(type.Name), type);
                    }
                    else
                    {
                        if (!type.IsDefinition && type.Scope != null && !shortName && !(type is TypeSpecification))
                        {
                            writer.Write("[{0}]", Escape(type.Scope.Name));
                        }
                        writer.WriteReference(shortName ? type.Name : type.FullName, type);
                    }
                }
            }
        }
Пример #51
0
        public static void WriteOperand(ITextOutput writer, object operand)
        {
            if (operand == null)
            {
                throw new ArgumentNullException("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;
            }

            MethodReference methodRef = operand as MethodReference;

            if (methodRef != null)
            {
                methodRef.WriteTo(writer);
                return;
            }

            TypeReference typeRef = operand as TypeReference;

            if (typeRef != null)
            {
                typeRef.WriteTo(writer);
                return;
            }

            FieldReference fieldRef = operand as FieldReference;

            if (fieldRef != null)
            {
                fieldRef.WriteTo(writer);
                return;
            }

            string s = operand as string;

            if (s != null)
            {
                writer.Write("\"" + s.Replace("\\", "\\\\").Replace("\"", "\\\"") + "\"");
                return;
            }

            s = ToInvariantCultureString(operand);
            writer.Write(s);
        }
Пример #52
0
		public static void WriteTo(this MethodReference method, ITextOutput writer)
		{
			if (method.ExplicitThis) {
				writer.Write("instance explicit ");
			}
			else if (method.HasThis) {
				writer.Write("instance ");
			}
			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(")");
		}
        public static void WriteOperand(ITextOutput writer, object operand)
        {
            if (operand == null)
            {
                throw new ArgumentNullException("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)
            {
                if (string.IsNullOrEmpty(variableRef.Name))
                {
                    writer.WriteReference(variableRef.Index.ToString(), variableRef);
                }
                else
                {
                    writer.WriteReference(Escape(variableRef.Name), 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)
            {
                writer.Write("\"" + NRefactory.CSharp.TextWriterTokenWriter.ConvertString(s) + "\"");
            }
            else if (operand is char)
            {
                writer.Write(((int)(char)operand).ToString());
            }
            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('-');
                    }
                    writer.Write("0.0");
                }
                else if (float.IsInfinity(val) || float.IsNaN(val))
                {
                    byte[] data = BitConverter.GetBytes(val);
                    writer.Write('(');
                    for (int i = 0; i < data.Length; i++)
                    {
                        if (i > 0)
                        {
                            writer.Write(' ');
                        }
                        writer.Write(data[i].ToString("X2"));
                    }
                    writer.Write(')');
                }
                else
                {
                    writer.Write(val.ToString("R", System.Globalization.CultureInfo.InvariantCulture));
                }
            }
            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('-');
                    }
                    writer.Write("0.0");
                }
                else if (double.IsInfinity(val) || double.IsNaN(val))
                {
                    byte[] data = BitConverter.GetBytes(val);
                    writer.Write('(');
                    for (int i = 0; i < data.Length; i++)
                    {
                        if (i > 0)
                        {
                            writer.Write(' ');
                        }
                        writer.Write(data[i].ToString("X2"));
                    }
                    writer.Write(')');
                }
                else
                {
                    writer.Write(val.ToString("R", System.Globalization.CultureInfo.InvariantCulture));
                }
            }
            else if (operand is bool)
            {
                writer.Write((bool)operand ? "true" : "false");
            }
            else
            {
                s = ToInvariantCultureString(operand);
                writer.Write(s);
            }
        }
Пример #54
0
		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 {
				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);
					}
				}
			}
		}
Пример #55
0
 static void WriteTo(this XFieldReference field, ITextOutput writer)
 {
     field.FieldType.WriteTo(writer, AstNameSyntax.SignatureNoNamedTypeParameters);
     writer.Write(' ');
     field.DeclaringType.WriteTo(writer, AstNameSyntax.TypeName);
     writer.Write("::");
     writer.WriteReference(Escape(field.Name), field);
 }
Пример #56
0
        public static void WriteOffsetReference(ITextOutput writer, Instruction instruction, MethodDef method, TextTokenType tokenType = TextTokenType.Label)
        {
            var r = instruction == null ? null : method == null ? (object)instruction : new InstructionReference(method, instruction);

            writer.WriteReference(DnlibExtensions.OffsetToString(instruction.GetOffset()), r, tokenType);
        }
Пример #57
0
        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)
            {
                if (!WholeProjectDecompiler.CanUseSdkStyleProjectFormat(module))
                {
                    options.DecompilerSettings.UseSdkStyleProjectFormat = false;
                }
                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
                IAssemblyResolver assemblyResolver = assembly.GetAssemblyResolver(loadOnDemand: options.FullDecompilation);
                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 (module.Reader.ReadDebugDirectory().Any(d => d.Type == DebugDirectoryEntryType.Reproducible))
                {
                    output.WriteLine("// This assembly was compiled using the /deterministic option.");
                }
                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);
            }
        }
Пример #58
0
        public static void WriteTo(this XTypeReference type, ITextOutput writer, AstNameSyntax syntax = AstNameSyntax.Signature)
        {
            var syntaxForElementTypes = syntax == AstNameSyntax.ShortTypeName ? AstNameSyntax.ShortTypeName
                                      : syntax == AstNameSyntax.SignatureNoNamedTypeParameters ? syntax 
                                      : AstNameSyntax.Signature;
            if (type is XArrayType)
            {
                var at = (XArrayType)type;
                at.ElementType.WriteTo(writer, syntaxForElementTypes);
                writer.Write('[');
                writer.Write(string.Join(", ", at.Dimensions));
                writer.Write(']');
            }
            else if (type is XGenericParameter)
            {
                writer.Write('!');
                if (((XGenericParameter)type).Owner is XMethodReference)
                    writer.Write('!');
                if (string.IsNullOrEmpty(type.Name) || type.Name[0] == '!' || syntax == AstNameSyntax.SignatureNoNamedTypeParameters)
                    writer.Write(((XGenericParameter)type).Position.ToString());
                else
                    writer.Write(Escape(type.Name));
            }
            else if (type is XByReferenceType)
            {
                ((XByReferenceType)type).ElementType.WriteTo(writer, syntaxForElementTypes);
                writer.Write('&');
            }
            else if (type is XGenericInstanceType)
            {
                type.GetElementType().WriteTo(writer, syntaxForElementTypes);
                writer.Write('<');
                var arguments = ((XGenericInstanceType)type).GenericArguments;
                for (int i = 0; i < arguments.Count; i++)
                {
                    if (i > 0)
                        writer.Write(", ");
                    arguments[i].WriteTo(writer, syntaxForElementTypes);
                }
                writer.Write('>');
            }
            else
            {
                string name = PrimitiveTypeName(type.FullName);
                if (syntax == AstNameSyntax.ShortTypeName)
                {
                    if (name != null)
                        writer.Write(name);
                    else
                        writer.WriteReference(Escape(type.Name), type);
                }
                else if ((syntax == AstNameSyntax.Signature || syntax == AstNameSyntax.SignatureNoNamedTypeParameters) && name != null)
                {
                    writer.Write(name);
                }
                else
                {
                    if (syntax == AstNameSyntax.Signature || syntax == AstNameSyntax.SignatureNoNamedTypeParameters)
                        writer.Write(type.IsValueType ? "valuetype " : "class ");

                    var typeAsMember = type as IXMemberReference;
                    if ((typeAsMember != null) && (typeAsMember.DeclaringType != null))
                    {
                        typeAsMember.DeclaringType.WriteTo(writer, AstNameSyntax.TypeName);
                        writer.Write('/');
                        writer.WriteReference(Escape(type.Name), type);
                    }
                    else
                    {
                        writer.WriteReference(Escape(type.FullName), type);
                    }
                }
            }
        }
Пример #59
0
		public override void DecompileType(TypeDef type, ITextOutput output, DecompilationOptions options)
		{
			WriteCommentLine(output, string.Format("Type: {0}", type.FullName));
			if (type.BaseType != null) {
				WriteComment(output, string.Format("Base type: "));
				output.WriteReference(IdentifierEscaper.Escape(type.BaseType.FullName), type.BaseType, TextTokenType.Comment);
				output.WriteLine();
			}
			foreach (var nested in type.NestedTypes) {
				DecompileType(nested, output, options);
				output.WriteLine();
			}

			foreach (var field in type.Fields) {
				DecompileField(field, output, options);
				output.WriteLine();
			}

			foreach (var property in type.Properties) {
				DecompileProperty(property, output, options);
				output.WriteLine();
			}

			foreach (var @event in type.Events) {
				DecompileEvent(@event, output, options);
				output.WriteLine();
			}

			foreach (var method in type.Methods) {
				DecompileMethod(method, output, options);
				output.WriteLine();
			}
		}
Пример #60
0
		public static void WriteOffsetReference(ITextOutput writer, ILInstruction instruction)
		{
			writer.WriteReference(/*CecilExtensions.OffsetToString*/(instruction.Offset.ToString()), instruction);
		}