Browse Source

Added more unit tests.

Make IType.GetMethods etc. return IEnumerable instead of IList - with IList, it wasn't clear whether the consumer was allowed to mutate the list.
newNRvisualizers
Daniel Grunwald 15 years ago
parent
commit
662a5ad5f4
  1. 1
      ICSharpCode.NRefactory.Tests/ICSharpCode.NRefactory.Tests.csproj
  2. 123
      ICSharpCode.NRefactory.Tests/TypeSystem/CecilLoaderTests.cs
  3. 15
      ICSharpCode.NRefactory.Tests/TypeSystem/TypeSystemTests.TestCase.cs
  4. 76
      ICSharpCode.NRefactory.Tests/TypeSystem/TypeSystemTests.cs
  5. 41
      ICSharpCode.NRefactory.Tests/Untested.cs
  6. 30
      ICSharpCode.NRefactory/TypeSystem/IType.cs
  7. 12
      ICSharpCode.NRefactory/TypeSystem/Implementation/AbstractType.cs
  8. 13
      ICSharpCode.NRefactory/TypeSystem/Implementation/DefaultMethod.cs
  9. 32
      ICSharpCode.NRefactory/TypeSystem/Implementation/DefaultTypeDefinition.cs
  10. 23
      ICSharpCode.NRefactory/TypeSystem/Implementation/DefaultTypeParameter.cs
  11. 20
      ICSharpCode.NRefactory/TypeSystem/Implementation/VoidTypeDefinition.cs
  12. 24
      ICSharpCode.NRefactory/TypeSystem/ParameterizedType.cs
  13. 12
      ICSharpCode.NRefactory/TypeSystem/ReflectionHelper.cs

1
ICSharpCode.NRefactory.Tests/ICSharpCode.NRefactory.Tests.csproj

@ -54,6 +54,7 @@ @@ -54,6 +54,7 @@
<Compile Include="TypeSystem\TestInterningProvider.cs" />
<Compile Include="TypeSystem\TypeSystemTests.cs" />
<Compile Include="TypeSystem\TypeSystemTests.TestCase.cs" />
<Compile Include="Untested.cs" />
<Compile Include="Util\TreeTraversalTests.cs" />
</ItemGroup>
<ItemGroup>

123
ICSharpCode.NRefactory.Tests/TypeSystem/CecilLoaderTests.cs

@ -79,7 +79,7 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -79,7 +79,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
// EncodingInfo only has an internal constructor
Assert.IsFalse(c.Methods.Any(m => m.IsConstructor));
// and no implicit ctor should be added:
Assert.AreEqual(0, c.GetConstructors(ctx).Count);
Assert.AreEqual(0, c.GetConstructors(ctx).Count());
}
[Test]
@ -115,7 +115,7 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -115,7 +115,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
{
ITypeDefinition c = Mscorlib.GetClass(typeof(void));
Assert.IsNotNull(c, "System.Void not found");
Assert.AreEqual(0, c.GetMethods(ctx).Count);
Assert.AreEqual(0, c.GetMethods(ctx).Count());
Assert.AreEqual(
new string[] {
"[System.SerializableAttribute]",
@ -124,5 +124,124 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -124,5 +124,124 @@ namespace ICSharpCode.NRefactory.TypeSystem
},
c.Attributes.Select(a => a.ToString()).ToArray());
}
[Test]
public void NestedClassInGenericClassTest()
{
ITypeDefinition dictionary = Mscorlib.GetClass(typeof(Dictionary<,>));
Assert.IsNotNull(dictionary);
ITypeDefinition valueCollection = Mscorlib.GetClass(typeof(Dictionary<,>.ValueCollection));
Assert.IsNotNull(valueCollection);
var dictionaryRT = new ParameterizedType(dictionary, new[] { Mscorlib.GetClass(typeof(string)), Mscorlib.GetClass(typeof(int)) });
IProperty valueProperty = dictionaryRT.GetProperties(ctx).Single(p => p.Name == "Values");
IType parameterizedValueCollection = valueProperty.ReturnType.Resolve(ctx);
Assert.AreEqual("System.Collections.Generic.Dictionary`2+ValueCollection[[System.String],[System.Int32]]", parameterizedValueCollection.DotNetName);
Assert.AreSame(valueCollection, parameterizedValueCollection.GetDefinition());
}
[Test]
public void ValueCollectionCountModifiers()
{
ITypeDefinition valueCollection = Mscorlib.GetClass(typeof(Dictionary<,>.ValueCollection));
Assert.AreEqual(Accessibility.Public, valueCollection.Accessibility);
Assert.IsTrue(valueCollection.IsSealed);
Assert.IsFalse(valueCollection.IsAbstract);
Assert.IsFalse(valueCollection.IsStatic);
IProperty count = valueCollection.Properties.Single(p => p.Name == "Count");
Assert.AreEqual(Accessibility.Public, count.Accessibility);
Assert.IsTrue(count.IsSealed);
Assert.IsFalse(count.IsVirtual);
Assert.IsFalse(count.IsAbstract);
}
[Test]
public void MathAcosModifiers()
{
ITypeDefinition math = Mscorlib.GetClass(typeof(Math));
Assert.AreEqual(Accessibility.Public, math.Accessibility);
Assert.IsTrue(math.IsSealed);
Assert.IsTrue(math.IsAbstract);
Assert.IsTrue(math.IsStatic);
IMethod acos = math.Methods.Single(p => p.Name == "Acos");
Assert.AreEqual(Accessibility.Public, acos.Accessibility);
Assert.IsTrue(acos.IsStatic);
Assert.IsFalse(acos.IsAbstract);
Assert.IsFalse(acos.IsSealed);
Assert.IsFalse(acos.IsVirtual);
Assert.IsFalse(acos.IsOverride);
}
[Test]
public void EncodingModifiers()
{
ITypeDefinition encoding = Mscorlib.GetClass(typeof(Encoding));
Assert.AreEqual(Accessibility.Public, encoding.Accessibility);
Assert.IsFalse(encoding.IsSealed);
Assert.IsTrue(encoding.IsAbstract);
IMethod getDecoder = encoding.Methods.Single(p => p.Name == "GetDecoder");
Assert.AreEqual(Accessibility.Public, getDecoder.Accessibility);
Assert.IsFalse(getDecoder.IsStatic);
Assert.IsFalse(getDecoder.IsAbstract);
Assert.IsFalse(getDecoder.IsSealed);
Assert.IsTrue(getDecoder.IsVirtual);
Assert.IsFalse(getDecoder.IsOverride);
IMethod getMaxByteCount = encoding.Methods.Single(p => p.Name == "GetMaxByteCount");
Assert.AreEqual(Accessibility.Public, getMaxByteCount.Accessibility);
Assert.IsFalse(getMaxByteCount.IsStatic);
Assert.IsTrue(getMaxByteCount.IsAbstract);
Assert.IsFalse(getMaxByteCount.IsSealed);
Assert.IsFalse(getMaxByteCount.IsVirtual);
Assert.IsFalse(getMaxByteCount.IsOverride);
IProperty encoderFallback = encoding.Properties.Single(p => p.Name == "EncoderFallback");
Assert.AreEqual(Accessibility.Public, encoderFallback.Accessibility);
Assert.IsFalse(encoderFallback.IsStatic);
Assert.IsFalse(encoderFallback.IsAbstract);
Assert.IsFalse(encoderFallback.IsSealed);
Assert.IsFalse(encoderFallback.IsVirtual);
Assert.IsFalse(encoderFallback.IsOverride);
}
[Test]
public void UnicodeEncodingModifiers()
{
ITypeDefinition encoding = Mscorlib.GetClass(typeof(UnicodeEncoding));
Assert.AreEqual(Accessibility.Public, encoding.Accessibility);
Assert.IsFalse(encoding.IsSealed);
Assert.IsFalse(encoding.IsAbstract);
IMethod getDecoder = encoding.Methods.Single(p => p.Name == "GetDecoder");
Assert.AreEqual(Accessibility.Public, getDecoder.Accessibility);
Assert.IsFalse(getDecoder.IsStatic);
Assert.IsFalse(getDecoder.IsAbstract);
Assert.IsFalse(getDecoder.IsSealed);
// Should be override, but actually is 'virtual'. We cannot do better because 'override' is not encoded in the metadata
// (the .override directive is unrelated; it's meant for explicit interface implementations)
Assert.IsTrue(getDecoder.IsVirtual);
Assert.IsFalse(getDecoder.IsOverride);
}
[Test]
public void UTF32EncodingModifiers()
{
ITypeDefinition encoding = Mscorlib.GetClass(typeof(UTF32Encoding));
Assert.AreEqual(Accessibility.Public, encoding.Accessibility);
Assert.IsTrue(encoding.IsSealed);
Assert.IsFalse(encoding.IsAbstract);
IMethod getDecoder = encoding.Methods.Single(p => p.Name == "GetDecoder");
Assert.AreEqual(Accessibility.Public, getDecoder.Accessibility);
Assert.IsFalse(getDecoder.IsStatic);
Assert.IsFalse(getDecoder.IsAbstract);
Assert.IsFalse(getDecoder.IsSealed);
// Should be override, but actually is 'virtual'. We cannot do better because 'override' is not encoded in the metadata
// (the .override directive is unrelated; it's meant for explicit interface implementations)
Assert.IsTrue(getDecoder.IsVirtual);
Assert.IsFalse(getDecoder.IsOverride);
}
}
}

15
ICSharpCode.NRefactory.Tests/TypeSystem/TypeSystemTests.TestCase.cs

@ -21,10 +21,25 @@ namespace ICSharpCode.NRefactory.TypeSystem.TestCase @@ -21,10 +21,25 @@ namespace ICSharpCode.NRefactory.TypeSystem.TestCase
public class DynamicTest
{
public dynamic SimpleProperty { get; set; }
public List<dynamic> DynamicGenerics1(Action<object, dynamic[], object> param) { return null; }
public void DynamicGenerics2(Action<object, dynamic, object> param) { }
public void DynamicGenerics3(Action<int, dynamic, object> param) { }
public void DynamicGenerics4(Action<int[], dynamic, object> param) { }
public void DynamicGenerics5(Action<int*[], dynamic, object> param) { }
}
public class GenericClass<A, B> where A : B
{
public void TestMethod<K, V>(string param) where V: K where K: IComparable<V> {}
public void GetIndex<T>(T element) where T : IEquatable<T> {}
}
public class PropertyTest
{
public int PropertyWithProtectedSetter { get; protected set; }
public object PropertyWithPrivateSetter { get; private set; }
}
}

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

@ -17,6 +17,14 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -17,6 +17,14 @@ namespace ICSharpCode.NRefactory.TypeSystem
{
protected IProjectContent testCasePC;
ITypeResolveContext ctx;
[SetUpAttribute]
public void SetUp()
{
ctx = AggregateTypeResolveContext.Combine(testCasePC, CecilLoaderTests.Mscorlib);
}
ITypeDefinition GetClass(Type type)
{
return testCasePC.GetClass(type.FullName, type.GetGenericArguments().Length, StringComparer.Ordinal);
@ -56,6 +64,13 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -56,6 +64,13 @@ namespace ICSharpCode.NRefactory.TypeSystem
Assert.AreEqual(0, method.Attributes.Count);
}
[Test]
public void DynamicType()
{
ITypeDefinition testClass = testCasePC.GetClass(typeof(DynamicTest));
Assert.AreSame(SharedTypes.Dynamic, testClass.Properties.Single().ReturnType.Resolve(ctx));
}
[Test]
[Ignore]
public void DynamicTypeInGenerics()
@ -73,7 +88,6 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -73,7 +88,6 @@ namespace ICSharpCode.NRefactory.TypeSystem
[Test]
public void AssemblyAttribute()
{
ITypeResolveContext ctx = AggregateTypeResolveContext.Combine(testCasePC, CecilLoaderTests.Mscorlib);
var attributes = testCasePC.AssemblyAttributes;
var typeTest = attributes.First(a => a.AttributeType.Resolve(ctx).FullName == typeof(TypeTestAttribute).FullName);
Assert.AreEqual(3, typeTest.PositionalArguments.Count);
@ -91,5 +105,65 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -91,5 +105,65 @@ namespace ICSharpCode.NRefactory.TypeSystem
// ? for NUnit.TestAttribute (because that assembly isn't in ctx)
Assert.AreEqual("System.Collections.Generic.IList`1[[?]]", crt.TypeArguments[1].DotNetName);
}
[Test]
public void TestClassTypeParameters()
{
var testClass = testCasePC.GetClass(typeof(GenericClass<,>));
Assert.AreSame(testClass, testClass.TypeParameters[0].ParentClass);
Assert.AreSame(testClass, testClass.TypeParameters[1].ParentClass);
Assert.AreSame(testClass.TypeParameters[1], testClass.TypeParameters[0].Constraints[0].Resolve(ctx));
}
[Test]
public void TestMethod()
{
var testClass = testCasePC.GetClass(typeof(GenericClass<,>));
IMethod m = testClass.Methods.Single(me => me.Name == "TestMethod");
Assert.AreEqual("K", m.TypeParameters[0].Name);
Assert.AreEqual("V", m.TypeParameters[1].Name);
Assert.AreSame(m, m.TypeParameters[0].ParentMethod);
Assert.AreSame(m, m.TypeParameters[1].ParentMethod);
Assert.AreEqual("System.IComparable`1[[``1]]", m.TypeParameters[0].Constraints[0].Resolve(ctx).DotNetName);
Assert.AreSame(m.TypeParameters[0], m.TypeParameters[1].Constraints[0].Resolve(ctx));
}
[Test]
public void GetIndex()
{
var testClass = testCasePC.GetClass(typeof(GenericClass<,>));
IMethod m = testClass.Methods.Single(me => me.Name == "GetIndex");
Assert.AreEqual("T", m.TypeParameters[0].Name);
Assert.AreSame(m, m.TypeParameters[0].ParentMethod);
ParameterizedType constraint = (ParameterizedType)m.TypeParameters[0].Constraints[0].Resolve(ctx);
Assert.AreEqual("IEquatable", constraint.Name);
Assert.AreEqual(1, constraint.TypeParameterCount);
Assert.AreEqual(1, constraint.TypeArguments.Count);
Assert.AreSame(m.TypeParameters[0], constraint.TypeArguments[0]);
}
[Test]
public void PropertyWithProtectedSetter()
{
var testClass = testCasePC.GetClass(typeof(PropertyTest));
IProperty p = testClass.Properties.Single(pr => pr.Name == "PropertyWithProtectedSetter");
Assert.AreEqual(Accessibility.Public, p.Accessibility);
Assert.AreEqual(Accessibility.Public, p.GetterAccessibility);
Assert.AreEqual(Accessibility.Protected, p.SetterAccessibility);
}
[Test]
public void PropertyWithPrivateSetter()
{
var testClass = testCasePC.GetClass(typeof(PropertyTest));
IProperty p = testClass.Properties.Single(pr => pr.Name == "PropertyWithPrivateSetter");
Assert.AreEqual(Accessibility.Public, p.Accessibility);
Assert.AreEqual(Accessibility.Public, p.GetterAccessibility);
Assert.AreEqual(Accessibility.Private, p.SetterAccessibility);
}
}
}

41
ICSharpCode.NRefactory.Tests/Untested.cs

@ -0,0 +1,41 @@ @@ -0,0 +1,41 @@
// Copyright (c) 2010 AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
namespace ICSharpCode.NRefactory
{
// This file contains unit tests from SharpDevelop 4.0 which are not (yet) ported to NRefactory
/*
class ReflectionOrCecilLayerTests {
[Test]
public void ParameterComparisonTest()
{
DefaultParameter p1 = new DefaultParameter("a", mscorlib.GetClass("System.String", 0).DefaultReturnType, DomRegion.Empty);
DefaultParameter p2 = new DefaultParameter("b", new GetClassReturnType(mscorlib, "System.String", 0), DomRegion.Empty);
IList<IParameter> a1 = new List<IParameter>();
IList<IParameter> a2 = new List<IParameter>();
a1.Add(p1);
a2.Add(p2);
Assert.AreEqual(0, DiffUtility.Compare(a1, a2));
}
[Test]
public void GenericDocumentationTagNamesTest()
{
DefaultClass c = (DefaultClass)mscorlib.GetClass("System.Collections.Generic.List", 1);
Assert.AreEqual("T:System.Collections.Generic.List`1",
c.DocumentationTag);
Assert.AreEqual("M:System.Collections.Generic.List`1.Add(`0)",
GetMethod(c, "Add").DocumentationTag);
Assert.AreEqual("M:System.Collections.Generic.List`1.AddRange(System.Collections.Generic.IEnumerable{`0})",
GetMethod(c, "AddRange").DocumentationTag);
Assert.AreEqual("M:System.Collections.Generic.List`1.ConvertAll``1(System.Converter{`0,``0})",
GetMethod(c, "ConvertAll").DocumentationTag);
}
}
*/
}

30
ICSharpCode.NRefactory/TypeSystem/IType.cs

@ -68,40 +68,34 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -68,40 +68,34 @@ namespace ICSharpCode.NRefactory.TypeSystem
/// If the inner class is generic, this method produces <see cref="ParameterizedType"/>s that
/// parameterize each nested class with its own type parameters.
/// </remarks>
/// <returns>A new mutable list</returns>
IList<IType> GetNestedTypes(ITypeResolveContext context);
IEnumerable<IType> GetNestedTypes(ITypeResolveContext context);
/// <summary>
/// Gets all methods that can be called on this return type.
/// </summary>
/// <remarks>The list does not include constructors.</remarks>
/// <returns>A new mutable list</returns>
IList<IMethod> GetMethods(ITypeResolveContext context);
IEnumerable<IMethod> GetMethods(ITypeResolveContext context);
/// <summary>
/// Gets all instance constructors for this type.
/// </summary>
/// <remarks>This list does not include constructors in base classes or static constructors.</remarks>
/// <returns>A new mutable list</returns>
IList<IMethod> GetConstructors(ITypeResolveContext context);
IEnumerable<IMethod> GetConstructors(ITypeResolveContext context);
/// <summary>
/// Gets all properties that can be called on this return type.
/// </summary>
/// <returns>A new mutable list</returns>
IList<IProperty> GetProperties(ITypeResolveContext context);
IEnumerable<IProperty> GetProperties(ITypeResolveContext context);
/// <summary>
/// Gets all fields that can be called on this return type.
/// </summary>
/// <returns>A new mutable list</returns>
IList<IField> GetFields(ITypeResolveContext context);
IEnumerable<IField> GetFields(ITypeResolveContext context);
/// <summary>
/// Gets all events that can be called on this return type.
/// </summary>
/// <returns>A new mutable list</returns>
IList<IEvent> GetEvents(ITypeResolveContext context);
IEnumerable<IEvent> GetEvents(ITypeResolveContext context);
}
[ContractClassFor(typeof(IType))]
@ -129,42 +123,42 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -129,42 +123,42 @@ namespace ICSharpCode.NRefactory.TypeSystem
return null;
}
IList<IType> IType.GetNestedTypes(ITypeResolveContext context)
IEnumerable<IType> IType.GetNestedTypes(ITypeResolveContext context)
{
Contract.Requires(context != null);
Contract.Ensures(Contract.Result<IList<IType>>() != null);
return null;
}
IList<IMethod> IType.GetMethods(ITypeResolveContext context)
IEnumerable<IMethod> IType.GetMethods(ITypeResolveContext context)
{
Contract.Requires(context != null);
Contract.Ensures(Contract.Result<IList<IMethod>>() != null);
return null;
}
IList<IMethod> IType.GetConstructors(ITypeResolveContext context)
IEnumerable<IMethod> IType.GetConstructors(ITypeResolveContext context)
{
Contract.Requires(context != null);
Contract.Ensures(Contract.Result<IList<IMethod>>() != null);
return null;
}
IList<IProperty> IType.GetProperties(ITypeResolveContext context)
IEnumerable<IProperty> IType.GetProperties(ITypeResolveContext context)
{
Contract.Requires(context != null);
Contract.Ensures(Contract.Result<IList<IProperty>>() != null);
return null;
}
IList<IField> IType.GetFields(ITypeResolveContext context)
IEnumerable<IField> IType.GetFields(ITypeResolveContext context)
{
Contract.Requires(context != null);
Contract.Ensures(Contract.Result<IList<IField>>() != null);
return null;
}
IList<IEvent> IType.GetEvents(ITypeResolveContext context)
IEnumerable<IEvent> IType.GetEvents(ITypeResolveContext context)
{
Contract.Requires(context != null);
Contract.Ensures(Contract.Result<IList<IEvent>>() != null);

12
ICSharpCode.NRefactory/TypeSystem/Implementation/AbstractType.cs

@ -66,32 +66,32 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -66,32 +66,32 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
return EmptyList<IType>.Instance;
}
public virtual IList<IType> GetNestedTypes(ITypeResolveContext context)
public virtual IEnumerable<IType> GetNestedTypes(ITypeResolveContext context)
{
return EmptyList<IType>.Instance;
}
public virtual IList<IMethod> GetMethods(ITypeResolveContext context)
public virtual IEnumerable<IMethod> GetMethods(ITypeResolveContext context)
{
return EmptyList<IMethod>.Instance;
}
public virtual IList<IMethod> GetConstructors(ITypeResolveContext context)
public virtual IEnumerable<IMethod> GetConstructors(ITypeResolveContext context)
{
return EmptyList<IMethod>.Instance;
}
public virtual IList<IProperty> GetProperties(ITypeResolveContext context)
public virtual IEnumerable<IProperty> GetProperties(ITypeResolveContext context)
{
return EmptyList<IProperty>.Instance;
}
public virtual IList<IField> GetFields(ITypeResolveContext context)
public virtual IEnumerable<IField> GetFields(ITypeResolveContext context)
{
return EmptyList<IField>.Instance;
}
public virtual IList<IEvent> GetEvents(ITypeResolveContext context)
public virtual IEnumerable<IEvent> GetEvents(ITypeResolveContext context)
{
return EmptyList<IEvent>.Instance;
}

13
ICSharpCode.NRefactory/TypeSystem/Implementation/DefaultMethod.cs

@ -113,5 +113,18 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -113,5 +113,18 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
b.Append(']');
return b.ToString();
}
public static DefaultMethod CreateDefaultConstructor(ITypeDefinition typeDefinition)
{
DomRegion region = new DomRegion(typeDefinition.Region.FileName, typeDefinition.Region.BeginLine, typeDefinition.Region.BeginColumn);
return new DefaultMethod(typeDefinition, ".ctor") {
EntityType = EntityType.Constructor,
Accessibility = typeDefinition.IsAbstract ? Accessibility.Protected : Accessibility.Public,
IsSynthetic = true,
Region = region,
BodyRegion = region,
ReturnType = typeDefinition
};
}
}
}

32
ICSharpCode.NRefactory/TypeSystem/Implementation/DefaultTypeDefinition.cs

@ -361,26 +361,24 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -361,26 +361,24 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
return this;
}
public virtual IList<IType> GetNestedTypes(ITypeResolveContext context)
public virtual IEnumerable<IType> GetNestedTypes(ITypeResolveContext context)
{
ITypeDefinition compound = GetCompoundClass();
if (compound != this)
return compound.GetNestedTypes(context);
List<IType> nestedTypes = new List<IType>();
using (var busyLock = BusyManager.Enter(this)) {
if (busyLock.Success) {
IList<IType> nestedTypes = null;
foreach (var baseTypeRef in this.BaseTypes) {
IType baseType = baseTypeRef.Resolve(context);
ITypeDefinition baseTypeDef = baseType.GetDefinition();
if (baseTypeDef != null && baseTypeDef.ClassType != ClassType.Interface) {
// get nested types from baseType (not baseTypeDef) so that generics work correctly
nestedTypes = baseType.GetNestedTypes(context);
nestedTypes.AddRange(baseType.GetNestedTypes(context));
break; // there is at most 1 non-interface base
}
}
if (nestedTypes == null)
nestedTypes = new List<IType>();
foreach (ITypeDefinition innerClass in this.InnerClasses) {
if (innerClass.TypeParameterCount > 0) {
// Parameterize inner classes with their own type parameters, as per <remarks> on IType.GetNestedTypes.
@ -389,14 +387,12 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -389,14 +387,12 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
nestedTypes.Add(innerClass);
}
}
return nestedTypes;
} else {
return new List<IType>();
}
}
return nestedTypes;
}
public virtual IList<IMethod> GetMethods(ITypeResolveContext context)
public virtual IEnumerable<IMethod> GetMethods(ITypeResolveContext context)
{
ITypeDefinition compound = GetCompoundClass();
if (compound != this)
@ -418,7 +414,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -418,7 +414,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
return methods;
}
public virtual IList<IMethod> GetConstructors(ITypeResolveContext context)
public virtual IEnumerable<IMethod> GetConstructors(ITypeResolveContext context)
{
ITypeDefinition compound = GetCompoundClass();
if (compound != this)
@ -431,21 +427,13 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -431,21 +427,13 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
if (this.ClassType == ClassType.Class && methods.Count == 0
|| this.ClassType == ClassType.Enum || this.ClassType == ClassType.Struct)
{
DomRegion region = new DomRegion(this.Region.FileName, this.Region.BeginLine, this.Region.BeginColumn);
methods.Add(new DefaultMethod(this, ".ctor") {
EntityType = EntityType.Constructor,
Accessibility = IsAbstract ? Accessibility.Protected : Accessibility.Public,
IsSynthetic = true,
Region = region,
BodyRegion = region,
ReturnType = this
});
methods.Add(DefaultMethod.CreateDefaultConstructor(this));
}
}
return methods;
}
public virtual IList<IProperty> GetProperties(ITypeResolveContext context)
public virtual IEnumerable<IProperty> GetProperties(ITypeResolveContext context)
{
ITypeDefinition compound = GetCompoundClass();
if (compound != this)
@ -467,7 +455,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -467,7 +455,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
return properties;
}
public virtual IList<IField> GetFields(ITypeResolveContext context)
public virtual IEnumerable<IField> GetFields(ITypeResolveContext context)
{
ITypeDefinition compound = GetCompoundClass();
if (compound != this)
@ -489,7 +477,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -489,7 +477,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
return fields;
}
public virtual IList<IEvent> GetEvents(ITypeResolveContext context)
public virtual IEnumerable<IEvent> GetEvents(ITypeResolveContext context)
{
ITypeDefinition compound = GetCompoundClass();
if (compound != this)

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

@ -179,6 +179,29 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -179,6 +179,29 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
return visitor.VisitTypeParameter(this);
}
DefaultTypeDefinition GetDummyClassForTypeParameter()
{
DefaultTypeDefinition c = new DefaultTypeDefinition(ParentClass ?? ParentMethod.DeclaringTypeDefinition, this.Name);
c.Region = new DomRegion(parent.Region.FileName, parent.Region.BeginLine, parent.Region.BeginColumn);
if (HasValueTypeConstraint) {
c.ClassType = ClassType.Struct;
} else if (HasDefaultConstructorConstraint) {
c.ClassType = ClassType.Class;
} else {
c.ClassType = ClassType.Interface;
}
return c;
}
public override IEnumerable<IMethod> GetConstructors(ITypeResolveContext context)
{
if (HasDefaultConstructorConstraint || HasValueTypeConstraint) {
return new [] { DefaultMethod.CreateDefaultConstructor(GetDummyClassForTypeParameter()) };
} else {
return EmptyList<IMethod>.Instance;
}
}
void ISupportsInterning.PrepareForInterning(IInterningProvider provider)
{
constraints = provider.InternList(constraints);

20
ICSharpCode.NRefactory/TypeSystem/Implementation/VoidTypeDefinition.cs

@ -17,29 +17,29 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -17,29 +17,29 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
this.IsSealed = true;
}
public override IList<IMethod> GetConstructors(ITypeResolveContext context)
public override IEnumerable<IMethod> GetConstructors(ITypeResolveContext context)
{
return new List<IMethod>();
return EmptyList<IMethod>.Instance;
}
public override IList<IEvent> GetEvents(ITypeResolveContext context)
public override IEnumerable<IEvent> GetEvents(ITypeResolveContext context)
{
return new List<IEvent>();
return EmptyList<IEvent>.Instance;
}
public override IList<IField> GetFields(ITypeResolveContext context)
public override IEnumerable<IField> GetFields(ITypeResolveContext context)
{
return new List<IField>();
return EmptyList<IField>.Instance;
}
public override IList<IMethod> GetMethods(ITypeResolveContext context)
public override IEnumerable<IMethod> GetMethods(ITypeResolveContext context)
{
return new List<IMethod>();
return EmptyList<IMethod>.Instance;
}
public override IList<IProperty> GetProperties(ITypeResolveContext context)
public override IEnumerable<IProperty> GetProperties(ITypeResolveContext context)
{
return new List<IProperty>();
return EmptyList<IProperty>.Instance;
}
}
}

24
ICSharpCode.NRefactory/TypeSystem/ParameterizedType.cs

@ -158,7 +158,7 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -158,7 +158,7 @@ namespace ICSharpCode.NRefactory.TypeSystem
return genericType.GetBaseTypes(context).Select(substitution.Apply);
}
public IList<IType> GetNestedTypes(ITypeResolveContext context)
public IEnumerable<IType> GetNestedTypes(ITypeResolveContext context)
{
/*
class Base<T> {
@ -172,17 +172,17 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -172,17 +172,17 @@ namespace ICSharpCode.NRefactory.TypeSystem
Base.GetNestedTypes() = { Base`1+Nested<T2> } where T2 = copy of T in Base`1+Nested
*/
Substitution substitution = new Substitution(typeArguments);
IList<IType> types = genericType.GetNestedTypes(context);
List<IType> types = genericType.GetNestedTypes(context).ToList();
for (int i = 0; i < types.Count; i++) {
types[i] = types[i].AcceptVisitor(substitution);
}
return types;
}
public IList<IMethod> GetMethods(ITypeResolveContext context)
public IEnumerable<IMethod> GetMethods(ITypeResolveContext context)
{
Substitution substitution = new Substitution(typeArguments);
IList<IMethod> methods = genericType.GetMethods(context);
List<IMethod> methods = genericType.GetMethods(context).ToList();
for (int i = 0; i < methods.Count; i++) {
SpecializedMethod m = new SpecializedMethod(methods[i]);
m.SetDeclaringType(this);
@ -192,10 +192,10 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -192,10 +192,10 @@ namespace ICSharpCode.NRefactory.TypeSystem
return methods;
}
public IList<IMethod> GetConstructors(ITypeResolveContext context)
public IEnumerable<IMethod> GetConstructors(ITypeResolveContext context)
{
Substitution substitution = new Substitution(typeArguments);
IList<IMethod> methods = genericType.GetConstructors(context);
List<IMethod> methods = genericType.GetConstructors(context).ToList();
for (int i = 0; i < methods.Count; i++) {
SpecializedMethod m = new SpecializedMethod(methods[i]);
m.SetDeclaringType(this);
@ -205,10 +205,10 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -205,10 +205,10 @@ namespace ICSharpCode.NRefactory.TypeSystem
return methods;
}
public IList<IProperty> GetProperties(ITypeResolveContext context)
public IEnumerable<IProperty> GetProperties(ITypeResolveContext context)
{
Substitution substitution = new Substitution(typeArguments);
IList<IProperty> properties = genericType.GetProperties(context);
List<IProperty> properties = genericType.GetProperties(context).ToList();
for (int i = 0; i < properties.Count; i++) {
SpecializedProperty p = new SpecializedProperty(properties[i]);
p.SetDeclaringType(this);
@ -218,10 +218,10 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -218,10 +218,10 @@ namespace ICSharpCode.NRefactory.TypeSystem
return properties;
}
public IList<IField> GetFields(ITypeResolveContext context)
public IEnumerable<IField> GetFields(ITypeResolveContext context)
{
Substitution substitution = new Substitution(typeArguments);
IList<IField> fields = genericType.GetFields(context);
List<IField> fields = genericType.GetFields(context).ToList();
for (int i = 0; i < fields.Count; i++) {
SpecializedField f = new SpecializedField(fields[i]);
f.SetDeclaringType(this);
@ -231,10 +231,10 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -231,10 +231,10 @@ namespace ICSharpCode.NRefactory.TypeSystem
return fields;
}
public IList<IEvent> GetEvents(ITypeResolveContext context)
public IEnumerable<IEvent> GetEvents(ITypeResolveContext context)
{
Substitution substitution = new Substitution(typeArguments);
IList<IEvent> events = genericType.GetEvents(context);
List<IEvent> events = genericType.GetEvents(context).ToList();
for (int i = 0; i < events.Count; i++) {
SpecializedEvent e = new SpecializedEvent(events[i]);
e.SetDeclaringType(this);

12
ICSharpCode.NRefactory/TypeSystem/ReflectionHelper.cs

@ -17,6 +17,14 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -17,6 +17,14 @@ namespace ICSharpCode.NRefactory.TypeSystem
/// <returns>Returns the class; or null if it is not found.</returns>
public static ITypeDefinition GetClass(this ITypeResolveContext context, Type type)
{
if (type == null)
return null;
while (type.IsArray || type.IsPointer || type.IsByRef)
type = type.GetElementType();
if (type.IsGenericType && !type.IsGenericTypeDefinition)
type = type.GetGenericTypeDefinition();
if (type.IsGenericParameter)
return null;
if (type.DeclaringType != null) {
ITypeDefinition declaringType = GetClass(context, type.DeclaringType);
if (declaringType != null) {
@ -42,9 +50,11 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -42,9 +50,11 @@ namespace ICSharpCode.NRefactory.TypeSystem
/// </summary>
/// <param name="type">The type to be converted.</param>
/// <param name="entity">The parent entity, used to fetch the ITypeParameter for generic types.</param>
/// <returns>Returns the class; or null if it is not found.</returns>
/// <returns>Returns the type reference.</returns>
public static ITypeReference ToTypeReference(this Type type, IEntity entity = null)
{
if (type == null)
return SharedTypes.UnknownType;
if (type.IsGenericType && !type.IsGenericTypeDefinition) {
ITypeReference def = ToTypeReference(type.GetGenericTypeDefinition(), entity);
Type[] arguments = type.GetGenericArguments();

Loading…
Cancel
Save