diff --git a/ICSharpCode.Decompiler.Tests/TestCases/ILPretty/Issue3729.cs b/ICSharpCode.Decompiler.Tests/TestCases/ILPretty/Issue3729.cs index 4ac1684c3..146cba9fb 100644 --- a/ICSharpCode.Decompiler.Tests/TestCases/ILPretty/Issue3729.cs +++ b/ICSharpCode.Decompiler.Tests/TestCases/ILPretty/Issue3729.cs @@ -46,7 +46,7 @@ namespace ICSharpCode.Decompiler.Tests.TestCases.ILPretty public void TestArrayElemCtor() { //IL_000f: Unknown result type (might be due to invalid IL or missing references) - MyStruct[] array = (MyStruct[])(object)new MyStruct[1] { + MyStruct[] array = new MyStruct[1] { new MyStruct(7) }; } diff --git a/ICSharpCode.Decompiler/TypeSystem/Implementation/UnknownType.cs b/ICSharpCode.Decompiler/TypeSystem/Implementation/UnknownType.cs index a39dcd695..eab3cd464 100644 --- a/ICSharpCode.Decompiler/TypeSystem/Implementation/UnknownType.cs +++ b/ICSharpCode.Decompiler/TypeSystem/Implementation/UnknownType.cs @@ -117,6 +117,22 @@ namespace ICSharpCode.Decompiler.TypeSystem.Implementation return new NullabilityAnnotatedType(this, nullability); } + /// + /// Returns this type without the knowledge whether it is a reference type. + /// + /// + /// Whether an unresolvable type is a reference type is not a property of the type, but of + /// the metadata that mentioned it: a signature spelling it `valuetype T` yields false, a + /// bare TypeRef yields null. Two such spellings of the same missing type must still compare + /// equal after type erasure, so NormalizeTypeVisitor drops the flag before comparing. + /// + internal UnknownType WithoutReferenceTypeKnowledge() + { + if (isReferenceType == null) + return this; + return new UnknownType(fullTypeName); + } + public override int GetHashCode() { return (namespaceKnown ? 812571 : 12651) ^ fullTypeName.GetHashCode(); diff --git a/ICSharpCode.Decompiler/TypeSystem/NormalizeTypeVisitor.cs b/ICSharpCode.Decompiler/TypeSystem/NormalizeTypeVisitor.cs index 7df9c4871..a1eafe028 100644 --- a/ICSharpCode.Decompiler/TypeSystem/NormalizeTypeVisitor.cs +++ b/ICSharpCode.Decompiler/TypeSystem/NormalizeTypeVisitor.cs @@ -97,6 +97,13 @@ namespace ICSharpCode.Decompiler.TypeSystem } } + public override IType VisitOtherType(IType type) + { + if (type is UnknownType unknownType) + return unknownType.WithoutReferenceTypeKnowledge(); + return base.VisitOtherType(type); + } + public override IType VisitTypeDefinition(ITypeDefinition type) { switch (type.KnownTypeCode)