//
// Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
// Copyright 2003-2008 Novell, Inc.
+// Copyright 2011 Xamarin Inc
//
using System;
// 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.BuiltinTypes, (int) data.Length, Location), new IntConstant (Compiler.BuiltinTypes, 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");
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;
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
}
}
+ public bool HasTypesFullyDefined {
+ get; set;
+ }
+
//
// Returns module global:: namespace
//
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;
}
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 ()
{
- 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 ();
throw new InternalErrorException (tc, e);
}
}
+
+ HasTypesFullyDefined = true;
}
public override void Emit ()
return DeclaringAssembly.IsCLSCompliant;
}
- protected override bool AddMemberType (TypeContainer ds)
+ protected override bool AddMemberType (TypeContainer tc)
{
- if (!AddToContainer (ds, ds.Name))
- return false;
- ds.NamespaceEntry.NS.AddType (this, ds.Definition);
- return true;
+ 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)
+ {
+ 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)
{
+ defined_type_containers.Remove (ds.MemberName);
ds.NamespaceEntry.NS.RemoveDeclSpace (ds.Basename);
base.RemoveMemberType (ds);
}
}
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;
return PartialContainer.IsClsComplianceRequired ();
}
- public override IList<MethodSpec> LookupExtensionMethod (TypeSpec extensionType, string name, int arity, ref NamespaceEntry scope)
+ public override ExtensionMethodCandidates LookupExtensionMethod (TypeSpec extensionType, string name, int arity)
{
return null;
}