Skip to content

Commit

Permalink
#2516: Add ILSpy.AddIn.slnf, ILSpy.Wpf.slnf and ILSpy.XPlat.slnf; rep…
Browse files Browse the repository at this point in the history
…laces Frontends.sln
  • Loading branch information
siegfriedpammer committed Oct 15, 2021
1 parent a08ef0e commit d2b3abb
Show file tree
Hide file tree
Showing 14 changed files with 221 additions and 119 deletions.
44 changes: 0 additions & 44 deletions Frontends.sln

This file was deleted.

132 changes: 88 additions & 44 deletions ICSharpCode.Decompiler.Console/IlspyCmdProgram.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,19 @@
using System.IO.Compression;
using System.IO.MemoryMappedFiles;
using System.Linq;
using McMaster.Extensions.CommandLineUtils;
using ICSharpCode.Decompiler.CSharp;
using ICSharpCode.Decompiler.TypeSystem;
using ICSharpCode.Decompiler.Metadata;
using ICSharpCode.Decompiler.Disassembler;
using System.Threading;
using System.Reflection.Metadata;
using System.Reflection.PortableExecutable;
using System.Threading;

using ICSharpCode.Decompiler.CSharp;
using ICSharpCode.Decompiler.CSharp.ProjectDecompiler;
using ICSharpCode.Decompiler.DebugInfo;
using ICSharpCode.Decompiler.Disassembler;
using ICSharpCode.Decompiler.Metadata;
using ICSharpCode.Decompiler.PdbProvider;
using ICSharpCode.Decompiler.CSharp.ProjectDecompiler;
using ICSharpCode.Decompiler.TypeSystem;

using McMaster.Extensions.CommandLineUtils;
// ReSharper disable All

namespace ICSharpCode.Decompiler.Console
Expand Down Expand Up @@ -86,56 +88,80 @@ private int OnExecute(CommandLineApplication app)
TextWriter output = System.Console.Out;
bool outputDirectorySpecified = !string.IsNullOrEmpty(OutputDirectory);

try {
if (CreateCompilableProjectFlag) {
try
{
if (CreateCompilableProjectFlag)
{
return DecompileAsProject(InputAssemblyName, OutputDirectory);
} else if (EntityTypes.Any()) {
}
else if (EntityTypes.Any())
{
var values = EntityTypes.SelectMany(v => v.Split(',', ';')).ToArray();
HashSet<TypeKind> kinds = TypesParser.ParseSelection(values);
if (outputDirectorySpecified) {
if (outputDirectorySpecified)
{
string outputName = Path.GetFileNameWithoutExtension(InputAssemblyName);
output = File.CreateText(Path.Combine(OutputDirectory, outputName) + ".list.txt");
}

return ListContent(InputAssemblyName, output, kinds);
} else if (ShowILCodeFlag || ShowILSequencePointsFlag) {
if (outputDirectorySpecified) {
}
else if (ShowILCodeFlag || ShowILSequencePointsFlag)
{
if (outputDirectorySpecified)
{
string outputName = Path.GetFileNameWithoutExtension(InputAssemblyName);
output = File.CreateText(Path.Combine(OutputDirectory, outputName) + ".il");
}

return ShowIL(InputAssemblyName, output);
} else if (CreateDebugInfoFlag) {
}
else if (CreateDebugInfoFlag)
{
string pdbFileName = null;
if (outputDirectorySpecified) {
if (outputDirectorySpecified)
{
string outputName = Path.GetFileNameWithoutExtension(InputAssemblyName);
pdbFileName = Path.Combine(OutputDirectory, outputName) + ".pdb";
} else {
}
else
{
pdbFileName = Path.ChangeExtension(InputAssemblyName, ".pdb");
}

return GeneratePdbForAssembly(InputAssemblyName, pdbFileName, app);
} else if (ShowVersion) {
}
else if (ShowVersion)
{
string vInfo = "ilspycmd: " + typeof(ILSpyCmdProgram).Assembly.GetName().Version.ToString() +
Environment.NewLine
+ "ICSharpCode.Decompiler: " +
typeof(FullTypeName).Assembly.GetName().Version.ToString();
Environment.NewLine
+ "ICSharpCode.Decompiler: " +
typeof(FullTypeName).Assembly.GetName().Version.ToString();
output.WriteLine(vInfo);
} else if (DumpPackageFlag) {
}
else if (DumpPackageFlag)
{
return DumpPackageAssemblies(InputAssemblyName, OutputDirectory, app);
} else {
if (outputDirectorySpecified) {
}
else
{
if (outputDirectorySpecified)
{
string outputName = Path.GetFileNameWithoutExtension(InputAssemblyName);
output = File.CreateText(Path.Combine(OutputDirectory,
(string.IsNullOrEmpty(TypeName) ? outputName : TypeName) + ".decompiled.cs"));
}

return Decompile(InputAssemblyName, output, TypeName);
}
} catch (Exception ex) {
}
catch (Exception ex)
{
app.Error.WriteLine(ex.ToString());
return ProgramExitCodes.EX_SOFTWARE;
} finally {
}
finally
{
output.Close();
}

Expand All @@ -156,7 +182,8 @@ CSharpDecompiler GetDecompiler(string assemblyFileName)
{
var module = new PEFile(assemblyFileName);
var resolver = new UniversalAssemblyResolver(assemblyFileName, false, module.Reader.DetectTargetFrameworkId());
foreach (var path in ReferencePaths) {
foreach (var path in ReferencePaths)
{
resolver.AddSearchDirectory(path);
}
return new CSharpDecompiler(assemblyFileName, resolver, GetSettings(module)) {
Expand All @@ -168,7 +195,8 @@ int ListContent(string assemblyFileName, TextWriter output, ISet<TypeKind> kinds
{
CSharpDecompiler decompiler = GetDecompiler(assemblyFileName);

foreach (var type in decompiler.TypeSystem.MainModule.TypeDefinitions) {
foreach (var type in decompiler.TypeSystem.MainModule.TypeDefinitions)
{
if (!kinds.Contains(type.Kind))
continue;
output.WriteLine($"{type.Kind} {type.FullName}");
Expand All @@ -180,8 +208,7 @@ int ShowIL(string assemblyFileName, TextWriter output)
{
var module = new PEFile(assemblyFileName);
output.WriteLine($"// IL code: {module.Name}");
var disassembler = new ReflectionDisassembler(new PlainTextOutput(output), CancellationToken.None)
{
var disassembler = new ReflectionDisassembler(new PlainTextOutput(output), CancellationToken.None) {
DebugInfo = TryLoadPDB(module),
ShowSequencePoints = ShowILSequencePointsFlag,
};
Expand All @@ -193,7 +220,8 @@ int DecompileAsProject(string assemblyFileName, string outputDirectory)
{
var module = new PEFile(assemblyFileName);
var resolver = new UniversalAssemblyResolver(assemblyFileName, false, module.Reader.DetectTargetFrameworkId());
foreach (var path in ReferencePaths) {
foreach (var path in ReferencePaths)
{
resolver.AddSearchDirectory(path);
}
var decompiler = new WholeProjectDecompiler(GetSettings(module), resolver, resolver, TryLoadPDB(module));
Expand All @@ -205,9 +233,12 @@ int Decompile(string assemblyFileName, TextWriter output, string typeName = null
{
CSharpDecompiler decompiler = GetDecompiler(assemblyFileName);

if (typeName == null) {
if (typeName == null)
{
output.Write(decompiler.DecompileWholeModuleAsString());
} else {
}
else
{
var name = new FullTypeName(typeName);
output.Write(decompiler.DecompileTypeAsString(name));
}
Expand All @@ -221,12 +252,14 @@ int GeneratePdbForAssembly(string assemblyFileName, string pdbFileName, CommandL
PEStreamOptions.PrefetchEntireImage,
metadataOptions: MetadataReaderOptions.None);

if (!PortablePdbWriter.HasCodeViewDebugDirectoryEntry(module)) {
if (!PortablePdbWriter.HasCodeViewDebugDirectoryEntry(module))
{
app.Error.WriteLine($"Cannot create PDB file for {assemblyFileName}, because it does not contain a PE Debug Directory Entry of type 'CodeView'.");
return ProgramExitCodes.EX_DATAERR;
}

using (FileStream stream = new FileStream(pdbFileName, FileMode.OpenOrCreate, FileAccess.Write)) {
using (FileStream stream = new FileStream(pdbFileName, FileMode.OpenOrCreate, FileAccess.Write))
{
var decompiler = GetDecompiler(assemblyFileName);
PortablePdbWriter.WritePdb(module, decompiler, GetSettings(module), stream);
}
Expand All @@ -236,27 +269,36 @@ int GeneratePdbForAssembly(string assemblyFileName, string pdbFileName, CommandL

int DumpPackageAssemblies(string packageFileName, string outputDirectory, CommandLineApplication app)
{
using (var memoryMappedPackage = MemoryMappedFile.CreateFromFile(packageFileName, FileMode.Open, null, 0, MemoryMappedFileAccess.Read)) {
using (var packageView = memoryMappedPackage.CreateViewAccessor(0, 0, MemoryMappedFileAccess.Read)) {
if (!SingleFileBundle.IsBundle(packageView, out long bundleHeaderOffset)) {
using (var memoryMappedPackage = MemoryMappedFile.CreateFromFile(packageFileName, FileMode.Open, null, 0, MemoryMappedFileAccess.Read))
{
using (var packageView = memoryMappedPackage.CreateViewAccessor(0, 0, MemoryMappedFileAccess.Read))
{
if (!SingleFileBundle.IsBundle(packageView, out long bundleHeaderOffset))
{
app.Error.WriteLine($"Cannot dump assembiles for {packageFileName}, because it is not a single file bundle.");
return ProgramExitCodes.EX_DATAERR;
}

var manifest = SingleFileBundle.ReadManifest(packageView, bundleHeaderOffset);
foreach (var entry in manifest.Entries) {
foreach (var entry in manifest.Entries)
{
Stream contents;

if (entry.CompressedSize == 0) {
if (entry.CompressedSize == 0)
{
contents = new UnmanagedMemoryStream(packageView.SafeMemoryMappedViewHandle, entry.Offset, entry.Size);
} else {
}
else
{
Stream compressedStream = new UnmanagedMemoryStream(packageView.SafeMemoryMappedViewHandle, entry.Offset, entry.CompressedSize);
Stream decompressedStream = new MemoryStream((int)entry.Size);
using (var deflateStream = new DeflateStream(compressedStream, CompressionMode.Decompress)) {
using (var deflateStream = new DeflateStream(compressedStream, CompressionMode.Decompress))
{
deflateStream.CopyTo(decompressedStream);
}

if (decompressedStream.Length != entry.Size) {
if (decompressedStream.Length != entry.Size)
{
app.Error.WriteLine($"Corrupted single-file entry '${entry.RelativePath}'. Declared decompressed size '${entry.Size}' is not the same as actual decompressed size '${decompressedStream.Length}'.");
return ProgramExitCodes.EX_DATAERR;
}
Expand All @@ -265,7 +307,8 @@ int DumpPackageAssemblies(string packageFileName, string outputDirectory, Comman
contents = decompressedStream;
}

using (var fileStream = File.Create(Path.Combine(outputDirectory, entry.RelativePath))) {
using (var fileStream = File.Create(Path.Combine(outputDirectory, entry.RelativePath)))
{
contents.CopyTo(fileStream);
}
}
Expand All @@ -277,7 +320,8 @@ int DumpPackageAssemblies(string packageFileName, string outputDirectory, Comman

IDebugInfoProvider TryLoadPDB(PEFile module)
{
if (InputPDBFile.IsSet) {
if (InputPDBFile.IsSet)
{
if (InputPDBFile.Value == null)
return DebugInfoUtils.LoadSymbols(module);
return DebugInfoUtils.FromFile(module, InputPDBFile.Value);
Expand Down
17 changes: 12 additions & 5 deletions ICSharpCode.Decompiler.Console/TypesParser.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
using System;
using System.Collections.Generic;
using System.Linq;

using ICSharpCode.Decompiler.TypeSystem;

namespace ICSharpCode.Decompiler.Console
Expand All @@ -11,9 +12,12 @@ public static HashSet<TypeKind> ParseSelection(string[] values)
{
var possibleValues = new Dictionary<string, TypeKind>(StringComparer.OrdinalIgnoreCase) { ["class"] = TypeKind.Class, ["struct"] = TypeKind.Struct, ["interface"] = TypeKind.Interface, ["enum"] = TypeKind.Enum, ["delegate"] = TypeKind.Delegate };
HashSet<TypeKind> kinds = new HashSet<TypeKind>();
if (values.Length == 1 && !possibleValues.Keys.Any(v => values[0].StartsWith(v, StringComparison.OrdinalIgnoreCase))) {
foreach (char ch in values[0]) {
switch (ch) {
if (values.Length == 1 && !possibleValues.Keys.Any(v => values[0].StartsWith(v, StringComparison.OrdinalIgnoreCase)))
{
foreach (char ch in values[0])
{
switch (ch)
{
case 'c':
kinds.Add(TypeKind.Class);
break;
Expand All @@ -31,8 +35,11 @@ public static HashSet<TypeKind> ParseSelection(string[] values)
break;
}
}
} else {
foreach (var value in values) {
}
else
{
foreach (var value in values)
{
string v = value;
while (v.Length > 0 && !possibleValues.ContainsKey(v))
v = v.Remove(v.Length - 1);
Expand Down
6 changes: 4 additions & 2 deletions ICSharpCode.Decompiler.Console/ValidationAttributes.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,10 @@ public ProjectOptionRequiresOutputDirectoryValidationAttribute()

protected override ValidationResult IsValid(object value, ValidationContext context)
{
if (value is ILSpyCmdProgram obj) {
if (obj.CreateCompilableProjectFlag && string.IsNullOrEmpty(obj.OutputDirectory)) {
if (value is ILSpyCmdProgram obj)
{
if (obj.CreateCompilableProjectFlag && string.IsNullOrEmpty(obj.OutputDirectory))
{
return new ValidationResult("--project cannot be used unless --outputdir is also specified");
}
}
Expand Down
Loading

0 comments on commit d2b3abb

Please sign in to comment.