From a0f52e118512e38112e045464801e702ffe0ba26 Mon Sep 17 00:00:00 2001 From: Siegfried Pammer Date: Fri, 1 Jul 2016 16:36:50 +0900 Subject: [PATCH] Add test and fix for conv.i/conv.u casts --- .../CSharp/TranslatedExpression.cs | 6 +++ .../Tests/ICSharpCode.Decompiler.Tests.csproj | 2 + .../Tests/TestCases/ConvTest.il | 44 +++++++++++++++++++ ICSharpCode.Decompiler/Tests/TestRunner.cs | 11 ++++- 4 files changed, 61 insertions(+), 2 deletions(-) create mode 100644 ICSharpCode.Decompiler/Tests/TestCases/ConvTest.il diff --git a/ICSharpCode.Decompiler/CSharp/TranslatedExpression.cs b/ICSharpCode.Decompiler/CSharp/TranslatedExpression.cs index 6db8f0289..0d2ff9af3 100644 --- a/ICSharpCode.Decompiler/CSharp/TranslatedExpression.cs +++ b/ICSharpCode.Decompiler/CSharp/TranslatedExpression.cs @@ -167,6 +167,12 @@ namespace ICSharpCode.Decompiler.CSharp .WithRR(new ResolveResult(new PointerType(expressionBuilder.compilation.FindType(KnownTypeCode.Void)))) .ConvertTo(targetType, expressionBuilder); } + if (targetType.IsKnownType(KnownTypeCode.IntPtr) || targetType.IsKnownType(KnownTypeCode.UIntPtr)) { + return Expression.CastTo(expressionBuilder.ConvertType(new PointerType(expressionBuilder.compilation.FindType(KnownTypeCode.Void)))) + .CastTo(expressionBuilder.ConvertType(targetType)) + .WithoutILInstruction() + .WithRR(expressionBuilder.resolver.WithCheckForOverflow(checkForOverflow).ResolveCast(targetType, ResolveResult)); + } if (type.Kind == TypeKind.ByReference && targetType.Kind == TypeKind.Pointer && Expression is DirectionExpression) { // convert from reference to pointer Expression arg = ((DirectionExpression)Expression).Expression.Detach(); diff --git a/ICSharpCode.Decompiler/Tests/ICSharpCode.Decompiler.Tests.csproj b/ICSharpCode.Decompiler/Tests/ICSharpCode.Decompiler.Tests.csproj index 20c8ff590..eaa6c80ed 100644 --- a/ICSharpCode.Decompiler/Tests/ICSharpCode.Decompiler.Tests.csproj +++ b/ICSharpCode.Decompiler/Tests/ICSharpCode.Decompiler.Tests.csproj @@ -89,6 +89,8 @@ + + diff --git a/ICSharpCode.Decompiler/Tests/TestCases/ConvTest.il b/ICSharpCode.Decompiler/Tests/TestCases/ConvTest.il new file mode 100644 index 000000000..f8c867cba --- /dev/null +++ b/ICSharpCode.Decompiler/Tests/TestCases/ConvTest.il @@ -0,0 +1,44 @@ +.assembly extern mscorlib +{ + .publickeytoken = ( + b7 7a 5c 56 19 34 e0 89 + ) + .ver 4:0:0:0 +} + +.assembly 'ConvTest' +{ + .ver 0:0:0:0 +} + +.module ConvTest.exe +// MVID: {987E1A15-519A-400C-B879-759CFB7F990B} +.corflags 0x00000001 // ILOnly + +.class private auto ansi abstract sealed beforefieldinit Program + extends [mscorlib]System.Object +{ + .method public hidebysig static void Print (native int) cil managed { + ldarg.0 + box [mscorlib]System.IntPtr + call void [mscorlib]System.Console::WriteLine(object) + ret + } + + .method public hidebysig static void Main (string[] args) cil managed { + .entrypoint + .try { + ldc.i4.0 + call void Program::Print(native int) + ldc.i8 7595444518666557374 + conv.i + call void Program::Print(native int) + leave.s eof + } catch [mscorlib]System.Exception { + callvirt instance string [mscorlib]System.Object::ToString() + call void [mscorlib]System.Console::WriteLine(object) + leave.s eof + } + eof: ret + } +} diff --git a/ICSharpCode.Decompiler/Tests/TestRunner.cs b/ICSharpCode.Decompiler/Tests/TestRunner.cs index 60ccec10d..7661e10af 100644 --- a/ICSharpCode.Decompiler/Tests/TestRunner.cs +++ b/ICSharpCode.Decompiler/Tests/TestRunner.cs @@ -113,6 +113,13 @@ namespace ICSharpCode.Decompiler.Tests { TestAssembleDecompileCompileOutput("ILTest.il"); } + + [Test] + public void ConvTest() + { + TestAssembleDecompileCompileOutput("ConvTest.il"); + TestAssembleDecompileCompileOutput("ConvTest.il", CompilerOptions.UseDebug | CompilerOptions.Force32Bit, AssemblerOptions.Force32Bit); + } [Test, Ignore("Fixed statements are broken")] public void UnsafeCode() @@ -150,13 +157,13 @@ namespace ICSharpCode.Decompiler.Tests } } - void TestAssembleDecompileCompileOutput(string testFileName, CompilerOptions options = CompilerOptions.UseDebug) + void TestAssembleDecompileCompileOutput(string testFileName, CompilerOptions options = CompilerOptions.UseDebug, AssemblerOptions asmOptions = AssemblerOptions.None) { string outputFile = null; CompilerResults decompiledOutputFile = null; try { - outputFile = Tester.AssembleIL(Path.Combine(TestCasePath, testFileName)); + outputFile = Tester.AssembleIL(Path.Combine(TestCasePath, testFileName), asmOptions); string decompiledCodeFile = Tester.DecompileCSharp(outputFile); decompiledOutputFile = Tester.CompileCSharp(decompiledCodeFile, options);