Check name collision between namespaces and types
authorMarek Safar <marek.safar@gmail.com>
Fri, 1 Apr 2011 11:01:43 +0000 (12:01 +0100)
committerMarek Safar <marek.safar@gmail.com>
Fri, 1 Apr 2011 11:17:12 +0000 (12:17 +0100)
24 files changed:
mcs/class/Microsoft.CSharp/Microsoft.CSharp.RuntimeBinder/RuntimeBinderContext.cs
mcs/errors/cs0101-3.cs [new file with mode: 0644]
mcs/errors/cs0101-4.cs [new file with mode: 0644]
mcs/errors/cs0101-5.cs [new file with mode: 0644]
mcs/errors/cs0111-3.cs [deleted file]
mcs/errors/known-issues-net_4_0
mcs/mcs/assembly.cs
mcs/mcs/attribute.cs
mcs/mcs/class.cs
mcs/mcs/context.cs
mcs/mcs/cs-parser.jay
mcs/mcs/decl.cs
mcs/mcs/delegate.cs
mcs/mcs/doc.cs
mcs/mcs/driver.cs
mcs/mcs/ecore.cs
mcs/mcs/enum.cs
mcs/mcs/eval.cs
mcs/mcs/expression.cs
mcs/mcs/generic.cs
mcs/mcs/location.cs
mcs/mcs/namespace.cs
mcs/mcs/roottypes.cs
mcs/tests/test-820.cs [new file with mode: 0644]

index 8917e68fe214b07f48b2f0ae19a4613788ec4c17..ee76880214e27f1e9894ddcb541b83b3af84f533 100644 (file)
@@ -117,7 +117,7 @@ namespace Microsoft.CSharp.RuntimeBinder
                        throw new NotImplementedException ();
                }
 
-               public IList<Compiler.MethodSpec> LookupExtensionMethod (Compiler.TypeSpec extensionType, string name, int arity, ref Compiler.NamespaceEntry scope)
+               public IList<Compiler.MethodSpec> LookupExtensionMethod (Compiler.TypeSpec extensionType, string name, int arity, ref Compiler.NamespaceContainer scope)
                {
                        // No extension method lookup in this context
                        return null;
diff --git a/mcs/errors/cs0101-3.cs b/mcs/errors/cs0101-3.cs
new file mode 100644 (file)
index 0000000..991f42e
--- /dev/null
@@ -0,0 +1,13 @@
+// CS0101: The namespace `Test' already contains a definition for `Foo'
+// Line: 10
+
+namespace Test
+{
+       public class Foo
+       {
+       }
+       
+       namespace Foo
+       {
+       }
+}
diff --git a/mcs/errors/cs0101-4.cs b/mcs/errors/cs0101-4.cs
new file mode 100644 (file)
index 0000000..223247f
--- /dev/null
@@ -0,0 +1,10 @@
+// CS0101: The namespace `global::' already contains a definition for `I<T>'
+// Line: 8
+
+interface I<T>
+{
+}
+
+partial class I<T>
+{
+}
diff --git a/mcs/errors/cs0101-5.cs b/mcs/errors/cs0101-5.cs
new file mode 100644 (file)
index 0000000..51eacb8
--- /dev/null
@@ -0,0 +1,8 @@
+// CS0101: The namespace `global::' already contains a definition for `Test'
+// Line: 6
+
+class Test {}
+
+namespace Test
+{
+}
diff --git a/mcs/errors/cs0111-3.cs b/mcs/errors/cs0111-3.cs
deleted file mode 100644 (file)
index 98e8003..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-// CS0111:
-// Line: 8
-
-using System;
-
-class Test {}
-
-namespace Test
-{
-    public class Foo
-    {
-               public static void Main ()
-               {
-                       Test t = new Test ();
-               }
-    }
-}
index 130f5fecb2d8cd053b0633f5c0e907daf2989b17..20c51b15662bee70d8e774b0a7475928bb1d6629 100644 (file)
@@ -24,7 +24,6 @@ cs0122-35.cs
 cs0012-8.cs
 dcs1979.cs
 cs0023-11.cs
-cs0111-3.cs
 cs0122-19.cs
 cs0122-28.cs
 cs0168-2.cs
index ae0d6faa5ee3a8be75cfb09e39e9bc0f502f4830..1539340009f475ec2c2ca29eaf0231a24fecc6b8 100644 (file)
@@ -872,26 +872,24 @@ namespace Mono.CSharp
                        }
 
                        if (entry_point == null) {
-                               if (Compiler.Settings.MainClass != null) {
-                                       // TODO: Should use MemberCache
-                                       DeclSpace main_cont = module.GetDefinition (Compiler.Settings.MainClass) as DeclSpace;
-                                       if (main_cont == null) {
-                                               Report.Error (1555, "Could not find `{0}' specified for Main method", Compiler.Settings.MainClass);
+                               string main_class = Compiler.Settings.MainClass;
+                               if (main_class != null) {
+                                       // TODO: Handle dotted names
+                                       var texpr = module.GlobalRootNamespace.LookupType (module, main_class, 0, Location.Null);
+                                       if (texpr == null) {
+                                               Report.Error (1555, "Could not find `{0}' specified for Main method", main_class);
                                                return;
                                        }
 
-                                       if (!(main_cont is ClassOrStruct)) {
-                                               Report.Error (1556, "`{0}' specified for Main method must be a valid class or struct", Compiler.Settings.MainClass);
+                                       var mtype = texpr.Type.MemberDefinition as ClassOrStruct;
+                                       if (mtype == null) {
+                                               Report.Error (1556, "`{0}' specified for Main method must be a valid class or struct", main_class);
                                                return;
                                        }
 
-                                       Report.Error (1558, main_cont.Location, "`{0}' does not have a suitable static Main method", main_cont.GetSignatureForError ());
-                                       return;
-                               }
-
-                               if (Report.Errors == 0) {
+                                       Report.Error (1558, mtype.Location, "`{0}' does not have a suitable static Main method", mtype.GetSignatureForError ());
+                               } else {
                                        string pname = file_name == null ? name : Path.GetFileName (file_name);
-
                                        Report.Error (5001, "Program `{0}' does not contain a static `Main' method suitable for an entry point",
                                                pname);
                                }
index c5ba8f6c4e61985fa545d534aac1639a4c7d5fe4..ddd440718d9c6b438620c7d3b6c4718987bc7fb9 100644 (file)
@@ -165,7 +165,7 @@ namespace Mono.CSharp {
                        }
 
                        // When re-attaching global attributes
-                       if (context is NamespaceEntry) {
+                       if (context is NamespaceContainer) {
                                this.targets[0] = target;
                                this.context = context;
                                return;
@@ -1155,7 +1155,7 @@ namespace Mono.CSharp {
                        return true;
                }
 
-               public void ConvertGlobalAttributes (TypeContainer member, NamespaceEntry currentNamespace, bool isGlobal)
+               public void ConvertGlobalAttributes (TypeContainer member, NamespaceContainer currentNamespace, bool isGlobal)
                {
                        var member_explicit_targets = member.ValidAttributeTargets;
                        for (int i = 0; i < Attrs.Count; ++i) {
index f9c0476781a91b9ed013b1869d823d7978dea060..f4b5a18a2e5ffa58487233434ff0f0590d70521b 100644 (file)
@@ -32,12 +32,19 @@ using System.Reflection;
 using System.Reflection.Emit;
 #endif
 
-namespace Mono.CSharp {
+namespace Mono.CSharp
+{
+
+       public interface ITypesContainer
+       {
+               Location Location { get; }
+               MemberName MemberName { get; }
+       }
 
        /// <summary>
        ///   This is the base class for structs and classes.  
        /// </summary>
-       public abstract class TypeContainer : DeclSpace, ITypeDefinition
+       public abstract class TypeContainer : DeclSpace, ITypeDefinition, ITypesContainer
        {
                //
                // Different context is needed when resolving type container base
@@ -96,7 +103,7 @@ namespace Mono.CSharp {
                                return tc.GetSignatureForError ();
                        }
 
-                       public IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope)
+                       public IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceContainer scope)
                        {
                                return null;
                        }
@@ -232,7 +239,7 @@ namespace Mono.CSharp {
                /// </remarks>
                PendingImplementation pending;
 
-               public TypeContainer (NamespaceEntry ns, DeclSpace parent, MemberName name,
+               public TypeContainer (NamespaceContainer ns, DeclSpace parent, MemberName name,
                                      Attributes attrs, MemberKind kind)
                        : base (ns, parent, name, attrs)
                {
@@ -1061,11 +1068,6 @@ namespace Mono.CSharp {
                        int type_size = Kind == MemberKind.Struct && first_nonstatic_field == null ? 1 : 0;
 
                        if (IsTopLevel) {
-                               // TODO: Completely wrong
-                               if (Module.GlobalRootNamespace.IsNamespace (Name)) {
-                                       Report.Error (519, Location, "`{0}' clashes with a predefined namespace", Name);
-                               }
-
                                TypeBuilder = Module.CreateBuilder (Name, TypeAttr, type_size);
                        } else {
                                TypeBuilder = Parent.TypeBuilder.DefineNestedType (Basename, TypeAttr, null, type_size);
@@ -2280,7 +2282,7 @@ namespace Mono.CSharp {
        {
                SecurityType declarative_security;
 
-               public ClassOrStruct (NamespaceEntry ns, DeclSpace parent,
+               public ClassOrStruct (NamespaceContainer ns, DeclSpace parent,
                                      MemberName name, Attributes attrs, MemberKind kind)
                        : base (ns, parent, name, attrs, kind)
                {
@@ -2405,7 +2407,7 @@ namespace Mono.CSharp {
                        }
                }
 
-               public override IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope)
+               public override IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceContainer scope)
                {
                        DeclSpace top_level = Parent;
                        if (top_level != null) {
@@ -2445,7 +2447,7 @@ namespace Mono.CSharp {
 
                public const TypeAttributes StaticClassAttribute = TypeAttributes.Abstract | TypeAttributes.Sealed;
 
-               public Class (NamespaceEntry ns, DeclSpace parent, MemberName name, Modifiers mod,
+               public Class (NamespaceContainer ns, DeclSpace parent, MemberName name, Modifiers mod,
                              Attributes attrs)
                        : base (ns, parent, name, attrs, MemberKind.Class)
                {
@@ -2689,7 +2691,7 @@ namespace Mono.CSharp {
                        Modifiers.UNSAFE    |
                        Modifiers.PRIVATE;
 
-               public Struct (NamespaceEntry ns, DeclSpace parent, MemberName name,
+               public Struct (NamespaceContainer ns, DeclSpace parent, MemberName name,
                               Modifiers mod, Attributes attrs)
                        : base (ns, parent, name, attrs, MemberKind.Struct)
                {
@@ -2879,7 +2881,7 @@ namespace Mono.CSharp {
                        Modifiers.UNSAFE    |
                        Modifiers.PRIVATE;
 
-               public Interface (NamespaceEntry ns, DeclSpace parent, MemberName name, Modifiers mod,
+               public Interface (NamespaceContainer ns, DeclSpace parent, MemberName name, Modifiers mod,
                                  Attributes attrs)
                        : base (ns, parent, name, attrs, MemberKind.Interface)
                {
index 7715ce3d7f44adc81ae9008151aaefd20dc54b0a..ff84ce57f144be0e24ea18c8d4e82390da1c60c1 100644 (file)
@@ -52,7 +52,7 @@ namespace Mono.CSharp
 
                string GetSignatureForError ();
 
-               IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope);
+               IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceContainer scope);
                FullNamedExpression LookupNamespaceOrType (string name, int arity, Location loc, bool ignore_cs0104);
                FullNamedExpression LookupNamespaceAlias (string name);
        }
@@ -515,7 +515,7 @@ namespace Mono.CSharp
                        return MemberContext.GetSignatureForError ();
                }
 
-               public IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope)
+               public IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceContainer scope)
                {
                        return MemberContext.LookupExtensionMethod (extensionType, name, arity, ref scope);
                }
index b0daf274ddbc7a61c596bf001f387ec3f37b6971..bbc5a0401ca2db09d7d16a5db174273a96b38c1d 100644 (file)
@@ -44,7 +44,7 @@ namespace Mono.CSharp
                
                static readonly object ModifierNone = 0;
        
-               NamespaceEntry  current_namespace;
+               NamespaceContainer  current_namespace;
                TypeContainer   current_container;
                DeclSpace       current_class;
                PropertyBase current_property;
@@ -505,7 +505,8 @@ namespace_declaration
        
                module.AddAttributes (attrs, current_namespace);
                
-               current_namespace = new NamespaceEntry (module, current_namespace, file, name.GetName ());
+               current_namespace = new NamespaceContainer (name, module, current_namespace, file);
+               module.AddTypesContainer (current_namespace);
                current_class = current_namespace.SlaveDeclSpace;
                current_container = current_class.PartialContainer;
          }
@@ -6445,12 +6446,6 @@ AnonymousMethodExpression end_anonymous (ParametersBlock anon_block)
        return retval;
 }
 
-public NamespaceEntry CurrentNamespace {
-       get { 
-                  return current_namespace;
-       }
-}
-
 void Error_SyntaxError (int token)
 {
        Error_SyntaxError (0, token, "Unexpected symbol");
index 2edc8578677a62e3cf76b55778daca7ea202cc3a..28f01b7abee48c12c3671024021c25276742aaa9 100644 (file)
@@ -13,6 +13,7 @@
 
 using System;
 using System.Collections.Generic;
+using System.Diagnostics;
 
 #if NET_2_1
 using XmlElement = System.Object;
@@ -33,6 +34,7 @@ namespace Mono.CSharp {
        //
        // Better name would be DottenName
        //
+       [DebuggerDisplay ("{GetSignatureForError()}")]
        public class MemberName {
                public readonly string Name;
                public TypeArguments TypeArguments;
@@ -684,7 +686,7 @@ namespace Mono.CSharp {
                        return true;
                }
 
-               public virtual IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope)
+               public virtual IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceContainer scope)
                {
                        return Parent.LookupExtensionMethod (extensionType, name, arity, ref scope);
                }
@@ -1239,7 +1241,7 @@ namespace Mono.CSharp {
                // This is the namespace in which this typecontainer
                // was declared.  We use this to resolve names.
                //
-               public NamespaceEntry NamespaceEntry;
+               public NamespaceContainer NamespaceEntry;
 
                public readonly string Basename;
                
@@ -1268,7 +1270,7 @@ namespace Mono.CSharp {
 
                static readonly string[] attribute_targets = new string [] { "type" };
 
-               public DeclSpace (NamespaceEntry ns, DeclSpace parent, MemberName name,
+               public DeclSpace (NamespaceContainer ns, DeclSpace parent, MemberName name,
                                  Attributes attrs)
                        : base (parent, name, attrs)
                {
@@ -1311,17 +1313,13 @@ namespace Mono.CSharp {
                                return false;
                        }
 
-                       if (this is ModuleContainer) {
-                               Report.Error (101, symbol.Location, 
-                                       "The namespace `{0}' already contains a definition for `{1}'",
-                                       ((DeclSpace)symbol).NamespaceEntry.GetSignatureForError (), symbol.MemberName.Name);
-                       } else if (symbol is TypeParameter) {
+                       if (symbol is TypeParameter) {
                                Report.Error (692, symbol.Location,
                                        "Duplicate type parameter `{0}'", symbol.GetSignatureForError ());
                        } else {
                                Report.Error (102, symbol.Location,
-                                             "The type `{0}' already contains a definition for `{1}'",
-                                             GetSignatureForError (), symbol.MemberName.Name);
+                                       "The type `{0}' already contains a definition for `{1}'",
+                                       GetSignatureForError (), symbol.MemberName.Name);
                        }
 
                        return false;
index b162485472e9d66334eab9d94a9d05eb40cd26b1..4a9e0d30e9a9eeeaa6706a36c4cb3422823bbd6a 100644 (file)
@@ -54,7 +54,7 @@ namespace Mono.CSharp {
                        Modifiers.UNSAFE |
                        Modifiers.PRIVATE;
 
-               public Delegate (NamespaceEntry ns, DeclSpace parent, FullNamedExpression type,
+               public Delegate (NamespaceContainer ns, DeclSpace parent, FullNamedExpression type,
                                 Modifiers mod_flags, MemberName name, ParametersCompiled param_list,
                                 Attributes attrs)
                        : base (ns, parent, name, attrs, MemberKind.Delegate)
index c9e414d86842d14724622740ccb7ba399c34ae8e..76f513ad67c576a76f1a3d61e860804de4937b7c 100644 (file)
@@ -275,7 +275,7 @@ namespace Mono.CSharp
                        var source_file = new CompilationSourceFile ("{documentation}", "", 1);
                        var doc_module = new ModuleContainer (module.Compiler);
                        doc_module.DocumentationBuilder = this;
-                       source_file.NamespaceContainer = new NamespaceEntry (doc_module, null, source_file, null);
+                       source_file.NamespaceContainer = new NamespaceContainer (null, doc_module, null, source_file);
 
                        Report parse_report = new Report (new NullReportPrinter ());
                        var parser = new CSharpParser (seekable, source_file, parse_report);
index 9646184e4d5ac882ad8c07bc89c8949197d41177..1f6ad48f673b273ca524bea844b8c396001be9e7 100644 (file)
@@ -110,7 +110,7 @@ namespace Mono.CSharp
                
                public void Parse (SeekableStreamReader reader, CompilationSourceFile file, ModuleContainer module)
                {
-                       file.NamespaceContainer = new NamespaceEntry (module, null, file, null);
+                       file.NamespaceContainer = new NamespaceContainer (null, module, null, file);
 
                        CSharpParser parser = new CSharpParser (reader, file);
                        parser.parse ();
index ab3982cb5ffaa27fa430fb9d42208a4507d65d2a..f99bee2e034415a3f0119e4f1f9546f88c31561c 100644 (file)
@@ -2155,7 +2155,7 @@ namespace Mono.CSharp {
                                return;
                        }
 
-                       NamespaceEntry.Error_NamespaceNotFound (loc, Name, ec.Module.Compiler.Report);
+                       NamespaceContainer.Error_NamespaceNotFound (loc, Name, ec.Module.Compiler.Report);
                }
 
                protected override Expression DoResolve (ResolveContext ec)
@@ -2838,10 +2838,10 @@ namespace Mono.CSharp {
        // 
        class ExtensionMethodGroupExpr : MethodGroupExpr, OverloadResolver.IErrorHandler
        {
-               NamespaceEntry namespace_entry;
+               NamespaceContainer namespace_entry;
                public readonly Expression ExtensionExpression;
 
-               public ExtensionMethodGroupExpr (IList<MethodSpec> list, NamespaceEntry n, Expression extensionExpr, Location l)
+               public ExtensionMethodGroupExpr (IList<MethodSpec> list, NamespaceContainer n, Expression extensionExpr, Location l)
                        : base (list.Cast<MemberSpec>().ToList (), extensionExpr.Type, l)
                {
                        this.namespace_entry = n;
@@ -3200,7 +3200,7 @@ namespace Mono.CSharp {
                                return null;
 
                        int arity = type_arguments == null ? 0 : type_arguments.Count;
-                       NamespaceEntry methods_scope = null;
+                       NamespaceContainer methods_scope = null;
                        var methods = rc.LookupExtensionMethod (InstanceExpression.Type, Methods[0].Name, arity, ref methods_scope);
                        if (methods == null)
                                return null;
index 13930c7dba6eba5810bc326cf745e8641c4b7a2a..fea8319c6e44b7a86a4d5bf28ee0e3622912a05f 100644 (file)
@@ -154,7 +154,7 @@ namespace Mono.CSharp {
                        Modifiers.INTERNAL |
                        Modifiers.PRIVATE;
 
-               public Enum (NamespaceEntry ns, DeclSpace parent, TypeExpression type,
+               public Enum (NamespaceContainer ns, DeclSpace parent, TypeExpression type,
                             Modifiers mod_flags, MemberName name, Attributes attrs)
                        : base (ns, parent, name, attrs, MemberKind.Enum)
                {
index f166b5319686eadcdd7ec6ebd7da2c16a7be7be2..dcfd1cb6f8e57b23309b52749683d587ef975078 100644 (file)
@@ -76,7 +76,7 @@ namespace Mono.CSharp
                        module.Evaluator = this;
 
                        source_file = new CompilationSourceFile ("{interactive}", "", 1);
-                       source_file.NamespaceContainer = new NamespaceEntry (module, null, source_file, null);
+                       source_file.NamespaceContainer = new NamespaceContainer (null, module, null, source_file);
 
                        ctx.SourceFiles.Add (source_file);
 
index f7452d4124bb2472a7f149b78db91f67be2a120e..b49ac011bcd32a5513d473cfff3c8dea5b5c0914 100644 (file)
@@ -7596,7 +7596,7 @@ namespace Mono.CSharp
                                        // Try to look for extension method when member lookup failed
                                        //
                                        if (MethodGroupExpr.IsExtensionMethodArgument (expr)) {
-                                               NamespaceEntry scope = null;
+                                               NamespaceContainer scope = null;
                                                var methods = rc.LookupExtensionMethod (expr_type, Name, lookup_arity, ref scope);
                                                if (methods != null) {
                                                        var emg = new ExtensionMethodGroupExpr (methods, scope, expr, loc);
index 82339850e9fc8cfad3bd3bbea3a995c8f5870d38..27b1a2ee92b7883d89beb483ea70d8332ec7e919 100644 (file)
@@ -2291,14 +2291,14 @@ namespace Mono.CSharp {
        {
                ParametersCompiled parameters;
 
-               public GenericMethod (NamespaceEntry ns, DeclSpace parent, MemberName name,
+               public GenericMethod (NamespaceContainer ns, DeclSpace parent, MemberName name,
                                      FullNamedExpression return_type, ParametersCompiled parameters)
                        : base (ns, parent, name, null)
                {
                        this.parameters = parameters;
                }
 
-               public GenericMethod (NamespaceEntry ns, DeclSpace parent, MemberName name, TypeParameter[] tparams,
+               public GenericMethod (NamespaceContainer ns, DeclSpace parent, MemberName name, TypeParameter[] tparams,
                                          FullNamedExpression return_type, ParametersCompiled parameters)
                        : this (ns, parent, name, return_type, parameters)
                {
index a507c59b8afb297ffc758d7420eec5ce2cb86d7f..921141b9b36042244d987886a5c172045cf841e9 100644 (file)
@@ -84,7 +84,7 @@ namespace Mono.CSharp {
                CompileUnitEntry comp_unit;
                Dictionary<string, SourceFile> include_files;
                Dictionary<string, bool> conditionals;
-               NamespaceEntry ns_container;
+               NamespaceContainer ns_container;
 
                public CompilationSourceFile (string name, string fullPathName, int index)
                        : base (name, fullPathName, index)
@@ -99,7 +99,7 @@ namespace Mono.CSharp {
                        get { return comp_unit; }
                }
 
-               public NamespaceEntry NamespaceContainer {
+               public NamespaceContainer NamespaceContainer {
                        get {
                                return ns_container;
                        }
index 07bb0d88937015c82b9bbfd882fbdb9db0129bb7..2568886596930712ce7344347f0cd1e7ae274f1c 100644 (file)
@@ -72,14 +72,14 @@ namespace Mono.CSharp {
                }
        }
 
-       /// <summary>
-       ///   Keeps track of the namespaces defined in the C# code.
-       ///
-       ///   This is an Expression to allow it to be referenced in the
-       ///   compiler parse/intermediate tree during name resolution.
-       /// </summary>
-       public class Namespace : FullNamedExpression {
-               
+       //
+       // Namespace cache for imported and compiler namespaces
+       //
+       // This is an Expression to allow it to be referenced in the
+       // compiler parse/intermediate tree during name resolution.
+       //
+       public class Namespace : FullNamedExpression
+       {
                Namespace parent;
                string fullname;
                protected Dictionary<string, Namespace> namespaces;
@@ -521,138 +521,23 @@ namespace Mono.CSharp {
        }
 
        //
-       // Namespace container as created by the parser
+       // Namespace block as created by the parser
        //
-       public class NamespaceEntry : IMemberContext {
-
-               public class UsingEntry {
-                       readonly MemberName name;
-                       Namespace resolved;
-                       
-                       public UsingEntry (MemberName name)
-                       {
-                               this.name = name;
-                       }
-
-                       public string GetSignatureForError ()
-                       {
-                               return name.GetSignatureForError ();
-                       }
-
-                       public Location Location {
-                               get { return name.Location; }
-                       }
-
-                       public MemberName MemberName {
-                               get { return name; }
-                       }
-                       
-                       public string Name {
-                               get { return GetSignatureForError (); }
-                       }
-
-                       public Namespace Resolve (IMemberContext rc)
-                       {
-                               if (resolved != null)
-                                       return resolved;
-
-                               FullNamedExpression fne = name.GetTypeExpression ().ResolveAsTypeStep (rc, false);
-                               if (fne == null)
-                                       return null;
-
-                               resolved = fne as Namespace;
-                               if (resolved == null) {
-                                       rc.Module.Compiler.Report.SymbolRelatedToPreviousError (fne.Type);
-                                       rc.Module.Compiler.Report.Error (138, Location,
-                                               "`{0}' is a type not a namespace. A using namespace directive can only be applied to namespaces",
-                                               GetSignatureForError ());
-                               }
-                               return resolved;
-                       }
-
-                       public override string ToString ()
-                       {
-                               return Name;
-                       }
-               }
-
-               public class UsingAliasEntry {
-                       public readonly string Alias;
-                       public Location Location;
-
-                       public UsingAliasEntry (string alias, Location loc)
-                       {
-                               this.Alias = alias;
-                               this.Location = loc;
-                       }
-
-                       public virtual FullNamedExpression Resolve (IMemberContext rc, bool local)
-                       {
-                               FullNamedExpression fne = rc.Module.GetRootNamespace (Alias);
-                               if (fne == null) {
-                                       rc.Module.Compiler.Report.Error (430, Location,
-                                               "The extern alias `{0}' was not specified in -reference option",
-                                               Alias);
-                               }
-
-                               return fne;
-                       }
-
-                       public override string ToString ()
-                       {
-                               return Alias;
-                       }
-                       
-               }
-
-               class LocalUsingAliasEntry : UsingAliasEntry {
-                       FullNamedExpression resolved;
-                       MemberName value;
-
-                       public LocalUsingAliasEntry (string alias, MemberName name, Location loc)
-                               : base (alias, loc)
-                       {
-                               this.value = name;
-                       }
-
-                       public override FullNamedExpression Resolve (IMemberContext rc, bool local)
-                       {
-                               if (resolved != null || value == null)
-                                       return resolved;
-
-                               if (local)
-                                       return null;
-
-                               resolved = value.GetTypeExpression ().ResolveAsTypeStep (rc, false);
-                               if (resolved == null) {
-                                       value = null;
-                                       return null;
-                               }
-
-                               if (resolved is TypeExpr)
-                                       resolved = resolved.ResolveAsTypeTerminal (rc, false);
-
-                               return resolved;
-                       }
-
-                       public override string ToString ()
-                       {
-                               return String.Format ("{0} = {1}", Alias, value.GetSignatureForError ());
-                       }
-               }
-
+       public class NamespaceContainer : IMemberContext, ITypesContainer
+       {
                Namespace ns;
 
                readonly ModuleContainer module;
-               readonly NamespaceEntry parent;
+               readonly NamespaceContainer parent;
                readonly CompilationSourceFile file;
+               readonly Location loc;
 
-               NamespaceEntry implicit_parent;
+               NamespaceContainer implicit_parent;
                int symfile_id;
 
                // Namespace using import block
-               List<UsingAliasEntry> using_aliases;
-               List<UsingEntry> using_clauses;
+               List<NamespaceUsingAlias> using_aliases;
+               List<NamespaceUsing> using_clauses;
                public bool DeclarationFound;
                // End
 
@@ -665,23 +550,24 @@ namespace Mono.CSharp {
 
                Namespace [] namespace_using_table;
 
-               public NamespaceEntry (ModuleContainer module, NamespaceEntry parent, CompilationSourceFile sourceFile, string name)
+               public NamespaceContainer (MemberName name, ModuleContainer module, NamespaceContainer parent, CompilationSourceFile sourceFile)
                {
                        this.module = module;
                        this.parent = parent;
                        this.file = sourceFile;
+                       this.loc = name == null ? Location.Null : name.Location;
 
                        if (parent != null)
-                               ns = parent.NS.GetNamespace (name, true);
+                               ns = parent.NS.GetNamespace (name.GetName (), true);
                        else if (name != null)
-                               ns = module.GlobalRootNamespace.GetNamespace (name, true);
+                               ns = module.GlobalRootNamespace.GetNamespace (name.GetName (), true);
                        else
                                ns = module.GlobalRootNamespace;
 
                        SlaveDeclSpace = new RootDeclSpace (module, this);
                }
 
-               private NamespaceEntry (ModuleContainer module, NamespaceEntry parent, CompilationSourceFile file, Namespace ns, bool slave)
+               private NamespaceContainer (ModuleContainer module, NamespaceContainer parent, CompilationSourceFile file, Namespace ns, bool slave)
                {
                        this.module = module;
                        this.parent = parent;
@@ -691,31 +577,47 @@ namespace Mono.CSharp {
                        this.SlaveDeclSpace = slave ? new RootDeclSpace (module, this) : null;
                }
 
+               #region Properties
+
+               public Location Location {
+                       get {
+                               return loc;
+                       }
+               }
+
+               public MemberName MemberName {
+                       get {
+                               return ns.MemberName;
+                       }
+               }
+
                public CompilationSourceFile SourceFile {
                        get {
                                return file;
                        }
                }
 
-               public List<UsingEntry> Usings {
+               public List<NamespaceUsing> Usings {
                        get {
                                return using_clauses;
                        }
                }
 
+               #endregion
+
                //
                // Extracts the using alises and using clauses into a couple of
                // arrays that might already have the same information;  Used by the
                // C# Eval mode.
                //
-               public void Extract (List<UsingAliasEntry> out_using_aliases, List<UsingEntry> out_using_clauses)
+               public void Extract (List<NamespaceUsingAlias> out_using_aliases, List<NamespaceUsing> out_using_clauses)
                {
                        if (using_aliases != null){
-                               foreach (UsingAliasEntry uae in using_aliases){
+                               foreach (NamespaceUsingAlias uae in using_aliases){
                                        bool replaced = false;
                                        
                                        for (int i = 0; i < out_using_aliases.Count; i++){
-                                               UsingAliasEntry out_uea = (UsingAliasEntry) out_using_aliases [i];
+                                               NamespaceUsingAlias out_uea = (NamespaceUsingAlias) out_using_aliases [i];
                                                
                                                if (out_uea.Alias == uae.Alias){
                                                        out_using_aliases [i] = uae;
@@ -729,10 +631,10 @@ namespace Mono.CSharp {
                        }
 
                        if (using_clauses != null){
-                               foreach (UsingEntry ue in using_clauses){
+                               foreach (NamespaceUsing ue in using_clauses){
                                        bool found = false;
                                        
-                                       foreach (UsingEntry out_ue in out_using_clauses)
+                                       foreach (NamespaceUsing out_ue in out_using_clauses)
                                                if (out_ue.Name == ue.Name){
                                                        found = true;
                                                        break;
@@ -753,11 +655,11 @@ namespace Mono.CSharp {
                // To implement these rules, the expressions in the using directives are resolved using 
                // the "doppelganger" (ghostly bodiless duplicate).
                //
-               NamespaceEntry doppelganger;
-               NamespaceEntry Doppelganger {
+               NamespaceContainer doppelganger;
+               NamespaceContainer Doppelganger {
                        get {
                                if (!IsImplicit && doppelganger == null) {
-                                       doppelganger = new NamespaceEntry (module, ImplicitParent, file, ns, true);
+                                       doppelganger = new NamespaceContainer (module, ImplicitParent, file, ns, true);
                                        doppelganger.using_aliases = using_aliases;
                                }
                                return doppelganger;
@@ -768,18 +670,18 @@ namespace Mono.CSharp {
                        get { return ns; }
                }
 
-               public NamespaceEntry Parent {
+               public NamespaceContainer Parent {
                        get { return parent; }
                }
 
-               public NamespaceEntry ImplicitParent {
+               public NamespaceContainer ImplicitParent {
                        get {
                                if (parent == null)
                                        return null;
                                if (implicit_parent == null) {
                                        implicit_parent = (parent.NS == ns.Parent)
                                                ? parent
-                                               : new NamespaceEntry (module, parent, file, ns.Parent, false);
+                                               : new NamespaceContainer (module, parent, file, ns.Parent, false);
                                }
                                return implicit_parent;
                        }
@@ -795,9 +697,9 @@ namespace Mono.CSharp {
                        }
 
                        if (using_clauses == null) {
-                               using_clauses = new List<UsingEntry> ();
+                               using_clauses = new List<NamespaceUsing> ();
                        } else {
-                               foreach (UsingEntry old_entry in using_clauses) {
+                               foreach (NamespaceUsing old_entry in using_clauses) {
                                        if (name.Equals (old_entry.MemberName)) {
                                                Compiler.Report.SymbolRelatedToPreviousError (old_entry.Location, old_entry.GetSignatureForError ());
                                                Compiler.Report.Warning (105, 3, loc, "The using directive for `{0}' appeared previously in this namespace", name.GetSignatureForError ());
@@ -806,12 +708,11 @@ namespace Mono.CSharp {
                                }
                        }
 
-                       using_clauses.Add (new UsingEntry (name));
+                       using_clauses.Add (new NamespaceUsing (name));
                }
 
                public void AddUsingAlias (string alias, MemberName name, Location loc)
                {
-                       // TODO: This is parser bussines
                        if (DeclarationFound){
                                Compiler.Report.Error (1529, loc, "A using clause must precede all other namespace elements except extern alias declarations");
                        }
@@ -821,10 +722,9 @@ namespace Mono.CSharp {
 
                public void AddUsingExternalAlias (string alias, Location loc, Report Report)
                {
-                       // TODO: Do this in parser
                        bool not_first = using_clauses != null || DeclarationFound;
                        if (using_aliases != null && !not_first) {
-                               foreach (UsingAliasEntry uae in using_aliases) {
+                               foreach (NamespaceUsingAlias uae in using_aliases) {
                                        if (uae is LocalUsingAliasEntry) {
                                                not_first = true;
                                                break;
@@ -840,15 +740,15 @@ namespace Mono.CSharp {
                                return;
                        }
 
-                       AddUsingAlias (new UsingAliasEntry (alias, loc));
+                       AddUsingAlias (new NamespaceUsingAlias (alias, loc));
                }
 
-               void AddUsingAlias (UsingAliasEntry uae)
+               void AddUsingAlias (NamespaceUsingAlias uae)
                {
                        if (using_aliases == null) {
-                               using_aliases = new List<UsingAliasEntry> ();
+                               using_aliases = new List<NamespaceUsingAlias> ();
                        } else {
-                               foreach (UsingAliasEntry entry in using_aliases) {
+                               foreach (NamespaceUsingAlias entry in using_aliases) {
                                        if (uae.Alias == entry.Alias) {
                                                Compiler.Report.SymbolRelatedToPreviousError (uae.Location, uae.Alias);
                                                Compiler.Report.Error (1537, entry.Location, "The using alias `{0}' appeared previously in this namespace",
@@ -865,7 +765,7 @@ namespace Mono.CSharp {
                // Does extension methods look up to find a method which matches name and extensionType.
                // Search starts from this namespace and continues hierarchically up to top level.
                //
-               public IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope)
+               public IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceContainer scope)
                {
                        List<MethodSpec> candidates = null;
                        foreach (Namespace n in GetUsingTable ()) {
@@ -908,7 +808,7 @@ namespace Mono.CSharp {
                {
                        // Precondition: Only simple names (no dots) will be looked up with this function.
                        FullNamedExpression resolved = null;
-                       for (NamespaceEntry curr_ns = this; curr_ns != null; curr_ns = curr_ns.ImplicitParent) {
+                       for (NamespaceContainer curr_ns = this; curr_ns != null; curr_ns = curr_ns.ImplicitParent) {
                                if ((resolved = curr_ns.Lookup (name, arity, loc, ignore_cs0104)) != null)
                                        break;
                        }
@@ -920,7 +820,7 @@ namespace Mono.CSharp {
                {
                        IEnumerable<string> all = Enumerable.Empty<string> ();
                        
-                       for (NamespaceEntry curr_ns = this; curr_ns != null; curr_ns = curr_ns.ImplicitParent){
+                       for (NamespaceContainer curr_ns = this; curr_ns != null; curr_ns = curr_ns.ImplicitParent){
                                foreach (Namespace using_ns in GetUsingTable ()){
                                        if (prefix.StartsWith (using_ns.Name)){
                                                int ld = prefix.LastIndexOf ('.');
@@ -940,11 +840,11 @@ namespace Mono.CSharp {
                // Looks-up a alias named @name in this and surrounding namespace declarations
                public FullNamedExpression LookupNamespaceAlias (string name)
                {
-                       for (NamespaceEntry n = this; n != null; n = n.ImplicitParent) {
+                       for (NamespaceContainer n = this; n != null; n = n.ImplicitParent) {
                                if (n.using_aliases == null)
                                        continue;
 
-                               foreach (UsingAliasEntry ue in n.using_aliases) {
+                               foreach (NamespaceUsingAlias ue in n.using_aliases) {
                                        if (ue.Alias == name)
                                                return ue.Resolve (Doppelganger ?? this, Doppelganger == null);
                                }
@@ -964,7 +864,7 @@ namespace Mono.CSharp {
                        // Check aliases. 
                        //
                        if (using_aliases != null && arity == 0) {
-                               foreach (UsingAliasEntry ue in using_aliases) {
+                               foreach (NamespaceUsingAlias ue in using_aliases) {
                                        if (ue.Alias == name) {
                                                if (fne != null) {
                                                        if (Doppelganger != null) {
@@ -1050,7 +950,7 @@ namespace Mono.CSharp {
 
                        var list = new List<Namespace> (using_clauses.Count);
 
-                       foreach (UsingEntry ue in using_clauses) {
+                       foreach (NamespaceUsing ue in using_clauses) {
                                Namespace using_ns = ue.Resolve (Doppelganger);
                                if (using_ns == null)
                                        continue;
@@ -1071,7 +971,7 @@ namespace Mono.CSharp {
                                        if (using_clauses != null) {
                                                using_list = new string [using_clauses.Count];
                                                for (int i = 0; i < using_clauses.Count; i++)
-                                                       using_list [i] = ((UsingEntry) using_clauses [i]).MemberName.GetName ();
+                                                       using_list [i] = ((NamespaceUsing) using_clauses [i]).MemberName.GetName ();
                                        }
 
                                        symfile_id = SymbolWriter.DefineNamespace (ns.Name, file.CompileUnitEntry, using_list, parent_id);
@@ -1135,12 +1035,12 @@ namespace Mono.CSharp {
                        resolved = true;
 
                        if (using_aliases != null) {
-                               foreach (UsingAliasEntry ue in using_aliases)
+                               foreach (NamespaceUsingAlias ue in using_aliases)
                                        ue.Resolve (Doppelganger, Doppelganger == null);
                        }
 
                        if (using_clauses != null) {
-                               foreach (UsingEntry ue in using_clauses)
+                               foreach (NamespaceUsing ue in using_clauses)
                                        ue.Resolve (Doppelganger);
                        }
 
@@ -1194,4 +1094,110 @@ namespace Mono.CSharp {
 
                #endregion
        }
+
+       public class NamespaceUsing
+       {
+               readonly MemberName name;
+               Namespace resolved;
+
+               public NamespaceUsing (MemberName name)
+               {
+                       this.name = name;
+               }
+
+               public string GetSignatureForError ()
+               {
+                       return name.GetSignatureForError ();
+               }
+
+               public Location Location
+               {
+                       get { return name.Location; }
+               }
+
+               public MemberName MemberName
+               {
+                       get { return name; }
+               }
+
+               public string Name
+               {
+                       get { return GetSignatureForError (); }
+               }
+
+               public Namespace Resolve (IMemberContext rc)
+               {
+                       if (resolved != null)
+                               return resolved;
+
+                       FullNamedExpression fne = name.GetTypeExpression ().ResolveAsTypeStep (rc, false);
+                       if (fne == null)
+                               return null;
+
+                       resolved = fne as Namespace;
+                       if (resolved == null) {
+                               rc.Module.Compiler.Report.SymbolRelatedToPreviousError (fne.Type);
+                               rc.Module.Compiler.Report.Error (138, Location,
+                                       "`{0}' is a type not a namespace. A using namespace directive can only be applied to namespaces",
+                                       GetSignatureForError ());
+                       }
+                       return resolved;
+               }
+       }
+
+       public class NamespaceUsingAlias
+       {
+               public readonly string Alias;
+               public Location Location;
+
+               public NamespaceUsingAlias (string alias, Location loc)
+               {
+                       this.Alias = alias;
+                       this.Location = loc;
+               }
+
+               public virtual FullNamedExpression Resolve (IMemberContext rc, bool local)
+               {
+                       FullNamedExpression fne = rc.Module.GetRootNamespace (Alias);
+                       if (fne == null) {
+                               rc.Module.Compiler.Report.Error (430, Location,
+                                       "The extern alias `{0}' was not specified in -reference option",
+                                       Alias);
+                       }
+
+                       return fne;
+               }
+       }
+
+       class LocalUsingAliasEntry : NamespaceUsingAlias
+       {
+               FullNamedExpression resolved;
+               MemberName value;
+
+               public LocalUsingAliasEntry (string alias, MemberName name, Location loc)
+                       : base (alias, loc)
+               {
+                       this.value = name;
+               }
+
+               public override FullNamedExpression Resolve (IMemberContext rc, bool local)
+               {
+                       if (resolved != null || value == null)
+                               return resolved;
+
+                       if (local)
+                               return null;
+
+                       resolved = value.GetTypeExpression ().ResolveAsTypeStep (rc, false);
+                       if (resolved == null) {
+                               value = null;
+                               return null;
+                       }
+
+                       if (resolved is TypeExpr)
+                               resolved = resolved.ResolveAsTypeTerminal (rc, false);
+
+                       return resolved;
+               }
+       }
 }
index b179287e1d823059126ab984452c6238fca0e86a..260259037c5f1bc1ef498821d224653b6d570767 100644 (file)
@@ -124,6 +124,9 @@ namespace Mono.CSharp
                readonly Dictionary<TypeSpec, ReferenceContainer> reference_types;
                readonly Dictionary<TypeSpec, MethodSpec> attrs_cache;
 
+               // Used for unique namespaces/types during parsing
+               Dictionary<MemberName, ITypesContainer> defined_type_containers;
+
                AssemblyDefinition assembly;
                readonly CompilerContext context;
                readonly RootNamespace global_ns;
@@ -154,6 +157,8 @@ namespace Mono.CSharp
                        pointer_types = new Dictionary<TypeSpec, PointerContainer> ();
                        reference_types = new Dictionary<TypeSpec, ReferenceContainer> ();
                        attrs_cache = new Dictionary<TypeSpec, MethodSpec> ();
+
+                       defined_type_containers = new Dictionary<MemberName, ITypesContainer> ();
                }
 
                #region Properties
@@ -370,7 +375,7 @@ namespace Mono.CSharp
                public RootNamespace CreateRootNamespace (string alias)
                {
                        if (alias == global_ns.Alias) {
-                               NamespaceEntry.Error_GlobalNamespaceRedefined (Location.Null, Report);
+                               NamespaceContainer.Error_GlobalNamespaceRedefined (Location.Null, Report);
                                return global_ns;
                        }
 
@@ -391,6 +396,9 @@ namespace Mono.CSharp
 
                public new void CreateType ()
                {
+                       // Release cache used by parser only
+                       defined_type_containers = null;
+
                        foreach (TypeContainer tc in types)
                                tc.CreateType ();
                }
@@ -490,12 +498,53 @@ namespace Mono.CSharp
                        return DeclaringAssembly.IsCLSCompliant;
                }
 
-               protected override bool AddMemberType (TypeContainer ds)
+               protected override bool AddMemberType (TypeContainer tc)
+               {
+                       if (AddTypesContainer (tc)) {
+                               if ((tc.ModFlags & Modifiers.PARTIAL) != 0)
+                                       defined_names.Add (tc.Name, tc);
+
+                               tc.NamespaceEntry.NS.AddType (this, tc.Definition);
+                               return true;
+                       }
+
+                       return false;
+               }
+
+               public bool AddTypesContainer (ITypesContainer container)
                {
-                       if (!AddToContainer (ds, ds.Name))
-                               return false;
-                       ds.NamespaceEntry.NS.AddType (this, ds.Definition);
-                       return true;
+                       var mn = container.MemberName;
+                       ITypesContainer found;
+                       if (!defined_type_containers.TryGetValue (mn, out found)) {
+                               defined_type_containers.Add (mn, container);
+                               return true;
+                       }
+
+                       if (container is NamespaceContainer && found is NamespaceContainer)
+                               return true;
+
+                       var container_tc = container as TypeContainer;
+                       var found_tc = found as TypeContainer;
+                       if (container_tc != null && found_tc != null && container_tc.Kind == found_tc.Kind) {
+                               if ((found_tc.ModFlags & container_tc.ModFlags & Modifiers.PARTIAL) != 0) {
+                                       return false;
+                               }
+
+                               if (((found_tc.ModFlags | container_tc.ModFlags) & Modifiers.PARTIAL) != 0) {
+                                       Report.SymbolRelatedToPreviousError (found_tc);
+                                       Error_MissingPartialModifier (container_tc);
+                                       return false;
+                               }
+                       }
+
+                       string ns = mn.Left != null ? mn.Left.GetSignatureForError () : Module.GlobalRootNamespace.GetSignatureForError ();
+                       mn = new MemberName (mn.Name, mn.TypeArguments, mn.Location);
+
+                       Report.SymbolRelatedToPreviousError (found.Location, "");
+                       Report.Error (101, container.Location,
+                               "The namespace `{0}' already contains a definition for `{1}'",
+                               ns, mn.GetSignatureForError ());
+                       return false;
                }
 
                protected override void RemoveMemberType (TypeContainer ds)
@@ -521,7 +570,7 @@ namespace Mono.CSharp
        }
 
        sealed class RootDeclSpace : TypeContainer {
-               public RootDeclSpace (ModuleContainer module, NamespaceEntry ns)
+               public RootDeclSpace (ModuleContainer module, NamespaceContainer ns)
                        : base (ns, null, MemberName.Null, null, 0)
                {
                        PartialContainer = module;
@@ -562,7 +611,7 @@ namespace Mono.CSharp
                        return PartialContainer.IsClsComplianceRequired ();
                }
 
-               public override IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope)
+               public override IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceContainer scope)
                {
                        return null;
                }
diff --git a/mcs/tests/test-820.cs b/mcs/tests/test-820.cs
new file mode 100644 (file)
index 0000000..b682281
--- /dev/null
@@ -0,0 +1,22 @@
+// Compiler options: -main:C
+
+using System;
+
+namespace NS
+{
+       public class C
+       {
+               public static void Main ()
+               {
+                       throw new NotImplementedException ();
+               }
+       }
+}
+
+public class C
+{
+       public static int Main (string[] a)
+       {
+               return 0;
+       }
+}