Browse Source

Store the underlying type for enums.

newNRvisualizers
Daniel Grunwald 15 years ago
parent
commit
0b1c04928d
  1. 9
      ICSharpCode.NRefactory.Tests/TypeSystem/TypeSystemTests.TestCase.cs
  2. 10
      ICSharpCode.NRefactory.Tests/TypeSystem/TypeSystemTests.cs
  3. 9
      ICSharpCode.NRefactory/CSharp/Resolver/CSharpResolver.cs
  4. 21
      ICSharpCode.NRefactory/TypeSystem/CecilLoader.cs
  5. 22
      ICSharpCode.NRefactory/TypeSystem/ExtensionMethods.cs
  6. 2
      ICSharpCode.NRefactory/TypeSystem/Implementation/DefaultTypeDefinition.cs

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

@ -44,4 +44,13 @@ namespace ICSharpCode.NRefactory.TypeSystem.TestCase @@ -44,4 +44,13 @@ namespace ICSharpCode.NRefactory.TypeSystem.TestCase
public string this[int index] { get { return "Test"; } }
}
public enum MyEnum : short
{
First,
Second,
Flag1 = 0x10,
Flag2 = 0x20,
CombinedFlags = Flag1 | Flag2
}
}

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

@ -181,5 +181,15 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -181,5 +181,15 @@ namespace ICSharpCode.NRefactory.TypeSystem
Assert.IsFalse(p.CanSet);
Assert.AreEqual(Accessibility.None, p.SetterAccessibility);
}
[Test]
public void EnumTest()
{
var e = testCasePC.GetClass(typeof(MyEnum));
Assert.AreEqual(ClassType.Enum, e.ClassType);
Assert.AreEqual(false, e.IsReferenceType);
Assert.AreEqual("System.Int16", e.BaseTypes[0].Resolve(ctx).DotNetName);
Assert.AreEqual(new[] { "System.Enum" }, e.GetBaseTypes(ctx).Select(t => t.DotNetName).ToArray());
}
}
}

9
ICSharpCode.NRefactory/CSharp/Resolver/CSharpResolver.cs

@ -378,7 +378,14 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver @@ -378,7 +378,14 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
else
return new ErrorResolveResult(targetType);
} else if (targetType.IsEnum()) {
throw new NotImplementedException();
code = ReflectionHelper.GetTypeCode(targetType.GetEnumUnderlyingType(context));
if (code >= TypeCode.SByte && code <= TypeCode.UInt64) {
try {
return new ConstantResolveResult(targetType, Convert.ChangeType(expression.ConstantValue, code, CultureInfo.InvariantCulture));
} catch (InvalidCastException) {
return new ErrorResolveResult(targetType);
}
}
}
}
return new ResolveResult(targetType);

21
ICSharpCode.NRefactory/TypeSystem/CecilLoader.cs

@ -456,12 +456,21 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -456,12 +456,21 @@ namespace ICSharpCode.NRefactory.TypeSystem
}
// set base classes
if (typeDefinition.BaseType != null) {
BaseTypes.Add(loader.ReadTypeReference(typeDefinition.BaseType, entity: this));
}
if (typeDefinition.HasInterfaces) {
foreach (TypeReference iface in typeDefinition.Interfaces) {
BaseTypes.Add(loader.ReadTypeReference(iface, entity: this));
if (typeDefinition.IsEnum) {
foreach (FieldDefinition enumField in typeDefinition.Fields) {
if (!enumField.IsStatic) {
BaseTypes.Add(loader.ReadTypeReference(enumField.FieldType, entity: this));
break;
}
}
} else {
if (typeDefinition.BaseType != null) {
BaseTypes.Add(loader.ReadTypeReference(typeDefinition.BaseType, entity: this));
}
if (typeDefinition.HasInterfaces) {
foreach (TypeReference iface in typeDefinition.Interfaces) {
BaseTypes.Add(loader.ReadTypeReference(iface, entity: this));
}
}
}

22
ICSharpCode.NRefactory/TypeSystem/ExtensionMethods.cs

@ -88,7 +88,9 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -88,7 +88,9 @@ namespace ICSharpCode.NRefactory.TypeSystem
throw new ArgumentNullException("type");
return type is ITypeDefinition && type.TypeParameterCount > 0;
}
#endregion
#region IsEnum / GetEnumUnderlyingType
/// <summary>
/// Gets whether the type is an enumeration type.
/// </summary>
@ -99,6 +101,26 @@ namespace ICSharpCode.NRefactory.TypeSystem @@ -99,6 +101,26 @@ namespace ICSharpCode.NRefactory.TypeSystem
ITypeDefinition def = type.GetDefinition();
return def != null && def.ClassType == ClassType.Enum;
}
/// <summary>
/// Gets the underlying type for this enum type.
/// </summary>
public static IType GetEnumUnderlyingType(this IType enumType, ITypeResolveContext context)
{
if (enumType == null)
throw new ArgumentNullException("enumType");
if (context == null)
throw new ArgumentNullException("context");
ITypeDefinition def = enumType.GetDefinition();
if (def != null && def.ClassType == ClassType.Enum) {
if (def.BaseTypes.Count == 1)
return def.BaseTypes[0].Resolve(context);
else
return context.GetClass(typeof(int)) ?? SharedTypes.UnknownType;
} else {
throw new ArgumentException("enumType must be an enum");
}
}
#endregion
}
}

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

@ -319,7 +319,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation @@ -319,7 +319,7 @@ namespace ICSharpCode.NRefactory.TypeSystem.Implementation
public IEnumerable<IType> GetBaseTypes(ITypeResolveContext context)
{
bool hasNonInterface = false;
if (baseTypes != null) {
if (baseTypes != null && this.ClassType != ClassType.Enum) {
foreach (ITypeReference baseTypeRef in baseTypes) {
IType baseType = baseTypeRef.Resolve(context);
ITypeDefinition baseTypeDef = baseType.GetDefinition();

Loading…
Cancel
Save