X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=mcs%2Fmcs%2Froottypes.cs;h=48f2b266b3b7637a15fdbf0c15a8dfebc27f70c6;hb=f574f7b447e29c6f083fcad4e6dc5f89d3cb4b4d;hp=01c9a329e87f44dd21405fa1921be89010047220;hpb=4ce2838b7c9e6d1b042a3e13d0e2d4901fb6f938;p=mono.git diff --git a/mcs/mcs/roottypes.cs b/mcs/mcs/roottypes.cs index 01c9a329e87..48f2b266b3b 100644 --- a/mcs/mcs/roottypes.cs +++ b/mcs/mcs/roottypes.cs @@ -8,6 +8,7 @@ // // Copyright 2001-2003 Ximian, Inc (http://www.ximian.com) // Copyright 2003-2008 Novell, Inc. +// Copyright 2011 Xamarin Inc // using System; @@ -28,7 +29,7 @@ namespace Mono.CSharp // // Module (top-level type) container // - public class ModuleContainer : TypeContainer + public sealed class ModuleContainer : TypeContainer { #if STATIC // @@ -36,7 +37,7 @@ namespace Mono.CSharp // sealed class StaticDataContainer : CompilerGeneratedClass { - Dictionary size_types; + readonly Dictionary size_types; new int fields; public StaticDataContainer (ModuleContainer module) @@ -63,27 +64,14 @@ namespace Mono.CSharp // DefineInitializedData because it creates public type, // and its name is not unique among modules // - size_type = new Struct (null, this, new MemberName ("$ArrayType=" + data.Length, Location), Modifiers.PRIVATE | Modifiers.COMPILER_GENERATED, null); + size_type = new Struct (null, this, new MemberName ("$ArrayType=" + data.Length, loc), Modifiers.PRIVATE | Modifiers.COMPILER_GENERATED, null); size_type.CreateType (); size_type.DefineType (); size_types.Add (data.Length, size_type); - var ctor = Module.PredefinedMembers.StructLayoutAttributeCtor.Resolve (Location); - if (ctor != null) { - var argsEncoded = new AttributeEncoder (); - argsEncoded.Encode ((short) LayoutKind.Explicit); - - var field_size = Module.PredefinedMembers.StructLayoutSize.Resolve (Location); - var pack = Module.PredefinedMembers.StructLayoutPack.Resolve (Location); - if (field_size != null && pack != null) { - argsEncoded.EncodeNamedArguments ( - new[] { field_size, pack }, - new[] { new IntConstant (Compiler.BuildinTypes, (int) data.Length, Location), new IntConstant (Compiler.BuildinTypes, 1, Location) } - ); - - size_type.TypeBuilder.SetCustomAttribute ((ConstructorInfo) ctor.GetMetaInfo (), argsEncoded.ToArray ()); - } - } + + // It has to work even if StructLayoutAttribute does not exist + size_type.TypeBuilder.__SetLayout (1, data.Length); } var name = "$field-" + fields.ToString ("X"); @@ -118,13 +106,19 @@ namespace Mono.CSharp public CharSet? DefaultCharSet; public TypeAttributes DefaultCharSetType = TypeAttributes.AnsiClass; - Dictionary> anonymous_types; - Dictionary arrays; + readonly Dictionary> anonymous_types; + readonly Dictionary array_types; + readonly Dictionary pointer_types; + readonly Dictionary reference_types; + readonly Dictionary attrs_cache; + + // Used for unique namespaces/types during parsing + Dictionary defined_type_containers; AssemblyDefinition assembly; readonly CompilerContext context; readonly RootNamespace global_ns; - Dictionary alias_ns; + readonly Dictionary alias_ns; ModuleBuilder builder; @@ -147,14 +141,28 @@ namespace Mono.CSharp anonymous_types = new Dictionary> (); global_ns = new GlobalRootNamespace (); alias_ns = new Dictionary (); - arrays = new Dictionary (); + array_types = new Dictionary (); + pointer_types = new Dictionary (); + reference_types = new Dictionary (); + attrs_cache = new Dictionary (); + + defined_type_containers = new Dictionary (); } #region Properties - public Dictionary ArraysCache { + internal Dictionary ArrayTypesCache { + get { + return array_types; + } + } + + // + // Cache for parameter-less attributes + // + internal Dictionary AttributeConstructorCache { get { - return arrays; + return attrs_cache; } } @@ -182,6 +190,10 @@ namespace Mono.CSharp } } + internal DocumentationBuilder DocumentationBuilder { + get; set; + } + public Evaluator Evaluator { get; set; } @@ -201,6 +213,10 @@ namespace Mono.CSharp } } + public bool HasTypesFullyDefined { + get; set; + } + // // Returns module global:: namespace // @@ -216,6 +232,12 @@ namespace Mono.CSharp } } + internal Dictionary PointerTypesCache { + get { + return pointer_types; + } + } + internal PredefinedAttributes PredefinedAttributes { get { return predefined_attributes; @@ -234,6 +256,12 @@ namespace Mono.CSharp } } + internal Dictionary ReferenceTypesCache { + get { + return reference_types; + } + } + public override string[] ValidAttributeTargets { get { return attribute_targets; @@ -259,21 +287,16 @@ namespace Mono.CSharp existing.Add (type); } - public void AddAttributes (List attrs) + public void AddAttribute (Attribute attr, IMemberContext context) { - AddAttributes (attrs, this); - } - - public void AddAttributes (List attrs, IMemberContext context) - { - foreach (Attribute a in attrs) - a.AttachTo (this, context); + attr.AttachTo (this, context); if (attributes == null) { - attributes = new Attributes (attrs); + attributes = new Attributes (attr); return; } - attributes.AddAttributes (attrs); + + attributes.AddAttribute (attr); } public override TypeContainer AddPartial (TypeContainer nextPart) @@ -344,7 +367,7 @@ namespace Mono.CSharp public RootNamespace CreateRootNamespace (string alias) { if (alias == global_ns.Alias) { - NamespaceEntry.Error_GlobalNamespaceRedefined (Location.Null, Report); + RootNamespace.Error_GlobalNamespaceRedefined (Report, Location.Null); return global_ns; } @@ -365,16 +388,25 @@ namespace Mono.CSharp public new void CreateType () { + // Release cache used by parser only + if (Evaluator == null) + defined_type_containers = null; + else + defined_type_containers.Clear (); + foreach (TypeContainer tc in types) tc.CreateType (); } public new void Define () { - InitializePredefinedTypes (); - - foreach (TypeContainer tc in types) - tc.DefineType (); + foreach (TypeContainer tc in types) { + try { + tc.DefineType (); + } catch (Exception e) { + throw new InternalErrorException (tc, e); + } + } foreach (TypeContainer tc in types) tc.ResolveTypeParameters (); @@ -386,6 +418,8 @@ namespace Mono.CSharp throw new InternalErrorException (tc, e); } } + + HasTypesFullyDefined = true; } public override void Emit () @@ -416,6 +450,12 @@ namespace Mono.CSharp c.EmitType (); } + internal override void GenerateDocComment (DocumentationBuilder builder) + { + foreach (var tc in types) + tc.GenerateDocComment (builder); + } + public AnonymousTypeClass GetAnonymousType (IList parameters) { List candidates; @@ -460,16 +500,58 @@ 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 (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 (DeclSpace ds) + protected override void RemoveMemberType (TypeContainer ds) { + defined_type_containers.Remove (ds.MemberName); ds.NamespaceEntry.NS.RemoveDeclSpace (ds.Basename); base.RemoveMemberType (ds); } @@ -491,7 +573,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; @@ -532,7 +614,7 @@ namespace Mono.CSharp return PartialContainer.IsClsComplianceRequired (); } - public override IList LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope) + public override ExtensionMethodCandidates LookupExtensionMethod (TypeSpec extensionType, string name, int arity) { return null; }