diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.cs b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.cs index f3ad3c213..da8f4b369 100644 --- a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.cs +++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.cs @@ -16,6 +16,7 @@ // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER // DEALINGS IN THE SOFTWARE. using System; +using System.Collections.Generic; namespace ICSharpCode.Decompiler.Tests.TestCases.Pretty { @@ -96,5 +97,19 @@ namespace ICSharpCode.Decompiler.Tests.TestCases.Pretty { return new T[size1, size2]; } + + public Type[] TestTypeOf() + { + return new Type[8] { + typeof(int), + typeof(int[]), + typeof(GenericClass<>), + typeof(GenericClass), + typeof(GenericClass), + typeof(Dictionary<, >), + typeof(List.Enumerator), + typeof(List<>.Enumerator) + }; + } } } diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.il b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.il index 7dedb9a29..09dd68e77 100644 --- a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.il +++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.il @@ -304,6 +304,65 @@ IL_000c: ret } // end of method Generics::NewArray + .method public hidebysig instance class [mscorlib]System.Type[] + TestTypeOf() cil managed + { + // Code size 118 (0x76) + .maxstack 3 + .locals init (class [mscorlib]System.Type[] V_0, + class [mscorlib]System.Type[] V_1) + IL_0000: nop + IL_0001: ldc.i4.8 + IL_0002: newarr [mscorlib]System.Type + IL_0007: stloc.1 + IL_0008: ldloc.1 + IL_0009: ldc.i4.0 + IL_000a: ldtoken [mscorlib]System.Int32 + IL_000f: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0014: stelem.ref + IL_0015: ldloc.1 + IL_0016: ldc.i4.1 + IL_0017: ldtoken int32[] + IL_001c: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0021: stelem.ref + IL_0022: ldloc.1 + IL_0023: ldc.i4.2 + IL_0024: ldtoken ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0029: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_002e: stelem.ref + IL_002f: ldloc.1 + IL_0030: ldc.i4.3 + IL_0031: ldtoken class ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0036: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_003b: stelem.ref + IL_003c: ldloc.1 + IL_003d: ldc.i4.4 + IL_003e: ldtoken class ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0043: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0048: stelem.ref + IL_0049: ldloc.1 + IL_004a: ldc.i4.5 + IL_004b: ldtoken [mscorlib]System.Collections.Generic.Dictionary`2 + IL_0050: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0055: stelem.ref + IL_0056: ldloc.1 + IL_0057: ldc.i4.6 + IL_0058: ldtoken valuetype [mscorlib]System.Collections.Generic.List`1/Enumerator + IL_005d: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0062: stelem.ref + IL_0063: ldloc.1 + IL_0064: ldc.i4.7 + IL_0065: ldtoken [mscorlib]System.Collections.Generic.List`1/Enumerator + IL_006a: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_006f: stelem.ref + IL_0070: ldloc.1 + IL_0071: stloc.0 + IL_0072: br.s IL_0074 + + IL_0074: ldloc.0 + IL_0075: ret + } // end of method Generics::TestTypeOf + .method public hidebysig specialname rtspecialname instance void .ctor() cil managed { diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.opt.il b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.opt.il index af5b2d1a4..d8e83a93d 100644 --- a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.opt.il +++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.opt.il @@ -231,6 +231,59 @@ IL_0007: ret } // end of method Generics::NewArray + .method public hidebysig instance class [mscorlib]System.Type[] + TestTypeOf() cil managed + { + // Code size 113 (0x71) + .maxstack 3 + .locals init (class [mscorlib]System.Type[] V_0) + IL_0000: ldc.i4.8 + IL_0001: newarr [mscorlib]System.Type + IL_0006: stloc.0 + IL_0007: ldloc.0 + IL_0008: ldc.i4.0 + IL_0009: ldtoken [mscorlib]System.Int32 + IL_000e: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0013: stelem.ref + IL_0014: ldloc.0 + IL_0015: ldc.i4.1 + IL_0016: ldtoken int32[] + IL_001b: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0020: stelem.ref + IL_0021: ldloc.0 + IL_0022: ldc.i4.2 + IL_0023: ldtoken ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0028: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_002d: stelem.ref + IL_002e: ldloc.0 + IL_002f: ldc.i4.3 + IL_0030: ldtoken class ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0035: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_003a: stelem.ref + IL_003b: ldloc.0 + IL_003c: ldc.i4.4 + IL_003d: ldtoken class ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0042: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0047: stelem.ref + IL_0048: ldloc.0 + IL_0049: ldc.i4.5 + IL_004a: ldtoken [mscorlib]System.Collections.Generic.Dictionary`2 + IL_004f: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0054: stelem.ref + IL_0055: ldloc.0 + IL_0056: ldc.i4.6 + IL_0057: ldtoken valuetype [mscorlib]System.Collections.Generic.List`1/Enumerator + IL_005c: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0061: stelem.ref + IL_0062: ldloc.0 + IL_0063: ldc.i4.7 + IL_0064: ldtoken [mscorlib]System.Collections.Generic.List`1/Enumerator + IL_0069: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_006e: stelem.ref + IL_006f: ldloc.0 + IL_0070: ret + } // end of method Generics::TestTypeOf + .method public hidebysig specialname rtspecialname instance void .ctor() cil managed { diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.opt.roslyn.il b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.opt.roslyn.il index 3112d5a7a..86ef337db 100644 --- a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.opt.roslyn.il +++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.opt.roslyn.il @@ -222,6 +222,56 @@ IL_0007: ret } // end of method Generics::NewArray + .method public hidebysig instance class [mscorlib]System.Type[] + TestTypeOf() cil managed + { + // Code size 111 (0x6f) + .maxstack 4 + IL_0000: ldc.i4.8 + IL_0001: newarr [mscorlib]System.Type + IL_0006: dup + IL_0007: ldc.i4.0 + IL_0008: ldtoken [mscorlib]System.Int32 + IL_000d: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0012: stelem.ref + IL_0013: dup + IL_0014: ldc.i4.1 + IL_0015: ldtoken int32[] + IL_001a: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_001f: stelem.ref + IL_0020: dup + IL_0021: ldc.i4.2 + IL_0022: ldtoken ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0027: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_002c: stelem.ref + IL_002d: dup + IL_002e: ldc.i4.3 + IL_002f: ldtoken class ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0034: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0039: stelem.ref + IL_003a: dup + IL_003b: ldc.i4.4 + IL_003c: ldtoken class ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0041: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0046: stelem.ref + IL_0047: dup + IL_0048: ldc.i4.5 + IL_0049: ldtoken [mscorlib]System.Collections.Generic.Dictionary`2 + IL_004e: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0053: stelem.ref + IL_0054: dup + IL_0055: ldc.i4.6 + IL_0056: ldtoken valuetype [mscorlib]System.Collections.Generic.List`1/Enumerator + IL_005b: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0060: stelem.ref + IL_0061: dup + IL_0062: ldc.i4.7 + IL_0063: ldtoken [mscorlib]System.Collections.Generic.List`1/Enumerator + IL_0068: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_006d: stelem.ref + IL_006e: ret + } // end of method Generics::TestTypeOf + .method public hidebysig specialname rtspecialname instance void .ctor() cil managed { diff --git a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.roslyn.il b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.roslyn.il index a433f6f70..fb056af8f 100644 --- a/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.roslyn.il +++ b/ICSharpCode.Decompiler.Tests/TestCases/Pretty/Generics.roslyn.il @@ -298,6 +298,62 @@ IL_000c: ret } // end of method Generics::NewArray + .method public hidebysig instance class [mscorlib]System.Type[] + TestTypeOf() cil managed + { + // Code size 116 (0x74) + .maxstack 4 + .locals init (class [mscorlib]System.Type[] V_0) + IL_0000: nop + IL_0001: ldc.i4.8 + IL_0002: newarr [mscorlib]System.Type + IL_0007: dup + IL_0008: ldc.i4.0 + IL_0009: ldtoken [mscorlib]System.Int32 + IL_000e: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0013: stelem.ref + IL_0014: dup + IL_0015: ldc.i4.1 + IL_0016: ldtoken int32[] + IL_001b: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0020: stelem.ref + IL_0021: dup + IL_0022: ldc.i4.2 + IL_0023: ldtoken ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0028: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_002d: stelem.ref + IL_002e: dup + IL_002f: ldc.i4.3 + IL_0030: ldtoken class ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0035: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_003a: stelem.ref + IL_003b: dup + IL_003c: ldc.i4.4 + IL_003d: ldtoken class ICSharpCode.Decompiler.Tests.TestCases.Pretty.Generics/GenericClass`1 + IL_0042: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0047: stelem.ref + IL_0048: dup + IL_0049: ldc.i4.5 + IL_004a: ldtoken [mscorlib]System.Collections.Generic.Dictionary`2 + IL_004f: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0054: stelem.ref + IL_0055: dup + IL_0056: ldc.i4.6 + IL_0057: ldtoken valuetype [mscorlib]System.Collections.Generic.List`1/Enumerator + IL_005c: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_0061: stelem.ref + IL_0062: dup + IL_0063: ldc.i4.7 + IL_0064: ldtoken [mscorlib]System.Collections.Generic.List`1/Enumerator + IL_0069: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) + IL_006e: stelem.ref + IL_006f: stloc.0 + IL_0070: br.s IL_0072 + + IL_0072: ldloc.0 + IL_0073: ret + } // end of method Generics::TestTypeOf + .method public hidebysig specialname rtspecialname instance void .ctor() cil managed { diff --git a/ICSharpCode.Decompiler/CSharp/OutputVisitor/CSharpAmbience.cs b/ICSharpCode.Decompiler/CSharp/OutputVisitor/CSharpAmbience.cs index a47250675..775cff0b0 100644 --- a/ICSharpCode.Decompiler/CSharp/OutputVisitor/CSharpAmbience.cs +++ b/ICSharpCode.Decompiler/CSharp/OutputVisitor/CSharpAmbience.cs @@ -184,6 +184,7 @@ namespace ICSharpCode.Decompiler.CSharp.OutputVisitor { TypeSystemAstBuilder astBuilder = new TypeSystemAstBuilder(); astBuilder.AddTypeReferenceAnnotations = true; + astBuilder.ShowTypeParametersForUnboundTypes = true; astBuilder.ShowModifiers = (ConversionFlags & ConversionFlags.ShowModifiers) == ConversionFlags.ShowModifiers; astBuilder.ShowAccessibility = (ConversionFlags & ConversionFlags.ShowAccessibility) == ConversionFlags.ShowAccessibility; astBuilder.AlwaysUseShortTypeNames = (ConversionFlags & ConversionFlags.UseFullyQualifiedTypeNames) != ConversionFlags.UseFullyQualifiedTypeNames; diff --git a/ICSharpCode.Decompiler/CSharp/Syntax/TypeSystemAstBuilder.cs b/ICSharpCode.Decompiler/CSharp/Syntax/TypeSystemAstBuilder.cs index 4f1957bcd..6c04e4b84 100644 --- a/ICSharpCode.Decompiler/CSharp/Syntax/TypeSystemAstBuilder.cs +++ b/ICSharpCode.Decompiler/CSharp/Syntax/TypeSystemAstBuilder.cs @@ -111,6 +111,12 @@ namespace ICSharpCode.Decompiler.CSharp.Syntax /// The default value is true. /// public bool ShowTypeParameters { get; set; } + + /// + /// Controls whether type parameter names are shown for unbound types. + /// The default value is false. + /// + public bool ShowTypeParametersForUnboundTypes { get; set; } /// /// Controls whether constraints on type parameter declarations are shown. @@ -262,6 +268,8 @@ namespace ICSharpCode.Decompiler.CSharp.Syntax return astType; } if (type is ITypeDefinition typeDef) { + if (ShowTypeParametersForUnboundTypes) + return ConvertTypeHelper(typeDef, typeDef.TypeArguments); if (typeDef.TypeParameterCount > 0) { // Unbound type IType[] typeArguments = new IType[typeDef.TypeParameterCount]; @@ -272,6 +280,7 @@ namespace ICSharpCode.Decompiler.CSharp.Syntax } else { return ConvertTypeHelper(typeDef, EmptyList.Instance); } + } return new SimpleType(type.Name); }