Browse Source

Remove parent pointer from ITypeParameter and enable sharing type parameters.

newNRvisualizers
Daniel Grunwald 15 years ago
parent
commit
b8330bebd6
  1. 8
      ICSharpCode.NRefactory.Tests/CSharp/Resolver/OverloadResolutionTests.cs
  2. 2
      ICSharpCode.NRefactory.Tests/TypeSystem/GetAllBaseTypesTest.cs
  3. 25
      ICSharpCode.NRefactory.Tests/TypeSystem/TestInterningProvider.cs
  4. 10
      ICSharpCode.NRefactory.Tests/TypeSystem/TypeSystemTests.cs
  5. 2
      ICSharpCode.NRefactory/CSharp/Resolver/ResolveVisitor.cs
  6. 16
      ICSharpCode.NRefactory/CSharp/Resolver/TypeInference.cs
  7. 14
      ICSharpCode.NRefactory/TypeSystem/CecilLoader.cs
  8. 48
      ICSharpCode.NRefactory/TypeSystem/ITypeParameter.cs
  9. 90
      ICSharpCode.NRefactory/TypeSystem/Implementation/DefaultTypeParameter.cs
  10. 2
      ICSharpCode.NRefactory/TypeSystem/Implementation/MethodTypeParameterSubstitution.cs
  11. 2
      ICSharpCode.NRefactory/TypeSystem/ParameterizedType.cs

8
ICSharpCode.NRefactory.Tests/CSharp/Resolver/OverloadResolutionTests.cs

@ -138,7 +138,7 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
// static void Foo<T>(T? ignored = default(T?)) where T : struct // static void Foo<T>(T? ignored = default(T?)) where T : struct
var m1 = MakeMethod(); var m1 = MakeMethod();
m1.TypeParameters.Add(new DefaultTypeParameter(m1, 0, "T") { HasValueTypeConstraint = true }); m1.TypeParameters.Add(new DefaultTypeParameter(EntityType.Method, 0, "T") { HasValueTypeConstraint = true });
m1.Parameters.Add(MakeOptionalParameter( m1.Parameters.Add(MakeOptionalParameter(
NullableType.Create(m1.TypeParameters[0], context), NullableType.Create(m1.TypeParameters[0], context),
"ignored" "ignored"
@ -146,12 +146,12 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
// class ClassConstraint<T> where T : class {} // class ClassConstraint<T> where T : class {}
DefaultTypeDefinition classConstraint = new DefaultTypeDefinition(dummyClass, "ClassConstraint"); DefaultTypeDefinition classConstraint = new DefaultTypeDefinition(dummyClass, "ClassConstraint");
classConstraint.TypeParameters.Add(new DefaultTypeParameter(classConstraint, 0, "T") { HasReferenceTypeConstraint = true }); classConstraint.TypeParameters.Add(new DefaultTypeParameter(EntityType.TypeDefinition, 0, "T") { HasReferenceTypeConstraint = true });
// static void Foo<T>(ClassConstraint<T> ignored = default(ClassConstraint<T>)) // static void Foo<T>(ClassConstraint<T> ignored = default(ClassConstraint<T>))
// where T : class // where T : class
var m2 = MakeMethod(); var m2 = MakeMethod();
m2.TypeParameters.Add(new DefaultTypeParameter(m2, 0, "T") { HasReferenceTypeConstraint = true }); m2.TypeParameters.Add(new DefaultTypeParameter(EntityType.Method, 0, "T") { HasReferenceTypeConstraint = true });
m2.Parameters.Add(MakeOptionalParameter( m2.Parameters.Add(MakeOptionalParameter(
new ParameterizedType(classConstraint, new[] { m2.TypeParameters[0] }), new ParameterizedType(classConstraint, new[] { m2.TypeParameters[0] }),
"ignored" "ignored"
@ -159,7 +159,7 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
// static void Foo<T>() // static void Foo<T>()
var m3 = MakeMethod(); var m3 = MakeMethod();
m3.TypeParameters.Add(new DefaultTypeParameter(m3, 0, "T")); m3.TypeParameters.Add(new DefaultTypeParameter(EntityType.Method, 0, "T"));
// Call: Foo<int>(); // Call: Foo<int>();
OverloadResolution o; OverloadResolution o;

2
ICSharpCode.NRefactory.Tests/TypeSystem/GetAllBaseTypesTest.cs

@ -84,7 +84,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
{ {
// class C<X> : C<C<X>> {} // class C<X> : C<C<X>> {}
DefaultTypeDefinition c = new DefaultTypeDefinition(mscorlib, string.Empty, "C"); DefaultTypeDefinition c = new DefaultTypeDefinition(mscorlib, string.Empty, "C");
c.TypeParameters.Add(new DefaultTypeParameter(c, 0, "X")); c.TypeParameters.Add(new DefaultTypeParameter(EntityType.TypeDefinition, 0, "X"));
c.BaseTypes.Add(new ParameterizedType(c, new [] { new ParameterizedType(c, new [] { c.TypeParameters[0] }) })); c.BaseTypes.Add(new ParameterizedType(c, new [] { new ParameterizedType(c, new [] { c.TypeParameters[0] }) }));
Assert.AreEqual(new [] { c }, c.GetAllBaseTypes(context).ToArray()); Assert.AreEqual(new [] { c }, c.GetAllBaseTypes(context).ToArray());
} }

25
ICSharpCode.NRefactory.Tests/TypeSystem/TestInterningProvider.cs

@ -140,15 +140,36 @@ namespace ICSharpCode.NRefactory.TypeSystem
} }
} }
IProjectContent[] LoadProjects(CecilLoader loader)
{
const string dir = @"C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.0\";
return new IProjectContent[] {
loader.LoadAssemblyFile(dir + "mscorlib.dll"),
loader.LoadAssemblyFile(dir + "System.dll"),
loader.LoadAssemblyFile(dir + "System.Core.dll"),
loader.LoadAssemblyFile(dir + "System.Xml.dll"),
loader.LoadAssemblyFile(dir + "System.Xml.Linq.dll"),
loader.LoadAssemblyFile(dir + "System.Data.dll"),
loader.LoadAssemblyFile(dir + "System.Drawing.dll"),
loader.LoadAssemblyFile(dir + "System.Windows.Forms.dll"),
loader.LoadAssemblyFile(dir + "WindowsBase.dll"),
loader.LoadAssemblyFile(dir + "PresentationCore.dll"),
loader.LoadAssemblyFile(dir + "PresentationFramework.dll")
};
}
[Test] [Test]
public void PrintStatistics() public void PrintStatistics()
{ {
long startMemory = GC.GetTotalMemory(true); long startMemory = GC.GetTotalMemory(true);
IProjectContent pc = new CecilLoader().LoadAssemblyFile(typeof(object).Assembly.Location); IProjectContent[] pc = LoadProjects(new CecilLoader());
long memoryWithFullPC = GC.GetTotalMemory(true) - startMemory; long memoryWithFullPC = GC.GetTotalMemory(true) - startMemory;
InterningProvider p = new InterningProvider(); InterningProvider p = new InterningProvider();
p.InternProject(pc); CecilLoader loader = new CecilLoader();
loader.InterningProvider = p;
pc = LoadProjects(loader);
PrintStatistics(p); PrintStatistics(p);
loader = null;
p = null; p = null;
long memoryWithInternedPC = GC.GetTotalMemory(true) - startMemory; long memoryWithInternedPC = GC.GetTotalMemory(true) - startMemory;
GC.KeepAlive(pc); GC.KeepAlive(pc);

10
ICSharpCode.NRefactory.Tests/TypeSystem/TypeSystemTests.cs

@ -134,8 +134,8 @@ namespace ICSharpCode.NRefactory.TypeSystem
public void TestClassTypeParameters() public void TestClassTypeParameters()
{ {
var testClass = testCasePC.GetClass(typeof(GenericClass<,>)); var testClass = testCasePC.GetClass(typeof(GenericClass<,>));
Assert.AreSame(testClass, testClass.TypeParameters[0].ParentClass); Assert.AreEqual(EntityType.TypeDefinition, testClass.TypeParameters[0].OwnerType);
Assert.AreSame(testClass, testClass.TypeParameters[1].ParentClass); Assert.AreEqual(EntityType.TypeDefinition, testClass.TypeParameters[1].OwnerType);
Assert.AreSame(testClass.TypeParameters[1], testClass.TypeParameters[0].Constraints[0].Resolve(ctx)); Assert.AreSame(testClass.TypeParameters[1], testClass.TypeParameters[0].Constraints[0].Resolve(ctx));
} }
@ -147,8 +147,8 @@ namespace ICSharpCode.NRefactory.TypeSystem
IMethod m = testClass.Methods.Single(me => me.Name == "TestMethod"); IMethod m = testClass.Methods.Single(me => me.Name == "TestMethod");
Assert.AreEqual("K", m.TypeParameters[0].Name); Assert.AreEqual("K", m.TypeParameters[0].Name);
Assert.AreEqual("V", m.TypeParameters[1].Name); Assert.AreEqual("V", m.TypeParameters[1].Name);
Assert.AreSame(m, m.TypeParameters[0].ParentMethod); Assert.AreEqual(EntityType.Method, m.TypeParameters[0].OwnerType);
Assert.AreSame(m, m.TypeParameters[1].ParentMethod); Assert.AreEqual(EntityType.Method, m.TypeParameters[1].OwnerType);
Assert.AreEqual("System.IComparable`1[[``1]]", m.TypeParameters[0].Constraints[0].Resolve(ctx).ReflectionName); Assert.AreEqual("System.IComparable`1[[``1]]", m.TypeParameters[0].Constraints[0].Resolve(ctx).ReflectionName);
Assert.AreSame(m.TypeParameters[0], m.TypeParameters[1].Constraints[0].Resolve(ctx)); Assert.AreSame(m.TypeParameters[0], m.TypeParameters[1].Constraints[0].Resolve(ctx));
@ -161,7 +161,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
IMethod m = testClass.Methods.Single(me => me.Name == "GetIndex"); IMethod m = testClass.Methods.Single(me => me.Name == "GetIndex");
Assert.AreEqual("T", m.TypeParameters[0].Name); Assert.AreEqual("T", m.TypeParameters[0].Name);
Assert.AreSame(m, m.TypeParameters[0].ParentMethod); Assert.AreEqual(EntityType.Method, m.TypeParameters[0].OwnerType);
ParameterizedType constraint = (ParameterizedType)m.TypeParameters[0].Constraints[0].Resolve(ctx); ParameterizedType constraint = (ParameterizedType)m.TypeParameters[0].Constraints[0].Resolve(ctx);
Assert.AreEqual("IEquatable", constraint.Name); Assert.AreEqual("IEquatable", constraint.Name);

2
ICSharpCode.NRefactory/CSharp/Resolver/ResolveVisitor.cs

@ -497,7 +497,7 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
throw new NotImplementedException(); throw new NotImplementedException();
} }
public object VisitUndocumentedExpression(UndocumentedExpression undocumentedExpression, object data) public override ResolveResult VisitUndocumentedExpression(UndocumentedExpression undocumentedExpression, object data)
{ {
// TODO: ? // TODO: ?
ScanChildren(undocumentedExpression); ScanChildren(undocumentedExpression);

16
ICSharpCode.NRefactory/CSharp/Resolver/TypeInference.cs

@ -712,16 +712,8 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
get { return EmptyList<IAttribute>.Instance; } get { return EmptyList<IAttribute>.Instance; }
} }
IEntity ITypeParameter.Parent { EntityType ITypeParameter.OwnerType {
get { throw new NotSupportedException(); } get { return EntityType.Method; }
}
IMethod ITypeParameter.ParentMethod {
get { throw new NotSupportedException(); }
}
ITypeDefinition ITypeParameter.ParentClass {
get { throw new NotSupportedException(); }
} }
IList<ITypeReference> ITypeParameter.Constraints { IList<ITypeReference> ITypeParameter.Constraints {
@ -759,6 +751,10 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
void IFreezable.Freeze() void IFreezable.Freeze()
{ {
} }
DomRegion ITypeParameter.Region {
get { return DomRegion.Empty; }
}
} }
#endregion #endregion

14
ICSharpCode.NRefactory/TypeSystem/CecilLoader.cs

@ -676,7 +676,8 @@ namespace ICSharpCode.NRefactory.TypeSystem
for (int i = 0; i < typeDefinition.GenericParameters.Count; i++) { for (int i = 0; i < typeDefinition.GenericParameters.Count; i++) {
if (typeDefinition.GenericParameters[i].Position != i) if (typeDefinition.GenericParameters[i].Position != i)
throw new InvalidOperationException("g.Position != i"); throw new InvalidOperationException("g.Position != i");
this.TypeParameters.Add(new DefaultTypeParameter(this, i, typeDefinition.GenericParameters[i].Name)); this.TypeParameters.Add(new DefaultTypeParameter(
EntityType.TypeDefinition, i, typeDefinition.GenericParameters[i].Name));
} }
} }
@ -686,7 +687,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
if (typeDefinition.HasGenericParameters) { if (typeDefinition.HasGenericParameters) {
for (int i = 0; i < typeDefinition.GenericParameters.Count; i++) { for (int i = 0; i < typeDefinition.GenericParameters.Count; i++) {
loader.AddConstraints((DefaultTypeParameter)this.TypeParameters[i], typeDefinition.GenericParameters[i]); loader.AddConstraints(this, (DefaultTypeParameter)this.TypeParameters[i], typeDefinition.GenericParameters[i]);
} }
} }
@ -879,10 +880,11 @@ namespace ICSharpCode.NRefactory.TypeSystem
for (int i = 0; i < method.GenericParameters.Count; i++) { for (int i = 0; i < method.GenericParameters.Count; i++) {
if (method.GenericParameters[i].Position != i) if (method.GenericParameters[i].Position != i)
throw new InvalidOperationException("g.Position != i"); throw new InvalidOperationException("g.Position != i");
m.TypeParameters.Add(new DefaultTypeParameter(m, i, method.GenericParameters[i].Name)); m.TypeParameters.Add(new DefaultTypeParameter(
EntityType.Method, i, method.GenericParameters[i].Name));
} }
for (int i = 0; i < method.GenericParameters.Count; i++) { for (int i = 0; i < method.GenericParameters.Count; i++) {
AddConstraints((DefaultTypeParameter)m.TypeParameters[i], method.GenericParameters[i]); AddConstraints(m, (DefaultTypeParameter)m.TypeParameters[i], method.GenericParameters[i]);
} }
} }
@ -1064,7 +1066,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
#endregion #endregion
#region Type Parameter Constraints #region Type Parameter Constraints
void AddConstraints(DefaultTypeParameter tp, GenericParameter g) void AddConstraints(IEntity parentEntity, DefaultTypeParameter tp, GenericParameter g)
{ {
switch (g.Attributes & GenericParameterAttributes.VarianceMask) { switch (g.Attributes & GenericParameterAttributes.VarianceMask) {
case GenericParameterAttributes.Contravariant: case GenericParameterAttributes.Contravariant:
@ -1081,7 +1083,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
if (g.HasConstraints) { if (g.HasConstraints) {
foreach (TypeReference constraint in g.Constraints) { foreach (TypeReference constraint in g.Constraints) {
tp.Constraints.Add(ReadTypeReference(constraint, entity: tp.Parent)); tp.Constraints.Add(ReadTypeReference(constraint, entity: parentEntity));
} }
} }
} }

48
ICSharpCode.NRefactory/TypeSystem/ITypeParameter.cs

@ -16,6 +16,12 @@ namespace ICSharpCode.NRefactory.TypeSystem
#endif #endif
public interface ITypeParameter : IType, IFreezable public interface ITypeParameter : IType, IFreezable
{ {
/// <summary>
/// Get the type of this type parameter's owner.
/// </summary>
/// <returns>EntityType.TypeDefinition or EntityType.Method</returns>
EntityType OwnerType { get; }
/// <summary> /// <summary>
/// Gets the index of the type parameter in the type parameter list of the owning method/class. /// Gets the index of the type parameter in the type parameter list of the owning method/class.
/// </summary> /// </summary>
@ -26,24 +32,6 @@ namespace ICSharpCode.NRefactory.TypeSystem
/// </summary> /// </summary>
IList<IAttribute> Attributes { get; } IList<IAttribute> Attributes { get; }
/// <summary>
/// Gets the class or method for which this type parameter is defined.
/// This property never returns null.
/// </summary>
IEntity Parent { get; }
/// <summary>
/// The method this type parameter is defined for.
/// This property returns null if the type parameter belongs to a class.
/// </summary>
IMethod ParentMethod { get; }
/// <summary>
/// The class this type parameter is defined for.
/// This property returns null if the type parameter belongs to a method.
/// </summary>
ITypeDefinition ParentClass { get; }
/// <summary> /// <summary>
/// Gets the contraints of this type parameter. /// Gets the contraints of this type parameter.
/// </summary> /// </summary>
@ -80,6 +68,11 @@ namespace ICSharpCode.NRefactory.TypeSystem
/// If this type parameter was bound, returns the unbound version of it. /// If this type parameter was bound, returns the unbound version of it.
/// </summary> /// </summary>
ITypeParameter UnboundTypeParameter { get; } ITypeParameter UnboundTypeParameter { get; }
/// <summary>
/// Gets the region where the type parameter is defined.
/// </summary>
DomRegion Region { get; }
} }
/// <summary> /// <summary>
@ -119,25 +112,6 @@ namespace ICSharpCode.NRefactory.TypeSystem
} }
} }
IEntity ITypeParameter.Parent {
get {
Contract.Ensures(Contract.Result<IEntity>() != null);
return null;
}
}
IMethod ITypeParameter.ParentMethod {
get {
return null;
}
}
ITypeDefinition ITypeParameter.ParentClass {
get {
return null;
}
}
IList<ITypeReference> ITypeParameter.Constraints { IList<ITypeReference> ITypeParameter.Constraints {
get { get {
Contract.Ensures(Contract.Result<IList<ITypeReference>>() != null); Contract.Ensures(Contract.Result<IList<ITypeReference>>() != null);

90
ICSharpCode.NRefactory/TypeSystem/Implementation/DefaultTypeParameter.cs

@ -14,13 +14,16 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
/// </summary> /// </summary>
public class DefaultTypeParameter : AbstractFreezable, ITypeParameter, ISupportsInterning public class DefaultTypeParameter : AbstractFreezable, ITypeParameter, ISupportsInterning
{ {
IEntity parent;
string name; string name;
int index; int index;
IList<ITypeReference> constraints; IList<ITypeReference> constraints;
IList<IAttribute> attributes; IList<IAttribute> attributes;
DomRegion region;
// Small fields: byte+byte+short
VarianceModifier variance; VarianceModifier variance;
EntityType ownerType;
BitVector16 flags; BitVector16 flags;
const ushort FlagReferenceTypeConstraint = 0x0001; const ushort FlagReferenceTypeConstraint = 0x0001;
@ -34,28 +37,15 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
base.FreezeInternal(); base.FreezeInternal();
} }
public DefaultTypeParameter(IMethod parentMethod, int index, string name) public DefaultTypeParameter(EntityType ownerType, int index, string name)
{ {
if (parentMethod == null) if (!(ownerType == EntityType.TypeDefinition || ownerType == EntityType.Method))
throw new ArgumentNullException("parentMethod"); throw new ArgumentException("owner must be a type or a method", "ownerType");
if (index < 0) if (index < 0)
throw new ArgumentOutOfRangeException("index", index, "Value must not be negative"); throw new ArgumentOutOfRangeException("index", index, "Value must not be negative");
if (name == null) if (name == null)
throw new ArgumentNullException("name"); throw new ArgumentNullException("name");
this.parent = parentMethod; this.ownerType = ownerType;
this.index = index;
this.name = name;
}
public DefaultTypeParameter(ITypeDefinition parentClass, int index, string name)
{
if (parentClass == null)
throw new ArgumentNullException("parentClass");
if (index < 0)
throw new ArgumentOutOfRangeException("index", index, "Value must not be negative");
if (name == null)
throw new ArgumentNullException("name");
this.parent = parentClass;
this.index = index; this.index = index;
this.name = name; this.name = name;
} }
@ -74,7 +64,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
public string ReflectionName { public string ReflectionName {
get { get {
if (parent is IMethod) if (ownerType == EntityType.Method)
return "``" + index.ToString(); return "``" + index.ToString();
else else
return "`" + index.ToString(); return "`" + index.ToString();
@ -114,11 +104,9 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
public override int GetHashCode() public override int GetHashCode()
{ {
int hashCode = parent.GetHashCode();
unchecked { unchecked {
hashCode += 1000000033 * index.GetHashCode(); return (int)ownerType * 178256151 + index;
} }
return hashCode;
} }
public override bool Equals(object obj) public override bool Equals(object obj)
@ -131,8 +119,13 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
DefaultTypeParameter p = other as DefaultTypeParameter; DefaultTypeParameter p = other as DefaultTypeParameter;
if (p == null) if (p == null)
return false; return false;
return parent.Equals(p.parent) return ownerType == p.ownerType && index == p.index;
&& index == p.index; }
public EntityType OwnerType {
get {
return ownerType;
}
} }
public int Index { public int Index {
@ -147,18 +140,6 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
} }
} }
public IEntity Parent {
get { return parent; }
}
public IMethod ParentMethod {
get { return parent as IMethod; }
}
public ITypeDefinition ParentClass {
get { return parent as ITypeDefinition; }
}
public IList<ITypeReference> Constraints { public IList<ITypeReference> Constraints {
get { get {
if (constraints == null) if (constraints == null)
@ -199,6 +180,14 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
} }
} }
public DomRegion Region {
get { return region; }
set {
CheckBeforeMutation();
region = value;
}
}
public virtual IType BoundTo { public virtual IType BoundTo {
get { return null; } get { return null; }
} }
@ -217,10 +206,12 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
return this; return this;
} }
static readonly SimpleProjectContent dummyProjectContent = new SimpleProjectContent();
DefaultTypeDefinition GetDummyClassForTypeParameter() DefaultTypeDefinition GetDummyClassForTypeParameter()
{ {
DefaultTypeDefinition c = new DefaultTypeDefinition(ParentClass ?? ParentMethod.DeclaringTypeDefinition, this.Name); DefaultTypeDefinition c = new DefaultTypeDefinition(dummyProjectContent, string.Empty, this.Name);
c.Region = new DomRegion(parent.Region.FileName, parent.Region.BeginLine, parent.Region.BeginColumn); c.Region = this.Region;
if (HasValueTypeConstraint) { if (HasValueTypeConstraint) {
c.ClassType = ClassType.Struct; c.ClassType = ClassType.Struct;
} else if (HasDefaultConstructorConstraint) { } else if (HasDefaultConstructorConstraint) {
@ -294,12 +285,29 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
int ISupportsInterning.GetHashCodeForInterning() int ISupportsInterning.GetHashCodeForInterning()
{ {
return GetHashCode(); unchecked {
int hashCode = GetHashCode();
if (name != null)
hashCode += name.GetHashCode();
if (attributes != null)
hashCode += attributes.GetHashCode();
if (constraints != null)
hashCode += constraints.GetHashCode();
hashCode += 771 * flags.Data + 900103 * (int)variance;
return hashCode;
}
} }
bool ISupportsInterning.EqualsForInterning(ISupportsInterning other) bool ISupportsInterning.EqualsForInterning(ISupportsInterning other)
{ {
return this == other; DefaultTypeParameter o = other as DefaultTypeParameter;
return o != null
&& this.attributes == o.attributes
&& this.constraints == o.constraints
&& this.flags == o.flags
&& this.ownerType == o.ownerType
&& this.index == o.index
&& this.variance == o.variance;
} }
public override string ToString() public override string ToString()

2
ICSharpCode.NRefactory/TypeSystem/Implementation/MethodTypeParameterSubstitution.cs

@ -21,7 +21,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
public override IType VisitTypeParameter(ITypeParameter type) public override IType VisitTypeParameter(ITypeParameter type)
{ {
int index = type.Index; int index = type.Index;
if (type.ParentMethod != null) { if (type.OwnerType == EntityType.Method) {
if (index >= 0 && index < typeArguments.Count) if (index >= 0 && index < typeArguments.Count)
return typeArguments[index]; return typeArguments[index];
else else

2
ICSharpCode.NRefactory/TypeSystem/ParameterizedType.cs

@ -35,7 +35,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
public override IType VisitTypeParameter(ITypeParameter type) public override IType VisitTypeParameter(ITypeParameter type)
{ {
int index = type.Index; int index = type.Index;
if (type.ParentClass != null) { if (type.OwnerType == EntityType.TypeDefinition) {
if (index >= 0 && index < typeArguments.Length) if (index >= 0 && index < typeArguments.Length)
return typeArguments[index]; return typeArguments[index];
else else

Loading…
Cancel
Save