Clenup few checks.
[mono.git] / mcs / mcs / typespec.cs
index 6eb94ca0b45333e0330d0ab41ef5045513addca0..22278a08dacd4806887da44e02ad0cfb9f93184e 100644 (file)
@@ -617,12 +617,23 @@ namespace Mono.CSharp
                                if (type1.MemberDefinition != target_type_def)
                                        return false;
 
-                               if (!type1.IsInterface && !type1.IsDelegate)
-                                       return false;
-
                                var t1_targs = type1.TypeArguments;
                                var t2_targs = type2.TypeArguments;
                                var targs_definition = target_type_def.TypeParameters;
+
+                               if (!type1.IsInterface && !type1.IsDelegate) {
+                                       //
+                                       // Internal compiler variance between G<object> and G<dynamic>
+                                       //
+                                       for (int i = 0; i < targs_definition.Length; ++i) {
+                                               if ((t1_targs[i] != TypeManager.object_type && t1_targs[i] != InternalType.Dynamic) ||
+                                                       (t2_targs[i] != TypeManager.object_type && t2_targs[i] != InternalType.Dynamic))
+                                                       return false;
+                                       }
+
+                                       return true;
+                               }
+
                                for (int i = 0; i < targs_definition.Length; ++i) {
                                        Variance v = targs_definition[i].Variance;
                                        if (v == Variance.None) {
@@ -800,6 +811,12 @@ namespace Mono.CSharp
                        state = (state & ~(StateFlags.CLSCompliant_Undetected | StateFlags.Obsolete_Undetected)) | StateFlags.CLSCompliant;
                }
 
+               public override int Arity {
+                       get {
+                               return 0;
+                       }
+               }
+
                public override string Name {
                        get {
                                return name;
@@ -812,12 +829,17 @@ namespace Mono.CSharp
                }
        }
 
-       public abstract class ElementTypeSpec : TypeSpec
+       public abstract class ElementTypeSpec : TypeSpec, ITypeDefinition
        {
                protected ElementTypeSpec (MemberKind kind, TypeSpec element, Type info)
-                       : base (kind, element.DeclaringType, element.MemberDefinition, info, element.Modifiers)
+                       : base (kind, element.DeclaringType, null, info, element.Modifiers)
                {
                        this.Element = element;
+
+                       // Has to use its own type definition instead of just element definition to
+                       // correctly identify itself for cases like x.MemberDefininition == predefined.MemberDefinition
+                       this.definition = this;
+
                        cache = MemberCache.Empty;
                }
 
@@ -859,12 +881,105 @@ namespace Mono.CSharp
                        mutated.info = null;
                        return mutated;
                }
+
+               #region ITypeDefinition Members
+
+               System.Reflection.Assembly IMemberDefinition.Assembly {
+                       get {
+                               return Element.Assembly;
+                       }
+               }
+
+               public string Namespace {
+                       get { throw new NotImplementedException (); }
+               }
+
+               public int TypeParametersCount {
+                       get {
+                               return 0;
+                       }
+               }
+
+               public TypeParameterSpec[] TypeParameters {
+                       get {
+                               throw new NotSupportedException ();
+                       }
+               }
+
+               public TypeSpec GetAttributeCoClass ()
+               {
+                       return Element.MemberDefinition.GetAttributeCoClass ();
+               }
+
+               public string GetAttributeDefaultMember ()
+               {
+                       return Element.MemberDefinition.GetAttributeDefaultMember ();
+               }
+
+               public MemberCache LoadMembers (TypeSpec declaringType)
+               {
+                       return Element.MemberDefinition.LoadMembers (declaringType);
+               }
+
+               public bool IsImported {
+                       get {
+                               return Element.MemberDefinition.IsImported;
+                       }
+               }
+
+               public string[] ConditionalConditions ()
+               {
+                       return Element.MemberDefinition.ConditionalConditions ();
+               }
+
+               bool IMemberDefinition.IsNotCLSCompliant ()
+               {
+                       return Element.MemberDefinition.IsNotCLSCompliant ();
+               }
+
+               public void SetIsAssigned ()
+               {
+                       Element.MemberDefinition.SetIsAssigned ();
+               }
+
+               public void SetIsUsed ()
+               {
+                       Element.MemberDefinition.SetIsUsed ();
+               }
+
+               #endregion
        }
 
        public class ArrayContainer : ElementTypeSpec
        {
+               struct TypeRankPair : IEquatable<TypeRankPair>
+               {
+                       TypeSpec ts;
+                       int rank;
+
+                       public TypeRankPair (TypeSpec ts, int rank)
+                       {
+                               this.ts = ts;
+                               this.rank = rank;
+                       }
+
+                       public override int GetHashCode ()
+                       {
+                               return ts.GetHashCode () ^ rank.GetHashCode ();
+                       }
+
+                       #region IEquatable<Tuple<T1,T2>> Members
+
+                       public bool Equals (TypeRankPair other)
+                       {
+                               return other.ts == ts && other.rank == rank;
+                       }
+
+                       #endregion
+               }
+
                readonly int rank;
-               static Dictionary<Tuple<TypeSpec, int>, ArrayContainer> instances = new Dictionary<Tuple<TypeSpec, int>, ArrayContainer> ();
+               static Dictionary<TypeRankPair, ArrayContainer> instances = new Dictionary<TypeRankPair, ArrayContainer> ();
 
                private ArrayContainer (TypeSpec element, int rank)
                        : base (MemberKind.ArrayType, element, null)
@@ -957,6 +1072,11 @@ namespace Mono.CSharp
                }
 
                protected override string GetPostfixSignature()
+               {
+                       return GetPostfixSignature (rank);
+               }
+
+               public static string GetPostfixSignature (int rank)
                {
                        StringBuilder sb = new StringBuilder ();
                        sb.Append ("[");
@@ -976,7 +1096,7 @@ namespace Mono.CSharp
                public static ArrayContainer MakeType (TypeSpec element, int rank)
                {
                        ArrayContainer ac;
-                       var key = Tuple.Create (element, rank);
+                       var key = new TypeRankPair (element, rank);
                        if (!instances.TryGetValue (key, out ac)) {
                                ac = new ArrayContainer (element, rank) {
                                        BaseType = TypeManager.array_type
@@ -990,7 +1110,7 @@ namespace Mono.CSharp
 
                public static void Reset ()
                {
-                       instances = new Dictionary<Tuple<TypeSpec, int>, ArrayContainer> ();
+                       instances = new Dictionary<TypeRankPair, ArrayContainer> ();
                }
        }