A type parameter can never be optional.
[mono.git] / mcs / gmcs / generic.cs
index 1e240a6e795b98bc129733d0cef4b0417deb6ed5..b21d4d372734522c007c9538c55e426dfb481274 100644 (file)
@@ -214,6 +214,14 @@ namespace Mono.CSharp {
                        get { return has_ctor_constraint; }
                }
 
+               bool GenericConstraints.IsReferenceType {
+                       get { return has_reference_type; }
+               }
+
+               bool GenericConstraints.IsValueType {
+                       get { return has_value_type; }
+               }
+
                bool GenericConstraints.HasClassConstraint {
                        get { return class_constraint_type != null; }
                }
@@ -605,11 +613,34 @@ namespace Mono.CSharp {
 
                        Expression aexpr = new EmptyExpression (atype);
 
+                       Type parent = ptype.BaseType;
+
                        //
-                       // First, check the class constraint.
+                       // First, check the `class' and `struct' constraints.
                        //
+                       if (parent == TypeManager.object_type) {
+                               if (!atype.IsClass) {
+                                       Report.Error (452, loc, "The type `{0}' must be " +
+                                                     "a reference type in order to use it " +
+                                                     "as type parameter `{1}' in the " +
+                                                     "generic type or method `{2}'.",
+                                                     atype, ptype, DeclarationName);
+                                       return false;
+                               }
+                       } else if (parent == TypeManager.value_type) {
+                               if (!atype.IsValueType) {
+                                       Report.Error (453, loc, "The type `{0}' must be " +
+                                                     "a value type in order to use it " +
+                                                     "as type parameter `{1}' in the " +
+                                                     "generic type or method `{2}'.",
+                                                     atype, ptype, DeclarationName);
+                                       return false;
+                               }
+                       }
 
-                       Type parent = ptype.BaseType;
+                       //
+                       // The class constraint comes next.
+                       //
                        if ((parent != null) && (parent != TypeManager.object_type)) {
                                if (!Convert.ImplicitStandardConversionExists (aexpr, parent)) {
                                        Report.Error (309, loc, "The type `{0}' must be " +
@@ -624,7 +655,11 @@ namespace Mono.CSharp {
                        //
                        // Now, check the interface constraints.
                        //
-                       foreach (Type itype in ptype.GetInterfaces ()) {
+                       foreach (TypeExpr iface in TypeManager.GetInterfaces (ptype)) {
+                               Type itype = iface.ResolveType (ec);
+                               if (itype == null)
+                                       return false;
+
                                if (!Convert.ImplicitStandardConversionExists (aexpr, itype)) {
                                        Report.Error (309, loc, "The type `{0}' must be " +
                                                      "convertible to `{1}' in order to " +
@@ -750,15 +785,9 @@ namespace Mono.CSharp {
                        return type;
                }
 
-               public Expression GetMemberAccess (EmitContext ec)
+               public Expression GetSimpleName (EmitContext ec)
                {
-                       TypeExpr current;
-                       if (ec.TypeContainer.CurrentType != null)
-                               current = ec.TypeContainer.CurrentType;
-                       else
-                               current = new TypeExpression (ec.ContainerType, loc);
-
-                       return new MemberAccess (current, Basename, args, loc);
+                       return new SimpleName (Basename, args, loc);
                }
 
                public override bool CheckAccessLevel (DeclSpace ds)
@@ -885,6 +914,22 @@ namespace Mono.CSharp {
                                throw new Exception ();
                        }
                }
+
+               public override void ApplyAttributeBuilder (Attribute a, CustomAttributeBuilder cb)
+               {
+                       // FIXME
+               }
+
+               protected override void VerifyObsoleteAttribute()
+               {
+                       // FIXME
+               }
+
+               public override AttributeTargets AttributeTargets {
+                       get {
+                               return AttributeTargets.Method | AttributeTargets.ReturnValue;
+                       }
+               }
        }
 
        public class DefaultValueExpression : Expression