diff --git a/ICSharpCode.Decompiler.Tests/ICSharpCode.Decompiler.Tests.csproj b/ICSharpCode.Decompiler.Tests/ICSharpCode.Decompiler.Tests.csproj
index 490bc4c50..89f6df071 100644
--- a/ICSharpCode.Decompiler.Tests/ICSharpCode.Decompiler.Tests.csproj
+++ b/ICSharpCode.Decompiler.Tests/ICSharpCode.Decompiler.Tests.csproj
@@ -66,6 +66,7 @@
+
diff --git a/ICSharpCode.Decompiler.Tests/PrettyTestRunner.cs b/ICSharpCode.Decompiler.Tests/PrettyTestRunner.cs
index f5eee0fb8..f2c340f2a 100644
--- a/ICSharpCode.Decompiler.Tests/PrettyTestRunner.cs
+++ b/ICSharpCode.Decompiler.Tests/PrettyTestRunner.cs
@@ -181,6 +181,12 @@ namespace ICSharpCode.Decompiler.Tests
Run(cscOptions: cscOptions);
}
+ [Test]
+ public void UnsafeCode([ValueSource("defaultOptions")] CompilerOptions cscOptions)
+ {
+ Run(cscOptions: cscOptions);
+ }
+
[Test]
public void PInvoke([ValueSource("defaultOptions")] CompilerOptions cscOptions)
{
diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Correctness/UnsafeCode.cs b/ICSharpCode.Decompiler.Tests/TestCases/Correctness/UnsafeCode.cs
index 300b89c48..c4bc7796b 100644
--- a/ICSharpCode.Decompiler.Tests/TestCases/Correctness/UnsafeCode.cs
+++ b/ICSharpCode.Decompiler.Tests/TestCases/Correctness/UnsafeCode.cs
@@ -22,7 +22,7 @@ namespace ICSharpCode.Decompiler.Tests.TestCases.Correctness
{
public class UnsafeCode
{
- struct SimpleStruct
+ private struct SimpleStruct
{
public int X;
public double Y;
@@ -34,66 +34,6 @@ namespace ICSharpCode.Decompiler.Tests.TestCases.Correctness
// (but for now, it's already valuable knowing whether the decompiled code can be re-compiled)
}
- public unsafe int* NullPointer
- {
- get {
- return null;
- }
- }
-
- public unsafe int* PointerCast(long* p)
- {
- return (int*)p;
- }
-
- public unsafe long ConvertDoubleToLong(double d)
- {
- return *(long*)(&d);
- }
-
- public unsafe double ConvertLongToDouble(long d)
- {
- return *(double*)(&d);
- }
-
- public unsafe int ConvertFloatToInt(float d)
- {
- return *(int*)(&d);
- }
-
- public unsafe float ConvertIntToFloat(int d)
- {
- return *(float*)(&d);
- }
-
- public unsafe int PointerCasts()
- {
- int i = 0;
- *(float*)&i = 0.5f;
- ((byte*)&i)[3] = 3;
- return i;
- }
-
- public unsafe void PassRefParameterAsPointer(ref int p)
- {
- fixed (int* ptr = &p) {
- this.PassPointerAsRefParameter(ptr);
- }
- }
-
- public unsafe void PassPointerAsRefParameter(int* p)
- {
- this.PassRefParameterAsPointer(ref *p);
- }
-
- public unsafe void AddressInMultiDimensionalArray(double[,] matrix)
- {
- fixed (double* ptr = &matrix[1, 2]) {
- this.PointerReferenceExpression(ptr);
- this.PointerReferenceExpression(ptr);
- }
- }
-
public unsafe int MultipleExitsOutOfFixedBlock(int[] arr)
{
fixed (int* ptr = &arr[0]) {
@@ -109,42 +49,7 @@ namespace ICSharpCode.Decompiler.Tests.TestCases.Correctness
Console.WriteLine("outside");
return 2;
}
-
- public unsafe void FixedStringAccess(string text)
- {
- fixed (char* ptr = text) {
- char* ptr2 = ptr;
- while (*ptr2 != '\0') {
- *ptr2 = 'A';
- ptr2++;
- }
- }
- }
-
- public unsafe void PutDoubleIntoLongArray1(long[] array, int index, double val)
- {
- fixed (long* ptr = array) {
- ((double*)ptr)[index] = val;
- }
- }
-
- public unsafe void PutDoubleIntoLongArray2(long[] array, int index, double val)
- {
- fixed (long* ptr = &array[index]) {
- *(double*)ptr = val;
- }
- }
-
- public unsafe string PointerReferenceExpression(double* d)
- {
- return d->ToString();
- }
-
- public unsafe string PointerReferenceExpression2(long addr)
- {
- return ((int*)addr)->ToString();
- }
-
+
public unsafe void FixMultipleStrings(string text)
{
fixed (char* ptr = text, userName = Environment.UserName, ptr2 = text) {
@@ -154,6 +59,11 @@ namespace ICSharpCode.Decompiler.Tests.TestCases.Correctness
}
}
+ public unsafe string UsePointer(double* ptr)
+ {
+ return ptr->ToString();
+ }
+
public unsafe string StackAlloc(int count)
{
char* ptr = stackalloc char[count];
@@ -161,64 +71,19 @@ namespace ICSharpCode.Decompiler.Tests.TestCases.Correctness
for (int i = 0; i < count; i++) {
ptr[i] = (char)i;
}
- return this.PointerReferenceExpression((double*)ptr);
+ return this.UsePointer((double*)ptr);
}
public unsafe string StackAllocStruct(int count)
{
SimpleStruct* s = stackalloc SimpleStruct[checked(count * 2)];
SimpleStruct* p = stackalloc SimpleStruct[10];
- return this.PointerReferenceExpression(&s->Y);
- }
-
- public unsafe int* PointerArithmetic(int* p)
- {
- return p + 2;
+ return this.UsePointer(&s->Y);
}
-
+
public unsafe byte* PointerArithmetic2(long* p, int y, int x)
{
return (byte*)((short*)p + (y * x));
}
-
- public unsafe long* PointerArithmetic3(long* p)
- {
- return (long*)((byte*)p + 3);
- }
-
- public unsafe long* PointerArithmetic4(void* p)
- {
- return (long*)((byte*)p + 3);
- }
-
- public unsafe int PointerArithmetic5(void* p, byte* q, int i)
- {
- return (int)(q[i] + *(byte*)p);
- }
-
- public unsafe int PointerSubtraction(long* p, long* q)
- {
- return (int)(p - q);
- }
-
- public unsafe long PointerSubtractionLong(long* p, long* q)
- {
- return p - q;
- }
-
- public unsafe int PointerSubtraction2(long* p, short* q)
- {
- return (int)((byte*)p - (byte*)q);
- }
-
- public unsafe int PointerSubtraction3(void* p, void* q)
- {
- return (int)((byte*)p - (byte*)q);
- }
-
- unsafe ~UnsafeCode()
- {
- this.PassPointerAsRefParameter(this.NullPointer);
- }
}
}
\ No newline at end of file
diff --git a/ICSharpCode.Decompiler.Tests/TestCases/ILPretty/.gitignore b/ICSharpCode.Decompiler.Tests/TestCases/ILPretty/.gitignore
new file mode 100644
index 000000000..61d62080a
--- /dev/null
+++ b/ICSharpCode.Decompiler.Tests/TestCases/ILPretty/.gitignore
@@ -0,0 +1 @@
+/*.dll
diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/.gitignore b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/.gitignore
index a520eba40..bf449394f 100644
--- a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/.gitignore
+++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/.gitignore
@@ -1,3 +1,4 @@
/*.res
/*.dll
/*.exe
+/*.pdb
diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.cs b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.cs
new file mode 100644
index 000000000..6ca516963
--- /dev/null
+++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.cs
@@ -0,0 +1,173 @@
+// Copyright (c) AlphaSierraPapa for the SharpDevelop Team
+//
+// Permission is hereby granted, free of charge, to any person obtaining a copy of this
+// software and associated documentation files (the "Software"), to deal in the Software
+// without restriction, including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
+// to whom the Software is furnished to do so, subject to the following conditions:
+//
+// The above copyright notice and this permission notice shall be included in all copies or
+// substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
+// FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
+// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+// DEALINGS IN THE SOFTWARE.
+
+namespace ICSharpCode.Decompiler.Tests.TestCases.Pretty
+{
+ public class UnsafeCode
+ {
+ private struct SimpleStruct
+ {
+ public int X;
+ public double Y;
+ }
+
+ public unsafe int* NullPointer {
+ get {
+ return null;
+ }
+ }
+
+ public unsafe int* PointerCast(long* p)
+ {
+ return (int*)p;
+ }
+
+ public unsafe long ConvertDoubleToLong(double d)
+ {
+ return *(long*)(&d);
+ }
+
+ public unsafe double ConvertLongToDouble(long d)
+ {
+ return *(double*)(&d);
+ }
+
+ public unsafe int ConvertFloatToInt(float d)
+ {
+ return *(int*)(&d);
+ }
+
+ public unsafe float ConvertIntToFloat(int d)
+ {
+ return *(float*)(&d);
+ }
+
+ public unsafe int PointerCasts()
+ {
+ int result = 0;
+ *(float*)(&result) = 0.5f;
+ ((byte*)(&result))[3] = 3;
+ return result;
+ }
+
+ public unsafe void PassRefParameterAsPointer(ref int p)
+ {
+ fixed (int* p2 = &p) {
+ this.PassPointerAsRefParameter(p2);
+ }
+ }
+
+ public unsafe void PassPointerAsRefParameter(int* p)
+ {
+ this.PassRefParameterAsPointer(ref *p);
+ }
+
+ public unsafe void AddressInMultiDimensionalArray(double[,] matrix)
+ {
+ fixed (double* d = &matrix[1, 2]) {
+ this.PointerReferenceExpression(d);
+ this.PointerReferenceExpression(d);
+ }
+ }
+
+ public unsafe void FixedStringAccess(string text)
+ {
+ fixed (char* ptr = text) {
+ char* ptr2 = ptr;
+ while (*ptr2 == 'a') {
+ *ptr2 = 'A';
+ ptr2++;
+ }
+ }
+ }
+
+ public unsafe void PutDoubleIntoLongArray1(long[] array, int index, double val)
+ {
+ fixed (long* ptr = array) {
+ *(double*)(ptr + index) = val;
+ }
+ }
+
+ public unsafe void PutDoubleIntoLongArray2(long[] array, int index, double val)
+ {
+ fixed (long* ptr = &array[index]) {
+ *(double*)ptr = val;
+ }
+ }
+
+ public unsafe string PointerReferenceExpression(double* d)
+ {
+ return d->ToString();
+ }
+
+ public unsafe string PointerReferenceExpression2(long addr)
+ {
+ return ((int*)addr)->ToString();
+ }
+
+ public unsafe int* PointerArithmetic(int* p)
+ {
+ return p + 2;
+ }
+
+ public unsafe long* PointerArithmetic2(long* p, int y, int x)
+ {
+ return 3 + p;
+ }
+
+ public unsafe long* PointerArithmetic3(long* p)
+ {
+ return (long*)((byte*)p + 3);
+ }
+
+ public unsafe long* PointerArithmetic4(void* p)
+ {
+ return (long*)((byte*)p + 3);
+ }
+
+ public unsafe int PointerArithmetic5(void* p, byte* q, int i)
+ {
+ return q[i] + *(byte*)p;
+ }
+
+ public unsafe int PointerSubtraction(long* p, long* q)
+ {
+ return (int)(p - q);
+ }
+
+ public unsafe long PointerSubtractionLong(long* p, long* q)
+ {
+ return p - q;
+ }
+
+ public unsafe int PointerSubtraction2(long* p, short* q)
+ {
+ return (int)((byte*)p - (byte*)q);
+ }
+
+ public unsafe int PointerSubtraction3(void* p, void* q)
+ {
+ return (int)((byte*)p - (byte*)q);
+ }
+
+ unsafe ~UnsafeCode()
+ {
+ this.PassPointerAsRefParameter(this.NullPointer);
+ }
+ }
+}
diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.il b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.il
new file mode 100644
index 000000000..7bf84bf45
--- /dev/null
+++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.il
@@ -0,0 +1,625 @@
+
+// Microsoft (R) .NET Framework IL Disassembler. Version 4.6.1055.0
+// Copyright (c) Microsoft Corporation. All rights reserved.
+
+
+
+// Metadata version: v4.0.30319
+.assembly extern mscorlib
+{
+ .publickeytoken = (B7 7A 5C 56 19 34 E0 89 ) // .z\V.4..
+ .ver 4:0:0:0
+}
+.assembly aaldze1a
+{
+ .custom instance void [mscorlib]System.Runtime.CompilerServices.CompilationRelaxationsAttribute::.ctor(int32) = ( 01 00 08 00 00 00 00 00 )
+ .custom instance void [mscorlib]System.Runtime.CompilerServices.RuntimeCompatibilityAttribute::.ctor() = ( 01 00 01 00 54 02 16 57 72 61 70 4E 6F 6E 45 78 // ....T..WrapNonEx
+ 63 65 70 74 69 6F 6E 54 68 72 6F 77 73 01 ) // ceptionThrows.
+ .permissionset reqmin
+ = {[mscorlib]System.Security.Permissions.SecurityPermissionAttribute = {property bool 'SkipVerification' = bool(true)}}
+ .hash algorithm 0x00008004
+ .ver 0:0:0:0
+}
+.module aaldze1a.dll
+// MVID: {70B2C372-F51A-4F0B-B8F4-F20FC0522B70}
+.custom instance void [mscorlib]System.Security.UnverifiableCodeAttribute::.ctor() = ( 01 00 00 00 )
+.imagebase 0x10000000
+.file alignment 0x00000200
+.stackreserve 0x00100000
+.subsystem 0x0003 // WINDOWS_CUI
+.corflags 0x00000001 // ILONLY
+// Image base: 0x015B0000
+
+
+// =============== CLASS MEMBERS DECLARATION ===================
+
+.class public auto ansi beforefieldinit ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode
+ extends [mscorlib]System.Object
+{
+ .class sequential ansi sealed nested private beforefieldinit SimpleStruct
+ extends [mscorlib]System.ValueType
+ {
+ .field public int32 X
+ .field public float64 Y
+ } // end of class SimpleStruct
+
+ .method public hidebysig specialname instance int32*
+ get_NullPointer() cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 1
+ .locals init (int32* V_0)
+ IL_0000: nop
+ IL_0001: ldc.i4.0
+ IL_0002: conv.u
+ IL_0003: stloc.0
+ IL_0004: br.s IL_0006
+
+ IL_0006: ldloc.0
+ IL_0007: ret
+ } // end of method UnsafeCode::get_NullPointer
+
+ .method public hidebysig instance int32*
+ PointerCast(int64* p) cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 1
+ .locals init (int32* V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: stloc.0
+ IL_0003: br.s IL_0005
+
+ IL_0005: ldloc.0
+ IL_0006: ret
+ } // end of method UnsafeCode::PointerCast
+
+ .method public hidebysig instance int64
+ ConvertDoubleToLong(float64 d) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 1
+ .locals init (int64 V_0)
+ IL_0000: nop
+ IL_0001: ldarga.s d
+ IL_0003: conv.u
+ IL_0004: ldind.i8
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::ConvertDoubleToLong
+
+ .method public hidebysig instance float64
+ ConvertLongToDouble(int64 d) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 1
+ .locals init (float64 V_0)
+ IL_0000: nop
+ IL_0001: ldarga.s d
+ IL_0003: conv.u
+ IL_0004: ldind.r8
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::ConvertLongToDouble
+
+ .method public hidebysig instance int32
+ ConvertFloatToInt(float32 d) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 1
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarga.s d
+ IL_0003: conv.u
+ IL_0004: ldind.i4
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::ConvertFloatToInt
+
+ .method public hidebysig instance float32
+ ConvertIntToFloat(int32 d) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 1
+ .locals init (float32 V_0)
+ IL_0000: nop
+ IL_0001: ldarga.s d
+ IL_0003: conv.u
+ IL_0004: ldind.r4
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::ConvertIntToFloat
+
+ .method public hidebysig instance int32
+ PointerCasts() cil managed
+ {
+ // Code size 26 (0x1a)
+ .maxstack 2
+ .locals init (int32 V_0,
+ int32 V_1)
+ IL_0000: nop
+ IL_0001: ldc.i4.0
+ IL_0002: stloc.0
+ IL_0003: ldloca.s V_0
+ IL_0005: conv.u
+ IL_0006: ldc.r4 0.5
+ IL_000b: stind.r4
+ IL_000c: ldloca.s V_0
+ IL_000e: conv.u
+ IL_000f: ldc.i4.3
+ IL_0010: conv.i
+ IL_0011: add
+ IL_0012: ldc.i4.3
+ IL_0013: stind.i1
+ IL_0014: ldloc.0
+ IL_0015: stloc.1
+ IL_0016: br.s IL_0018
+
+ IL_0018: ldloc.1
+ IL_0019: ret
+ } // end of method UnsafeCode::PointerCasts
+
+ .method public hidebysig instance void
+ PassRefParameterAsPointer(int32& p) cil managed
+ {
+ // Code size 18 (0x12)
+ .maxstack 2
+ .locals init (int32& pinned V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: stloc.0
+ IL_0003: nop
+ IL_0004: ldarg.0
+ IL_0005: ldloc.0
+ IL_0006: conv.i
+ IL_0007: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassPointerAsRefParameter(int32*)
+ IL_000c: nop
+ IL_000d: nop
+ IL_000e: ldc.i4.0
+ IL_000f: conv.u
+ IL_0010: stloc.0
+ IL_0011: ret
+ } // end of method UnsafeCode::PassRefParameterAsPointer
+
+ .method public hidebysig instance void
+ PassPointerAsRefParameter(int32* p) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 8
+ IL_0000: nop
+ IL_0001: ldarg.0
+ IL_0002: ldarg.1
+ IL_0003: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassRefParameterAsPointer(int32&)
+ IL_0008: nop
+ IL_0009: ret
+ } // end of method UnsafeCode::PassPointerAsRefParameter
+
+ .method public hidebysig instance void
+ AddressInMultiDimensionalArray(float64[0...,0...] matrix) cil managed
+ {
+ // Code size 34 (0x22)
+ .maxstack 3
+ .locals init (float64& pinned V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldc.i4.1
+ IL_0003: ldc.i4.2
+ IL_0004: call instance float64& float64[0...,0...]::Address(int32,
+ int32)
+ IL_0009: stloc.0
+ IL_000a: nop
+ IL_000b: ldarg.0
+ IL_000c: ldloc.0
+ IL_000d: conv.i
+ IL_000e: call instance string ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PointerReferenceExpression(float64*)
+ IL_0013: pop
+ IL_0014: ldarg.0
+ IL_0015: ldloc.0
+ IL_0016: conv.i
+ IL_0017: call instance string ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PointerReferenceExpression(float64*)
+ IL_001c: pop
+ IL_001d: nop
+ IL_001e: ldc.i4.0
+ IL_001f: conv.u
+ IL_0020: stloc.0
+ IL_0021: ret
+ } // end of method UnsafeCode::AddressInMultiDimensionalArray
+
+ .method public hidebysig instance void
+ FixedStringAccess(string text) cil managed
+ {
+ // Code size 45 (0x2d)
+ .maxstack 2
+ .locals init (char* V_0,
+ char* V_1,
+ string pinned V_2,
+ bool V_3)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: stloc.2
+ IL_0003: ldloc.2
+ IL_0004: conv.i
+ IL_0005: dup
+ IL_0006: brfalse.s IL_000e
+
+ IL_0008: call int32 [mscorlib]System.Runtime.CompilerServices.RuntimeHelpers::get_OffsetToStringData()
+ IL_000d: add
+ IL_000e: stloc.0
+ IL_000f: nop
+ IL_0010: ldloc.0
+ IL_0011: stloc.1
+ IL_0012: br.s IL_001f
+
+ IL_0014: nop
+ IL_0015: ldloc.1
+ IL_0016: ldc.i4.s 65
+ IL_0018: stind.i2
+ IL_0019: ldloc.1
+ IL_001a: ldc.i4.2
+ IL_001b: conv.i
+ IL_001c: add
+ IL_001d: stloc.1
+ IL_001e: nop
+ IL_001f: ldloc.1
+ IL_0020: ldind.u2
+ IL_0021: ldc.i4.s 97
+ IL_0023: ceq
+ IL_0025: stloc.3
+ IL_0026: ldloc.3
+ IL_0027: brtrue.s IL_0014
+
+ IL_0029: nop
+ IL_002a: ldnull
+ IL_002b: stloc.2
+ IL_002c: ret
+ } // end of method UnsafeCode::FixedStringAccess
+
+ .method public hidebysig instance void
+ PutDoubleIntoLongArray1(int64[] 'array',
+ int32 index,
+ float64 val) cil managed
+ {
+ // Code size 39 (0x27)
+ .maxstack 3
+ .locals init (int64& pinned V_0,
+ int64[] V_1)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: dup
+ IL_0003: stloc.1
+ IL_0004: brfalse.s IL_000b
+
+ IL_0006: ldloc.1
+ IL_0007: ldlen
+ IL_0008: conv.i4
+ IL_0009: brtrue.s IL_0010
+
+ IL_000b: ldc.i4.0
+ IL_000c: conv.u
+ IL_000d: stloc.0
+ IL_000e: br.s IL_0018
+
+ IL_0010: ldloc.1
+ IL_0011: ldc.i4.0
+ IL_0012: ldelema [mscorlib]System.Int64
+ IL_0017: stloc.0
+ IL_0018: nop
+ IL_0019: ldloc.0
+ IL_001a: conv.i
+ IL_001b: ldarg.2
+ IL_001c: conv.i
+ IL_001d: ldc.i4.8
+ IL_001e: mul
+ IL_001f: add
+ IL_0020: ldarg.3
+ IL_0021: stind.r8
+ IL_0022: nop
+ IL_0023: ldc.i4.0
+ IL_0024: conv.u
+ IL_0025: stloc.0
+ IL_0026: ret
+ } // end of method UnsafeCode::PutDoubleIntoLongArray1
+
+ .method public hidebysig instance void
+ PutDoubleIntoLongArray2(int64[] 'array',
+ int32 index,
+ float64 val) cil managed
+ {
+ // Code size 19 (0x13)
+ .maxstack 2
+ .locals init (int64& pinned V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: ldelema [mscorlib]System.Int64
+ IL_0008: stloc.0
+ IL_0009: nop
+ IL_000a: ldloc.0
+ IL_000b: conv.i
+ IL_000c: ldarg.3
+ IL_000d: stind.r8
+ IL_000e: nop
+ IL_000f: ldc.i4.0
+ IL_0010: conv.u
+ IL_0011: stloc.0
+ IL_0012: ret
+ } // end of method UnsafeCode::PutDoubleIntoLongArray2
+
+ .method public hidebysig instance string
+ PointerReferenceExpression(float64* d) cil managed
+ {
+ // Code size 12 (0xc)
+ .maxstack 1
+ .locals init (string V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: call instance string [mscorlib]System.Double::ToString()
+ IL_0007: stloc.0
+ IL_0008: br.s IL_000a
+
+ IL_000a: ldloc.0
+ IL_000b: ret
+ } // end of method UnsafeCode::PointerReferenceExpression
+
+ .method public hidebysig instance string
+ PointerReferenceExpression2(int64 addr) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 1
+ .locals init (string V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: conv.u
+ IL_0003: call instance string [mscorlib]System.Int32::ToString()
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerReferenceExpression2
+
+ .method public hidebysig instance int32*
+ PointerArithmetic(int32* p) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 2
+ .locals init (int32* V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldc.i4.8
+ IL_0003: conv.i
+ IL_0004: add
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::PointerArithmetic
+
+ .method public hidebysig instance int64*
+ PointerArithmetic2(int64* p,
+ int32 y,
+ int32 x) cil managed
+ {
+ // Code size 11 (0xb)
+ .maxstack 2
+ .locals init (int64* V_0)
+ IL_0000: nop
+ IL_0001: ldc.i4.s 24
+ IL_0003: conv.i
+ IL_0004: ldarg.1
+ IL_0005: add
+ IL_0006: stloc.0
+ IL_0007: br.s IL_0009
+
+ IL_0009: ldloc.0
+ IL_000a: ret
+ } // end of method UnsafeCode::PointerArithmetic2
+
+ .method public hidebysig instance int64*
+ PointerArithmetic3(int64* p) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 2
+ .locals init (int64* V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldc.i4.3
+ IL_0003: conv.i
+ IL_0004: add
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::PointerArithmetic3
+
+ .method public hidebysig instance int64*
+ PointerArithmetic4(void* p) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 2
+ .locals init (int64* V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldc.i4.3
+ IL_0003: conv.i
+ IL_0004: add
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::PointerArithmetic4
+
+ .method public hidebysig instance int32
+ PointerArithmetic5(void* p,
+ uint8* q,
+ int32 i) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.2
+ IL_0002: ldarg.3
+ IL_0003: add
+ IL_0004: ldind.u1
+ IL_0005: ldarg.1
+ IL_0006: ldind.u1
+ IL_0007: add
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerArithmetic5
+
+ .method public hidebysig instance int32
+ PointerSubtraction(int64* p,
+ int64* q) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: sub
+ IL_0004: ldc.i4.8
+ IL_0005: div
+ IL_0006: conv.i8
+ IL_0007: conv.i4
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerSubtraction
+
+ .method public hidebysig instance int64
+ PointerSubtractionLong(int64* p,
+ int64* q) cil managed
+ {
+ // Code size 12 (0xc)
+ .maxstack 2
+ .locals init (int64 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: sub
+ IL_0004: ldc.i4.8
+ IL_0005: div
+ IL_0006: conv.i8
+ IL_0007: stloc.0
+ IL_0008: br.s IL_000a
+
+ IL_000a: ldloc.0
+ IL_000b: ret
+ } // end of method UnsafeCode::PointerSubtractionLong
+
+ .method public hidebysig instance int32
+ PointerSubtraction2(int64* p,
+ int16* q) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: sub
+ IL_0004: ldc.i4.1
+ IL_0005: div
+ IL_0006: conv.i8
+ IL_0007: conv.i4
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerSubtraction2
+
+ .method public hidebysig instance int32
+ PointerSubtraction3(void* p,
+ void* q) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: sub
+ IL_0004: ldc.i4.1
+ IL_0005: div
+ IL_0006: conv.i8
+ IL_0007: conv.i4
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerSubtraction3
+
+ .method family hidebysig virtual instance void
+ Finalize() cil managed
+ {
+ // Code size 27 (0x1b)
+ .maxstack 2
+ .try
+ {
+ IL_0000: nop
+ IL_0001: ldarg.0
+ IL_0002: ldarg.0
+ IL_0003: call instance int32* ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::get_NullPointer()
+ IL_0008: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassPointerAsRefParameter(int32*)
+ IL_000d: nop
+ IL_000e: nop
+ IL_000f: leave.s IL_0019
+
+ } // end .try
+ finally
+ {
+ IL_0011: ldarg.0
+ IL_0012: call instance void [mscorlib]System.Object::Finalize()
+ IL_0017: nop
+ IL_0018: endfinally
+ } // end handler
+ IL_0019: nop
+ IL_001a: ret
+ } // end of method UnsafeCode::Finalize
+
+ .method public hidebysig specialname rtspecialname
+ instance void .ctor() cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldarg.0
+ IL_0001: call instance void [mscorlib]System.Object::.ctor()
+ IL_0006: ret
+ } // end of method UnsafeCode::.ctor
+
+ .property instance int32* NullPointer()
+ {
+ .get instance int32* ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::get_NullPointer()
+ } // end of property UnsafeCode::NullPointer
+} // end of class ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode
+
+
+// =============================================================
+
+// *********** DISASSEMBLY COMPLETE ***********************
+// WARNING: Created Win32 resource file ../../../TestCases/Pretty\UnsafeCode.res
diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.opt.il b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.opt.il
new file mode 100644
index 000000000..c628de3c4
--- /dev/null
+++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.opt.il
@@ -0,0 +1,488 @@
+
+// Microsoft (R) .NET Framework IL Disassembler. Version 4.6.1055.0
+// Copyright (c) Microsoft Corporation. All rights reserved.
+
+
+
+// Metadata version: v4.0.30319
+.assembly extern mscorlib
+{
+ .publickeytoken = (B7 7A 5C 56 19 34 E0 89 ) // .z\V.4..
+ .ver 4:0:0:0
+}
+.assembly puaa14mr
+{
+ .custom instance void [mscorlib]System.Runtime.CompilerServices.CompilationRelaxationsAttribute::.ctor(int32) = ( 01 00 08 00 00 00 00 00 )
+ .custom instance void [mscorlib]System.Runtime.CompilerServices.RuntimeCompatibilityAttribute::.ctor() = ( 01 00 01 00 54 02 16 57 72 61 70 4E 6F 6E 45 78 // ....T..WrapNonEx
+ 63 65 70 74 69 6F 6E 54 68 72 6F 77 73 01 ) // ceptionThrows.
+ .permissionset reqmin
+ = {[mscorlib]System.Security.Permissions.SecurityPermissionAttribute = {property bool 'SkipVerification' = bool(true)}}
+ .hash algorithm 0x00008004
+ .ver 0:0:0:0
+}
+.module puaa14mr.dll
+// MVID: {CFE0F8E8-DA3C-494E-93C4-14BC506B54FF}
+.custom instance void [mscorlib]System.Security.UnverifiableCodeAttribute::.ctor() = ( 01 00 00 00 )
+.imagebase 0x10000000
+.file alignment 0x00000200
+.stackreserve 0x00100000
+.subsystem 0x0003 // WINDOWS_CUI
+.corflags 0x00000001 // ILONLY
+// Image base: 0x014E0000
+
+
+// =============== CLASS MEMBERS DECLARATION ===================
+
+.class public auto ansi beforefieldinit ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode
+ extends [mscorlib]System.Object
+{
+ .class sequential ansi sealed nested private beforefieldinit SimpleStruct
+ extends [mscorlib]System.ValueType
+ {
+ .field public int32 X
+ .field public float64 Y
+ } // end of class SimpleStruct
+
+ .method public hidebysig specialname instance int32*
+ get_NullPointer() cil managed
+ {
+ // Code size 3 (0x3)
+ .maxstack 8
+ IL_0000: ldc.i4.0
+ IL_0001: conv.u
+ IL_0002: ret
+ } // end of method UnsafeCode::get_NullPointer
+
+ .method public hidebysig instance int32*
+ PointerCast(int64* p) cil managed
+ {
+ // Code size 2 (0x2)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ret
+ } // end of method UnsafeCode::PointerCast
+
+ .method public hidebysig instance int64
+ ConvertDoubleToLong(float64 d) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarga.s d
+ IL_0002: conv.u
+ IL_0003: ldind.i8
+ IL_0004: ret
+ } // end of method UnsafeCode::ConvertDoubleToLong
+
+ .method public hidebysig instance float64
+ ConvertLongToDouble(int64 d) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarga.s d
+ IL_0002: conv.u
+ IL_0003: ldind.r8
+ IL_0004: ret
+ } // end of method UnsafeCode::ConvertLongToDouble
+
+ .method public hidebysig instance int32
+ ConvertFloatToInt(float32 d) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarga.s d
+ IL_0002: conv.u
+ IL_0003: ldind.i4
+ IL_0004: ret
+ } // end of method UnsafeCode::ConvertFloatToInt
+
+ .method public hidebysig instance float32
+ ConvertIntToFloat(int32 d) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarga.s d
+ IL_0002: conv.u
+ IL_0003: ldind.r4
+ IL_0004: ret
+ } // end of method UnsafeCode::ConvertIntToFloat
+
+ .method public hidebysig instance int32
+ PointerCasts() cil managed
+ {
+ // Code size 21 (0x15)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: ldc.i4.0
+ IL_0001: stloc.0
+ IL_0002: ldloca.s V_0
+ IL_0004: conv.u
+ IL_0005: ldc.r4 0.5
+ IL_000a: stind.r4
+ IL_000b: ldloca.s V_0
+ IL_000d: conv.u
+ IL_000e: ldc.i4.3
+ IL_000f: conv.i
+ IL_0010: add
+ IL_0011: ldc.i4.3
+ IL_0012: stind.i1
+ IL_0013: ldloc.0
+ IL_0014: ret
+ } // end of method UnsafeCode::PointerCasts
+
+ .method public hidebysig instance void
+ PassRefParameterAsPointer(int32& p) cil managed
+ {
+ // Code size 14 (0xe)
+ .maxstack 2
+ .locals init (int32& pinned V_0)
+ IL_0000: ldarg.1
+ IL_0001: stloc.0
+ IL_0002: ldarg.0
+ IL_0003: ldloc.0
+ IL_0004: conv.i
+ IL_0005: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassPointerAsRefParameter(int32*)
+ IL_000a: ldc.i4.0
+ IL_000b: conv.u
+ IL_000c: stloc.0
+ IL_000d: ret
+ } // end of method UnsafeCode::PassRefParameterAsPointer
+
+ .method public hidebysig instance void
+ PassPointerAsRefParameter(int32* p) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.0
+ IL_0001: ldarg.1
+ IL_0002: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassRefParameterAsPointer(int32&)
+ IL_0007: ret
+ } // end of method UnsafeCode::PassPointerAsRefParameter
+
+ .method public hidebysig instance void
+ AddressInMultiDimensionalArray(float64[0...,0...] matrix) cil managed
+ {
+ // Code size 31 (0x1f)
+ .maxstack 3
+ .locals init (float64& pinned V_0)
+ IL_0000: ldarg.1
+ IL_0001: ldc.i4.1
+ IL_0002: ldc.i4.2
+ IL_0003: call instance float64& float64[0...,0...]::Address(int32,
+ int32)
+ IL_0008: stloc.0
+ IL_0009: ldarg.0
+ IL_000a: ldloc.0
+ IL_000b: conv.i
+ IL_000c: call instance string ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PointerReferenceExpression(float64*)
+ IL_0011: pop
+ IL_0012: ldarg.0
+ IL_0013: ldloc.0
+ IL_0014: conv.i
+ IL_0015: call instance string ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PointerReferenceExpression(float64*)
+ IL_001a: pop
+ IL_001b: ldc.i4.0
+ IL_001c: conv.u
+ IL_001d: stloc.0
+ IL_001e: ret
+ } // end of method UnsafeCode::AddressInMultiDimensionalArray
+
+ .method public hidebysig instance void
+ FixedStringAccess(string text) cil managed
+ {
+ // Code size 36 (0x24)
+ .maxstack 2
+ .locals init (char* V_0,
+ char* V_1,
+ string pinned V_2)
+ IL_0000: ldarg.1
+ IL_0001: stloc.2
+ IL_0002: ldloc.2
+ IL_0003: conv.i
+ IL_0004: dup
+ IL_0005: brfalse.s IL_000d
+
+ IL_0007: call int32 [mscorlib]System.Runtime.CompilerServices.RuntimeHelpers::get_OffsetToStringData()
+ IL_000c: add
+ IL_000d: stloc.0
+ IL_000e: ldloc.0
+ IL_000f: stloc.1
+ IL_0010: br.s IL_001b
+
+ IL_0012: ldloc.1
+ IL_0013: ldc.i4.s 65
+ IL_0015: stind.i2
+ IL_0016: ldloc.1
+ IL_0017: ldc.i4.2
+ IL_0018: conv.i
+ IL_0019: add
+ IL_001a: stloc.1
+ IL_001b: ldloc.1
+ IL_001c: ldind.u2
+ IL_001d: ldc.i4.s 97
+ IL_001f: beq.s IL_0012
+
+ IL_0021: ldnull
+ IL_0022: stloc.2
+ IL_0023: ret
+ } // end of method UnsafeCode::FixedStringAccess
+
+ .method public hidebysig instance void
+ PutDoubleIntoLongArray1(int64[] 'array',
+ int32 index,
+ float64 val) cil managed
+ {
+ // Code size 36 (0x24)
+ .maxstack 3
+ .locals init (int64& pinned V_0,
+ int64[] V_1)
+ IL_0000: ldarg.1
+ IL_0001: dup
+ IL_0002: stloc.1
+ IL_0003: brfalse.s IL_000a
+
+ IL_0005: ldloc.1
+ IL_0006: ldlen
+ IL_0007: conv.i4
+ IL_0008: brtrue.s IL_000f
+
+ IL_000a: ldc.i4.0
+ IL_000b: conv.u
+ IL_000c: stloc.0
+ IL_000d: br.s IL_0017
+
+ IL_000f: ldloc.1
+ IL_0010: ldc.i4.0
+ IL_0011: ldelema [mscorlib]System.Int64
+ IL_0016: stloc.0
+ IL_0017: ldloc.0
+ IL_0018: conv.i
+ IL_0019: ldarg.2
+ IL_001a: conv.i
+ IL_001b: ldc.i4.8
+ IL_001c: mul
+ IL_001d: add
+ IL_001e: ldarg.3
+ IL_001f: stind.r8
+ IL_0020: ldc.i4.0
+ IL_0021: conv.u
+ IL_0022: stloc.0
+ IL_0023: ret
+ } // end of method UnsafeCode::PutDoubleIntoLongArray1
+
+ .method public hidebysig instance void
+ PutDoubleIntoLongArray2(int64[] 'array',
+ int32 index,
+ float64 val) cil managed
+ {
+ // Code size 16 (0x10)
+ .maxstack 2
+ .locals init (int64& pinned V_0)
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: ldelema [mscorlib]System.Int64
+ IL_0007: stloc.0
+ IL_0008: ldloc.0
+ IL_0009: conv.i
+ IL_000a: ldarg.3
+ IL_000b: stind.r8
+ IL_000c: ldc.i4.0
+ IL_000d: conv.u
+ IL_000e: stloc.0
+ IL_000f: ret
+ } // end of method UnsafeCode::PutDoubleIntoLongArray2
+
+ .method public hidebysig instance string
+ PointerReferenceExpression(float64* d) cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: call instance string [mscorlib]System.Double::ToString()
+ IL_0006: ret
+ } // end of method UnsafeCode::PointerReferenceExpression
+
+ .method public hidebysig instance string
+ PointerReferenceExpression2(int64 addr) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: conv.u
+ IL_0002: call instance string [mscorlib]System.Int32::ToString()
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerReferenceExpression2
+
+ .method public hidebysig instance int32*
+ PointerArithmetic(int32* p) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldc.i4.8
+ IL_0002: conv.i
+ IL_0003: add
+ IL_0004: ret
+ } // end of method UnsafeCode::PointerArithmetic
+
+ .method public hidebysig instance int64*
+ PointerArithmetic2(int64* p,
+ int32 y,
+ int32 x) cil managed
+ {
+ // Code size 6 (0x6)
+ .maxstack 8
+ IL_0000: ldc.i4.s 24
+ IL_0002: conv.i
+ IL_0003: ldarg.1
+ IL_0004: add
+ IL_0005: ret
+ } // end of method UnsafeCode::PointerArithmetic2
+
+ .method public hidebysig instance int64*
+ PointerArithmetic3(int64* p) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldc.i4.3
+ IL_0002: conv.i
+ IL_0003: add
+ IL_0004: ret
+ } // end of method UnsafeCode::PointerArithmetic3
+
+ .method public hidebysig instance int64*
+ PointerArithmetic4(void* p) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldc.i4.3
+ IL_0002: conv.i
+ IL_0003: add
+ IL_0004: ret
+ } // end of method UnsafeCode::PointerArithmetic4
+
+ .method public hidebysig instance int32
+ PointerArithmetic5(void* p,
+ uint8* q,
+ int32 i) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.2
+ IL_0001: ldarg.3
+ IL_0002: add
+ IL_0003: ldind.u1
+ IL_0004: ldarg.1
+ IL_0005: ldind.u1
+ IL_0006: add
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerArithmetic5
+
+ .method public hidebysig instance int32
+ PointerSubtraction(int64* p,
+ int64* q) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: sub
+ IL_0003: ldc.i4.8
+ IL_0004: div
+ IL_0005: conv.i8
+ IL_0006: conv.i4
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerSubtraction
+
+ .method public hidebysig instance int64
+ PointerSubtractionLong(int64* p,
+ int64* q) cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: sub
+ IL_0003: ldc.i4.8
+ IL_0004: div
+ IL_0005: conv.i8
+ IL_0006: ret
+ } // end of method UnsafeCode::PointerSubtractionLong
+
+ .method public hidebysig instance int32
+ PointerSubtraction2(int64* p,
+ int16* q) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: sub
+ IL_0003: ldc.i4.1
+ IL_0004: div
+ IL_0005: conv.i8
+ IL_0006: conv.i4
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerSubtraction2
+
+ .method public hidebysig instance int32
+ PointerSubtraction3(void* p,
+ void* q) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: sub
+ IL_0003: ldc.i4.1
+ IL_0004: div
+ IL_0005: conv.i8
+ IL_0006: conv.i4
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerSubtraction3
+
+ .method family hidebysig virtual instance void
+ Finalize() cil managed
+ {
+ // Code size 22 (0x16)
+ .maxstack 2
+ .try
+ {
+ IL_0000: ldarg.0
+ IL_0001: ldarg.0
+ IL_0002: call instance int32* ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::get_NullPointer()
+ IL_0007: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassPointerAsRefParameter(int32*)
+ IL_000c: leave.s IL_0015
+
+ } // end .try
+ finally
+ {
+ IL_000e: ldarg.0
+ IL_000f: call instance void [mscorlib]System.Object::Finalize()
+ IL_0014: endfinally
+ } // end handler
+ IL_0015: ret
+ } // end of method UnsafeCode::Finalize
+
+ .method public hidebysig specialname rtspecialname
+ instance void .ctor() cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldarg.0
+ IL_0001: call instance void [mscorlib]System.Object::.ctor()
+ IL_0006: ret
+ } // end of method UnsafeCode::.ctor
+
+ .property instance int32* NullPointer()
+ {
+ .get instance int32* ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::get_NullPointer()
+ } // end of property UnsafeCode::NullPointer
+} // end of class ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode
+
+
+// =============================================================
+
+// *********** DISASSEMBLY COMPLETE ***********************
+// WARNING: Created Win32 resource file ../../../TestCases/Pretty\UnsafeCode.opt.res
diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.opt.roslyn.il b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.opt.roslyn.il
new file mode 100644
index 000000000..bd5b99a4c
--- /dev/null
+++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.opt.roslyn.il
@@ -0,0 +1,494 @@
+
+// Microsoft (R) .NET Framework IL Disassembler. Version 4.6.1055.0
+// Copyright (c) Microsoft Corporation. All rights reserved.
+
+
+
+// Metadata version: v4.0.30319
+.assembly extern mscorlib
+{
+ .publickeytoken = (B7 7A 5C 56 19 34 E0 89 ) // .z\V.4..
+ .ver 4:0:0:0
+}
+.assembly UnsafeCode
+{
+ .custom instance void [mscorlib]System.Runtime.CompilerServices.CompilationRelaxationsAttribute::.ctor(int32) = ( 01 00 08 00 00 00 00 00 )
+ .custom instance void [mscorlib]System.Runtime.CompilerServices.RuntimeCompatibilityAttribute::.ctor() = ( 01 00 01 00 54 02 16 57 72 61 70 4E 6F 6E 45 78 // ....T..WrapNonEx
+ 63 65 70 74 69 6F 6E 54 68 72 6F 77 73 01 ) // ceptionThrows.
+
+ // --- The following custom attribute is added automatically, do not uncomment -------
+ // .custom instance void [mscorlib]System.Diagnostics.DebuggableAttribute::.ctor(valuetype [mscorlib]System.Diagnostics.DebuggableAttribute/DebuggingModes) = ( 01 00 02 00 00 00 00 00 )
+
+ .permissionset reqmin
+ = {[mscorlib]System.Security.Permissions.SecurityPermissionAttribute = {property bool 'SkipVerification' = bool(true)}}
+ .hash algorithm 0x00008004
+ .ver 0:0:0:0
+}
+.module UnsafeCode.dll
+// MVID: {858D67FE-2C39-4F0B-B696-FA10954BDC00}
+.custom instance void [mscorlib]System.Security.UnverifiableCodeAttribute::.ctor() = ( 01 00 00 00 )
+.imagebase 0x10000000
+.file alignment 0x00000200
+.stackreserve 0x00100000
+.subsystem 0x0003 // WINDOWS_CUI
+.corflags 0x00000001 // ILONLY
+// Image base: 0x01270000
+
+
+// =============== CLASS MEMBERS DECLARATION ===================
+
+.class public auto ansi beforefieldinit ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode
+ extends [mscorlib]System.Object
+{
+ .class sequential ansi sealed nested private beforefieldinit SimpleStruct
+ extends [mscorlib]System.ValueType
+ {
+ .field public int32 X
+ .field public float64 Y
+ } // end of class SimpleStruct
+
+ .method public hidebysig specialname instance int32*
+ get_NullPointer() cil managed
+ {
+ // Code size 3 (0x3)
+ .maxstack 8
+ IL_0000: ldc.i4.0
+ IL_0001: conv.u
+ IL_0002: ret
+ } // end of method UnsafeCode::get_NullPointer
+
+ .method public hidebysig instance int32*
+ PointerCast(int64* p) cil managed
+ {
+ // Code size 2 (0x2)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ret
+ } // end of method UnsafeCode::PointerCast
+
+ .method public hidebysig instance int64
+ ConvertDoubleToLong(float64 d) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarga.s d
+ IL_0002: conv.u
+ IL_0003: ldind.i8
+ IL_0004: ret
+ } // end of method UnsafeCode::ConvertDoubleToLong
+
+ .method public hidebysig instance float64
+ ConvertLongToDouble(int64 d) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarga.s d
+ IL_0002: conv.u
+ IL_0003: ldind.r8
+ IL_0004: ret
+ } // end of method UnsafeCode::ConvertLongToDouble
+
+ .method public hidebysig instance int32
+ ConvertFloatToInt(float32 d) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarga.s d
+ IL_0002: conv.u
+ IL_0003: ldind.i4
+ IL_0004: ret
+ } // end of method UnsafeCode::ConvertFloatToInt
+
+ .method public hidebysig instance float32
+ ConvertIntToFloat(int32 d) cil managed
+ {
+ // Code size 5 (0x5)
+ .maxstack 8
+ IL_0000: ldarga.s d
+ IL_0002: conv.u
+ IL_0003: ldind.r4
+ IL_0004: ret
+ } // end of method UnsafeCode::ConvertIntToFloat
+
+ .method public hidebysig instance int32
+ PointerCasts() cil managed
+ {
+ // Code size 20 (0x14)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: ldc.i4.0
+ IL_0001: stloc.0
+ IL_0002: ldloca.s V_0
+ IL_0004: conv.u
+ IL_0005: ldc.r4 0.5
+ IL_000a: stind.r4
+ IL_000b: ldloca.s V_0
+ IL_000d: conv.u
+ IL_000e: ldc.i4.3
+ IL_000f: add
+ IL_0010: ldc.i4.3
+ IL_0011: stind.i1
+ IL_0012: ldloc.0
+ IL_0013: ret
+ } // end of method UnsafeCode::PointerCasts
+
+ .method public hidebysig instance void
+ PassRefParameterAsPointer(int32& p) cil managed
+ {
+ // Code size 14 (0xe)
+ .maxstack 2
+ .locals init (int32& pinned V_0)
+ IL_0000: ldarg.1
+ IL_0001: stloc.0
+ IL_0002: ldarg.0
+ IL_0003: ldloc.0
+ IL_0004: conv.i
+ IL_0005: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassPointerAsRefParameter(int32*)
+ IL_000a: ldc.i4.0
+ IL_000b: conv.u
+ IL_000c: stloc.0
+ IL_000d: ret
+ } // end of method UnsafeCode::PassRefParameterAsPointer
+
+ .method public hidebysig instance void
+ PassPointerAsRefParameter(int32* p) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.0
+ IL_0001: ldarg.1
+ IL_0002: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassRefParameterAsPointer(int32&)
+ IL_0007: ret
+ } // end of method UnsafeCode::PassPointerAsRefParameter
+
+ .method public hidebysig instance void
+ AddressInMultiDimensionalArray(float64[0...,0...] matrix) cil managed
+ {
+ // Code size 31 (0x1f)
+ .maxstack 3
+ .locals init (float64& pinned V_0)
+ IL_0000: ldarg.1
+ IL_0001: ldc.i4.1
+ IL_0002: ldc.i4.2
+ IL_0003: call instance float64& float64[0...,0...]::Address(int32,
+ int32)
+ IL_0008: stloc.0
+ IL_0009: ldarg.0
+ IL_000a: ldloc.0
+ IL_000b: conv.i
+ IL_000c: call instance string ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PointerReferenceExpression(float64*)
+ IL_0011: pop
+ IL_0012: ldarg.0
+ IL_0013: ldloc.0
+ IL_0014: conv.i
+ IL_0015: call instance string ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PointerReferenceExpression(float64*)
+ IL_001a: pop
+ IL_001b: ldc.i4.0
+ IL_001c: conv.u
+ IL_001d: stloc.0
+ IL_001e: ret
+ } // end of method UnsafeCode::AddressInMultiDimensionalArray
+
+ .method public hidebysig instance void
+ FixedStringAccess(string text) cil managed
+ {
+ // Code size 37 (0x25)
+ .maxstack 2
+ .locals init (char* V_0,
+ string pinned V_1,
+ char* V_2)
+ IL_0000: ldarg.1
+ IL_0001: stloc.1
+ IL_0002: ldloc.1
+ IL_0003: conv.i
+ IL_0004: stloc.0
+ IL_0005: ldloc.0
+ IL_0006: brfalse.s IL_0010
+
+ IL_0008: ldloc.0
+ IL_0009: call int32 [mscorlib]System.Runtime.CompilerServices.RuntimeHelpers::get_OffsetToStringData()
+ IL_000e: add
+ IL_000f: stloc.0
+ IL_0010: ldloc.0
+ IL_0011: stloc.2
+ IL_0012: br.s IL_001c
+
+ IL_0014: ldloc.2
+ IL_0015: ldc.i4.s 65
+ IL_0017: stind.i2
+ IL_0018: ldloc.2
+ IL_0019: ldc.i4.2
+ IL_001a: add
+ IL_001b: stloc.2
+ IL_001c: ldloc.2
+ IL_001d: ldind.u2
+ IL_001e: ldc.i4.s 97
+ IL_0020: beq.s IL_0014
+
+ IL_0022: ldnull
+ IL_0023: stloc.1
+ IL_0024: ret
+ } // end of method UnsafeCode::FixedStringAccess
+
+ .method public hidebysig instance void
+ PutDoubleIntoLongArray1(int64[] 'array',
+ int32 index,
+ float64 val) cil managed
+ {
+ // Code size 36 (0x24)
+ .maxstack 3
+ .locals init (int64& pinned V_0,
+ int64[] V_1)
+ IL_0000: ldarg.1
+ IL_0001: dup
+ IL_0002: stloc.1
+ IL_0003: brfalse.s IL_000a
+
+ IL_0005: ldloc.1
+ IL_0006: ldlen
+ IL_0007: conv.i4
+ IL_0008: brtrue.s IL_000f
+
+ IL_000a: ldc.i4.0
+ IL_000b: conv.u
+ IL_000c: stloc.0
+ IL_000d: br.s IL_0017
+
+ IL_000f: ldloc.1
+ IL_0010: ldc.i4.0
+ IL_0011: ldelema [mscorlib]System.Int64
+ IL_0016: stloc.0
+ IL_0017: ldloc.0
+ IL_0018: conv.i
+ IL_0019: ldarg.2
+ IL_001a: conv.i
+ IL_001b: ldc.i4.8
+ IL_001c: mul
+ IL_001d: add
+ IL_001e: ldarg.3
+ IL_001f: stind.r8
+ IL_0020: ldc.i4.0
+ IL_0021: conv.u
+ IL_0022: stloc.0
+ IL_0023: ret
+ } // end of method UnsafeCode::PutDoubleIntoLongArray1
+
+ .method public hidebysig instance void
+ PutDoubleIntoLongArray2(int64[] 'array',
+ int32 index,
+ float64 val) cil managed
+ {
+ // Code size 16 (0x10)
+ .maxstack 2
+ .locals init (int64& pinned V_0)
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: ldelema [mscorlib]System.Int64
+ IL_0007: stloc.0
+ IL_0008: ldloc.0
+ IL_0009: conv.i
+ IL_000a: ldarg.3
+ IL_000b: stind.r8
+ IL_000c: ldc.i4.0
+ IL_000d: conv.u
+ IL_000e: stloc.0
+ IL_000f: ret
+ } // end of method UnsafeCode::PutDoubleIntoLongArray2
+
+ .method public hidebysig instance string
+ PointerReferenceExpression(float64* d) cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: call instance string [mscorlib]System.Double::ToString()
+ IL_0006: ret
+ } // end of method UnsafeCode::PointerReferenceExpression
+
+ .method public hidebysig instance string
+ PointerReferenceExpression2(int64 addr) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: conv.u
+ IL_0002: call instance string [mscorlib]System.Int32::ToString()
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerReferenceExpression2
+
+ .method public hidebysig instance int32*
+ PointerArithmetic(int32* p) cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldc.i4.2
+ IL_0002: conv.i
+ IL_0003: ldc.i4.4
+ IL_0004: mul
+ IL_0005: add
+ IL_0006: ret
+ } // end of method UnsafeCode::PointerArithmetic
+
+ .method public hidebysig instance int64*
+ PointerArithmetic2(int64* p,
+ int32 y,
+ int32 x) cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldc.i4.3
+ IL_0001: conv.i
+ IL_0002: ldc.i4.8
+ IL_0003: mul
+ IL_0004: ldarg.1
+ IL_0005: add
+ IL_0006: ret
+ } // end of method UnsafeCode::PointerArithmetic2
+
+ .method public hidebysig instance int64*
+ PointerArithmetic3(int64* p) cil managed
+ {
+ // Code size 4 (0x4)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldc.i4.3
+ IL_0002: add
+ IL_0003: ret
+ } // end of method UnsafeCode::PointerArithmetic3
+
+ .method public hidebysig instance int64*
+ PointerArithmetic4(void* p) cil managed
+ {
+ // Code size 4 (0x4)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldc.i4.3
+ IL_0002: add
+ IL_0003: ret
+ } // end of method UnsafeCode::PointerArithmetic4
+
+ .method public hidebysig instance int32
+ PointerArithmetic5(void* p,
+ uint8* q,
+ int32 i) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.2
+ IL_0001: ldarg.3
+ IL_0002: add
+ IL_0003: ldind.u1
+ IL_0004: ldarg.1
+ IL_0005: ldind.u1
+ IL_0006: add
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerArithmetic5
+
+ .method public hidebysig instance int32
+ PointerSubtraction(int64* p,
+ int64* q) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: sub
+ IL_0003: ldc.i4.8
+ IL_0004: div
+ IL_0005: conv.i8
+ IL_0006: conv.i4
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerSubtraction
+
+ .method public hidebysig instance int64
+ PointerSubtractionLong(int64* p,
+ int64* q) cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: sub
+ IL_0003: ldc.i4.8
+ IL_0004: div
+ IL_0005: conv.i8
+ IL_0006: ret
+ } // end of method UnsafeCode::PointerSubtractionLong
+
+ .method public hidebysig instance int32
+ PointerSubtraction2(int64* p,
+ int16* q) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: sub
+ IL_0003: ldc.i4.1
+ IL_0004: div
+ IL_0005: conv.i8
+ IL_0006: conv.i4
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerSubtraction2
+
+ .method public hidebysig instance int32
+ PointerSubtraction3(void* p,
+ void* q) cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.1
+ IL_0001: ldarg.2
+ IL_0002: sub
+ IL_0003: ldc.i4.1
+ IL_0004: div
+ IL_0005: conv.i8
+ IL_0006: conv.i4
+ IL_0007: ret
+ } // end of method UnsafeCode::PointerSubtraction3
+
+ .method family hidebysig virtual instance void
+ Finalize() cil managed
+ {
+ .override [mscorlib]System.Object::Finalize
+ // Code size 22 (0x16)
+ .maxstack 2
+ .try
+ {
+ IL_0000: ldarg.0
+ IL_0001: ldarg.0
+ IL_0002: call instance int32* ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::get_NullPointer()
+ IL_0007: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassPointerAsRefParameter(int32*)
+ IL_000c: leave.s IL_0015
+
+ } // end .try
+ finally
+ {
+ IL_000e: ldarg.0
+ IL_000f: call instance void [mscorlib]System.Object::Finalize()
+ IL_0014: endfinally
+ } // end handler
+ IL_0015: ret
+ } // end of method UnsafeCode::Finalize
+
+ .method public hidebysig specialname rtspecialname
+ instance void .ctor() cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 8
+ IL_0000: ldarg.0
+ IL_0001: call instance void [mscorlib]System.Object::.ctor()
+ IL_0006: ret
+ } // end of method UnsafeCode::.ctor
+
+ .property instance int32* NullPointer()
+ {
+ .get instance int32* ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::get_NullPointer()
+ } // end of property UnsafeCode::NullPointer
+} // end of class ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode
+
+
+// =============================================================
+
+// *********** DISASSEMBLY COMPLETE ***********************
diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.roslyn.il b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.roslyn.il
new file mode 100644
index 000000000..8577e57aa
--- /dev/null
+++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/UnsafeCode.roslyn.il
@@ -0,0 +1,631 @@
+
+// Microsoft (R) .NET Framework IL Disassembler. Version 4.6.1055.0
+// Copyright (c) Microsoft Corporation. All rights reserved.
+
+
+
+// Metadata version: v4.0.30319
+.assembly extern mscorlib
+{
+ .publickeytoken = (B7 7A 5C 56 19 34 E0 89 ) // .z\V.4..
+ .ver 4:0:0:0
+}
+.assembly UnsafeCode
+{
+ .custom instance void [mscorlib]System.Runtime.CompilerServices.CompilationRelaxationsAttribute::.ctor(int32) = ( 01 00 08 00 00 00 00 00 )
+ .custom instance void [mscorlib]System.Runtime.CompilerServices.RuntimeCompatibilityAttribute::.ctor() = ( 01 00 01 00 54 02 16 57 72 61 70 4E 6F 6E 45 78 // ....T..WrapNonEx
+ 63 65 70 74 69 6F 6E 54 68 72 6F 77 73 01 ) // ceptionThrows.
+
+ // --- The following custom attribute is added automatically, do not uncomment -------
+ // .custom instance void [mscorlib]System.Diagnostics.DebuggableAttribute::.ctor(valuetype [mscorlib]System.Diagnostics.DebuggableAttribute/DebuggingModes) = ( 01 00 07 01 00 00 00 00 )
+
+ .permissionset reqmin
+ = {[mscorlib]System.Security.Permissions.SecurityPermissionAttribute = {property bool 'SkipVerification' = bool(true)}}
+ .hash algorithm 0x00008004
+ .ver 0:0:0:0
+}
+.module UnsafeCode.dll
+// MVID: {BCDFA7E7-0E94-44F0-8A8C-85049FECA738}
+.custom instance void [mscorlib]System.Security.UnverifiableCodeAttribute::.ctor() = ( 01 00 00 00 )
+.imagebase 0x10000000
+.file alignment 0x00000200
+.stackreserve 0x00100000
+.subsystem 0x0003 // WINDOWS_CUI
+.corflags 0x00000001 // ILONLY
+// Image base: 0x01330000
+
+
+// =============== CLASS MEMBERS DECLARATION ===================
+
+.class public auto ansi beforefieldinit ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode
+ extends [mscorlib]System.Object
+{
+ .class sequential ansi sealed nested private beforefieldinit SimpleStruct
+ extends [mscorlib]System.ValueType
+ {
+ .field public int32 X
+ .field public float64 Y
+ } // end of class SimpleStruct
+
+ .method public hidebysig specialname instance int32*
+ get_NullPointer() cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 1
+ .locals init (int32* V_0)
+ IL_0000: nop
+ IL_0001: ldc.i4.0
+ IL_0002: conv.u
+ IL_0003: stloc.0
+ IL_0004: br.s IL_0006
+
+ IL_0006: ldloc.0
+ IL_0007: ret
+ } // end of method UnsafeCode::get_NullPointer
+
+ .method public hidebysig instance int32*
+ PointerCast(int64* p) cil managed
+ {
+ // Code size 7 (0x7)
+ .maxstack 1
+ .locals init (int32* V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: stloc.0
+ IL_0003: br.s IL_0005
+
+ IL_0005: ldloc.0
+ IL_0006: ret
+ } // end of method UnsafeCode::PointerCast
+
+ .method public hidebysig instance int64
+ ConvertDoubleToLong(float64 d) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 1
+ .locals init (int64 V_0)
+ IL_0000: nop
+ IL_0001: ldarga.s d
+ IL_0003: conv.u
+ IL_0004: ldind.i8
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::ConvertDoubleToLong
+
+ .method public hidebysig instance float64
+ ConvertLongToDouble(int64 d) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 1
+ .locals init (float64 V_0)
+ IL_0000: nop
+ IL_0001: ldarga.s d
+ IL_0003: conv.u
+ IL_0004: ldind.r8
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::ConvertLongToDouble
+
+ .method public hidebysig instance int32
+ ConvertFloatToInt(float32 d) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 1
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarga.s d
+ IL_0003: conv.u
+ IL_0004: ldind.i4
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::ConvertFloatToInt
+
+ .method public hidebysig instance float32
+ ConvertIntToFloat(int32 d) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 1
+ .locals init (float32 V_0)
+ IL_0000: nop
+ IL_0001: ldarga.s d
+ IL_0003: conv.u
+ IL_0004: ldind.r4
+ IL_0005: stloc.0
+ IL_0006: br.s IL_0008
+
+ IL_0008: ldloc.0
+ IL_0009: ret
+ } // end of method UnsafeCode::ConvertIntToFloat
+
+ .method public hidebysig instance int32
+ PointerCasts() cil managed
+ {
+ // Code size 25 (0x19)
+ .maxstack 2
+ .locals init (int32 V_0,
+ int32 V_1)
+ IL_0000: nop
+ IL_0001: ldc.i4.0
+ IL_0002: stloc.0
+ IL_0003: ldloca.s V_0
+ IL_0005: conv.u
+ IL_0006: ldc.r4 0.5
+ IL_000b: stind.r4
+ IL_000c: ldloca.s V_0
+ IL_000e: conv.u
+ IL_000f: ldc.i4.3
+ IL_0010: add
+ IL_0011: ldc.i4.3
+ IL_0012: stind.i1
+ IL_0013: ldloc.0
+ IL_0014: stloc.1
+ IL_0015: br.s IL_0017
+
+ IL_0017: ldloc.1
+ IL_0018: ret
+ } // end of method UnsafeCode::PointerCasts
+
+ .method public hidebysig instance void
+ PassRefParameterAsPointer(int32& p) cil managed
+ {
+ // Code size 18 (0x12)
+ .maxstack 2
+ .locals init (int32& pinned V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: stloc.0
+ IL_0003: nop
+ IL_0004: ldarg.0
+ IL_0005: ldloc.0
+ IL_0006: conv.i
+ IL_0007: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassPointerAsRefParameter(int32*)
+ IL_000c: nop
+ IL_000d: nop
+ IL_000e: ldc.i4.0
+ IL_000f: conv.u
+ IL_0010: stloc.0
+ IL_0011: ret
+ } // end of method UnsafeCode::PassRefParameterAsPointer
+
+ .method public hidebysig instance void
+ PassPointerAsRefParameter(int32* p) cil managed
+ {
+ // Code size 10 (0xa)
+ .maxstack 8
+ IL_0000: nop
+ IL_0001: ldarg.0
+ IL_0002: ldarg.1
+ IL_0003: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassRefParameterAsPointer(int32&)
+ IL_0008: nop
+ IL_0009: ret
+ } // end of method UnsafeCode::PassPointerAsRefParameter
+
+ .method public hidebysig instance void
+ AddressInMultiDimensionalArray(float64[0...,0...] matrix) cil managed
+ {
+ // Code size 34 (0x22)
+ .maxstack 3
+ .locals init (float64& pinned V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldc.i4.1
+ IL_0003: ldc.i4.2
+ IL_0004: call instance float64& float64[0...,0...]::Address(int32,
+ int32)
+ IL_0009: stloc.0
+ IL_000a: nop
+ IL_000b: ldarg.0
+ IL_000c: ldloc.0
+ IL_000d: conv.i
+ IL_000e: call instance string ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PointerReferenceExpression(float64*)
+ IL_0013: pop
+ IL_0014: ldarg.0
+ IL_0015: ldloc.0
+ IL_0016: conv.i
+ IL_0017: call instance string ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PointerReferenceExpression(float64*)
+ IL_001c: pop
+ IL_001d: nop
+ IL_001e: ldc.i4.0
+ IL_001f: conv.u
+ IL_0020: stloc.0
+ IL_0021: ret
+ } // end of method UnsafeCode::AddressInMultiDimensionalArray
+
+ .method public hidebysig instance void
+ FixedStringAccess(string text) cil managed
+ {
+ // Code size 46 (0x2e)
+ .maxstack 2
+ .locals init (char* V_0,
+ string pinned V_1,
+ char* V_2,
+ bool V_3)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: stloc.1
+ IL_0003: ldloc.1
+ IL_0004: conv.i
+ IL_0005: stloc.0
+ IL_0006: ldloc.0
+ IL_0007: brfalse.s IL_0011
+
+ IL_0009: ldloc.0
+ IL_000a: call int32 [mscorlib]System.Runtime.CompilerServices.RuntimeHelpers::get_OffsetToStringData()
+ IL_000f: add
+ IL_0010: stloc.0
+ IL_0011: nop
+ IL_0012: ldloc.0
+ IL_0013: stloc.2
+ IL_0014: br.s IL_0020
+
+ IL_0016: nop
+ IL_0017: ldloc.2
+ IL_0018: ldc.i4.s 65
+ IL_001a: stind.i2
+ IL_001b: ldloc.2
+ IL_001c: ldc.i4.2
+ IL_001d: add
+ IL_001e: stloc.2
+ IL_001f: nop
+ IL_0020: ldloc.2
+ IL_0021: ldind.u2
+ IL_0022: ldc.i4.s 97
+ IL_0024: ceq
+ IL_0026: stloc.3
+ IL_0027: ldloc.3
+ IL_0028: brtrue.s IL_0016
+
+ IL_002a: nop
+ IL_002b: ldnull
+ IL_002c: stloc.1
+ IL_002d: ret
+ } // end of method UnsafeCode::FixedStringAccess
+
+ .method public hidebysig instance void
+ PutDoubleIntoLongArray1(int64[] 'array',
+ int32 index,
+ float64 val) cil managed
+ {
+ // Code size 39 (0x27)
+ .maxstack 3
+ .locals init (int64& pinned V_0,
+ int64[] V_1)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: dup
+ IL_0003: stloc.1
+ IL_0004: brfalse.s IL_000b
+
+ IL_0006: ldloc.1
+ IL_0007: ldlen
+ IL_0008: conv.i4
+ IL_0009: brtrue.s IL_0010
+
+ IL_000b: ldc.i4.0
+ IL_000c: conv.u
+ IL_000d: stloc.0
+ IL_000e: br.s IL_0018
+
+ IL_0010: ldloc.1
+ IL_0011: ldc.i4.0
+ IL_0012: ldelema [mscorlib]System.Int64
+ IL_0017: stloc.0
+ IL_0018: nop
+ IL_0019: ldloc.0
+ IL_001a: conv.i
+ IL_001b: ldarg.2
+ IL_001c: conv.i
+ IL_001d: ldc.i4.8
+ IL_001e: mul
+ IL_001f: add
+ IL_0020: ldarg.3
+ IL_0021: stind.r8
+ IL_0022: nop
+ IL_0023: ldc.i4.0
+ IL_0024: conv.u
+ IL_0025: stloc.0
+ IL_0026: ret
+ } // end of method UnsafeCode::PutDoubleIntoLongArray1
+
+ .method public hidebysig instance void
+ PutDoubleIntoLongArray2(int64[] 'array',
+ int32 index,
+ float64 val) cil managed
+ {
+ // Code size 19 (0x13)
+ .maxstack 2
+ .locals init (int64& pinned V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: ldelema [mscorlib]System.Int64
+ IL_0008: stloc.0
+ IL_0009: nop
+ IL_000a: ldloc.0
+ IL_000b: conv.i
+ IL_000c: ldarg.3
+ IL_000d: stind.r8
+ IL_000e: nop
+ IL_000f: ldc.i4.0
+ IL_0010: conv.u
+ IL_0011: stloc.0
+ IL_0012: ret
+ } // end of method UnsafeCode::PutDoubleIntoLongArray2
+
+ .method public hidebysig instance string
+ PointerReferenceExpression(float64* d) cil managed
+ {
+ // Code size 12 (0xc)
+ .maxstack 1
+ .locals init (string V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: call instance string [mscorlib]System.Double::ToString()
+ IL_0007: stloc.0
+ IL_0008: br.s IL_000a
+
+ IL_000a: ldloc.0
+ IL_000b: ret
+ } // end of method UnsafeCode::PointerReferenceExpression
+
+ .method public hidebysig instance string
+ PointerReferenceExpression2(int64 addr) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 1
+ .locals init (string V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: conv.u
+ IL_0003: call instance string [mscorlib]System.Int32::ToString()
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerReferenceExpression2
+
+ .method public hidebysig instance int32*
+ PointerArithmetic(int32* p) cil managed
+ {
+ // Code size 12 (0xc)
+ .maxstack 3
+ .locals init (int32* V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldc.i4.2
+ IL_0003: conv.i
+ IL_0004: ldc.i4.4
+ IL_0005: mul
+ IL_0006: add
+ IL_0007: stloc.0
+ IL_0008: br.s IL_000a
+
+ IL_000a: ldloc.0
+ IL_000b: ret
+ } // end of method UnsafeCode::PointerArithmetic
+
+ .method public hidebysig instance int64*
+ PointerArithmetic2(int64* p,
+ int32 y,
+ int32 x) cil managed
+ {
+ // Code size 12 (0xc)
+ .maxstack 2
+ .locals init (int64* V_0)
+ IL_0000: nop
+ IL_0001: ldc.i4.3
+ IL_0002: conv.i
+ IL_0003: ldc.i4.8
+ IL_0004: mul
+ IL_0005: ldarg.1
+ IL_0006: add
+ IL_0007: stloc.0
+ IL_0008: br.s IL_000a
+
+ IL_000a: ldloc.0
+ IL_000b: ret
+ } // end of method UnsafeCode::PointerArithmetic2
+
+ .method public hidebysig instance int64*
+ PointerArithmetic3(int64* p) cil managed
+ {
+ // Code size 9 (0x9)
+ .maxstack 2
+ .locals init (int64* V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldc.i4.3
+ IL_0003: add
+ IL_0004: stloc.0
+ IL_0005: br.s IL_0007
+
+ IL_0007: ldloc.0
+ IL_0008: ret
+ } // end of method UnsafeCode::PointerArithmetic3
+
+ .method public hidebysig instance int64*
+ PointerArithmetic4(void* p) cil managed
+ {
+ // Code size 9 (0x9)
+ .maxstack 2
+ .locals init (int64* V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldc.i4.3
+ IL_0003: add
+ IL_0004: stloc.0
+ IL_0005: br.s IL_0007
+
+ IL_0007: ldloc.0
+ IL_0008: ret
+ } // end of method UnsafeCode::PointerArithmetic4
+
+ .method public hidebysig instance int32
+ PointerArithmetic5(void* p,
+ uint8* q,
+ int32 i) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.2
+ IL_0002: ldarg.3
+ IL_0003: add
+ IL_0004: ldind.u1
+ IL_0005: ldarg.1
+ IL_0006: ldind.u1
+ IL_0007: add
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerArithmetic5
+
+ .method public hidebysig instance int32
+ PointerSubtraction(int64* p,
+ int64* q) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: sub
+ IL_0004: ldc.i4.8
+ IL_0005: div
+ IL_0006: conv.i8
+ IL_0007: conv.i4
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerSubtraction
+
+ .method public hidebysig instance int64
+ PointerSubtractionLong(int64* p,
+ int64* q) cil managed
+ {
+ // Code size 12 (0xc)
+ .maxstack 2
+ .locals init (int64 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: sub
+ IL_0004: ldc.i4.8
+ IL_0005: div
+ IL_0006: conv.i8
+ IL_0007: stloc.0
+ IL_0008: br.s IL_000a
+
+ IL_000a: ldloc.0
+ IL_000b: ret
+ } // end of method UnsafeCode::PointerSubtractionLong
+
+ .method public hidebysig instance int32
+ PointerSubtraction2(int64* p,
+ int16* q) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: sub
+ IL_0004: ldc.i4.1
+ IL_0005: div
+ IL_0006: conv.i8
+ IL_0007: conv.i4
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerSubtraction2
+
+ .method public hidebysig instance int32
+ PointerSubtraction3(void* p,
+ void* q) cil managed
+ {
+ // Code size 13 (0xd)
+ .maxstack 2
+ .locals init (int32 V_0)
+ IL_0000: nop
+ IL_0001: ldarg.1
+ IL_0002: ldarg.2
+ IL_0003: sub
+ IL_0004: ldc.i4.1
+ IL_0005: div
+ IL_0006: conv.i8
+ IL_0007: conv.i4
+ IL_0008: stloc.0
+ IL_0009: br.s IL_000b
+
+ IL_000b: ldloc.0
+ IL_000c: ret
+ } // end of method UnsafeCode::PointerSubtraction3
+
+ .method family hidebysig virtual instance void
+ Finalize() cil managed
+ {
+ .override [mscorlib]System.Object::Finalize
+ // Code size 26 (0x1a)
+ .maxstack 2
+ IL_0000: nop
+ .try
+ {
+ IL_0001: nop
+ IL_0002: ldarg.0
+ IL_0003: ldarg.0
+ IL_0004: call instance int32* ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::get_NullPointer()
+ IL_0009: call instance void ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::PassPointerAsRefParameter(int32*)
+ IL_000e: nop
+ IL_000f: leave.s IL_0019
+
+ } // end .try
+ finally
+ {
+ IL_0011: ldarg.0
+ IL_0012: call instance void [mscorlib]System.Object::Finalize()
+ IL_0017: nop
+ IL_0018: endfinally
+ } // end handler
+ IL_0019: ret
+ } // end of method UnsafeCode::Finalize
+
+ .method public hidebysig specialname rtspecialname
+ instance void .ctor() cil managed
+ {
+ // Code size 8 (0x8)
+ .maxstack 8
+ IL_0000: ldarg.0
+ IL_0001: call instance void [mscorlib]System.Object::.ctor()
+ IL_0006: nop
+ IL_0007: ret
+ } // end of method UnsafeCode::.ctor
+
+ .property instance int32* NullPointer()
+ {
+ .get instance int32* ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode::get_NullPointer()
+ } // end of property UnsafeCode::NullPointer
+} // end of class ICSharpCode.Decompiler.Tests.TestCases.Pretty.UnsafeCode
+
+
+// =============================================================
+
+// *********** DISASSEMBLY COMPLETE ***********************
diff --git a/ICSharpCode.Decompiler/IL/ControlFlow/DetectPinnedRegions.cs b/ICSharpCode.Decompiler/IL/ControlFlow/DetectPinnedRegions.cs
index 30b7dea39..a06218a54 100644
--- a/ICSharpCode.Decompiler/IL/ControlFlow/DetectPinnedRegions.cs
+++ b/ICSharpCode.Decompiler/IL/ControlFlow/DetectPinnedRegions.cs
@@ -337,6 +337,7 @@ namespace ICSharpCode.Decompiler.IL.ControlFlow
new PointerType(((ByReferenceType)oldVar.Type).ElementType),
oldVar.Index);
newVar.Name = oldVar.Name;
+ newVar.HasGeneratedName = oldVar.HasGeneratedName;
oldVar.Function.Variables.Add(newVar);
ReplacePinnedVar(oldVar, newVar, pinnedRegion);
} else if (pinnedRegion.Variable.Type.IsKnownType(KnownTypeCode.String)) {
@@ -383,6 +384,7 @@ namespace ICSharpCode.Decompiler.IL.ControlFlow
if (nativeVar.Kind == VariableKind.Local) {
newVar = new ILVariable(VariableKind.PinnedLocal, nativeVar.Type, nativeVar.Index);
newVar.Name = nativeVar.Name;
+ newVar.HasGeneratedName = nativeVar.HasGeneratedName;
nativeVar.Function.Variables.Add(newVar);
ReplacePinnedVar(nativeVar, newVar, pinnedRegion);
} else {