public virtual void DefineContainerMembers ()
{
foreach (MemberCore mc in this) {
- mc.Define ();
+ try {
+ mc.Define ();
+ } catch (Exception e) {
+ throw new InternalErrorException (mc.Location, mc.GetSignatureForError (), e);
+ }
}
}
Report.Warning (659, 3, container.Location, "`{0}' overrides Object.Equals(object) but does not override Object.GetHashCode()", container.GetSignatureForError ());
}
}
-
}
public sealed class IndexerArrayList : MemberCoreArrayList
{
flags = f;
- ret_type = o.OperatorMethod.ReturnType;
- Type [] pt = o.OperatorMethod.ParameterTypes;
+ ret_type = o.MemberType;
+ Type [] pt = o.ParameterTypes;
type1 = pt [0];
type2 = pt [1];
op = o;
int reg = 0;
// Skip erroneous code.
- if (op.OperatorMethod == null)
+ if (op.MethodBuilder == null)
continue;
switch (op.OperatorType){
// Holds the operators
MemberCoreArrayList operators;
- // Holds the iterators
- ArrayList iterators;
+ // Holds the compiler generated classes
+ ArrayList compiler_generated;
//
// Pointers to the default constructor and the default static constructor
ArrayList type_bases;
+ bool members_resolved;
+ bool members_resolved_ok;
bool members_defined;
bool members_defined_ok;
Type GenericType;
GenericTypeParameterBuilder[] gen_params;
- public TypeContainer PartialContainer;
ArrayList partial_parts;
/// <remarks>
Attributes attrs, Kind kind)
: base (ns, parent, name, attrs)
{
- if (parent != null && parent != RootContext.Tree.Types && parent.NamespaceEntry != ns)
+ if (parent != null && parent.NamespaceEntry != ns)
throw new InternalErrorException ("A nested type should be in the same NamespaceEntry as its enclosing class");
this.Kind = kind;
this.PartialContainer = this;
}
- public bool AddToMemberContainer (MemberCore symbol)
+ public bool AddMember (MemberCore symbol)
{
return AddToContainer (symbol, symbol.MemberName.MethodName);
}
- protected virtual bool AddToTypeContainer (DeclSpace ds)
+ protected virtual bool AddMemberType (DeclSpace ds)
{
return AddToContainer (ds, ds.Basename);
}
public void AddConstant (Const constant)
{
- if (!AddToMemberContainer (constant))
+ if (!AddMember (constant))
return;
if (constants == null)
public void AddEnum (Mono.CSharp.Enum e)
{
- if (!AddToTypeContainer (e))
+ if (!AddMemberType (e))
return;
if (enums == null)
enums.Add (e);
}
-
- public bool AddClassOrStruct (TypeContainer c)
- {
- if (!AddToTypeContainer (c))
- return false;
- if (types == null)
- types = new ArrayList (2);
+ public TypeContainer AddTypeContainer (TypeContainer tc, bool is_interface)
+ {
+ if (!AddMemberType (tc))
+ return tc;
- RootContext.Tree.RecordDecl (c.NamespaceEntry.NS, c.MemberName, c);
- types.Add (c);
- return true;
+ if (is_interface) {
+ if (interfaces == null)
+ interfaces = new MemberCoreArrayList ();
+ interfaces.Add (tc);
+ } else {
+ if (types == null)
+ types = new ArrayList (2);
+ types.Add (tc);
+ }
+ return tc;
}
- public virtual TypeContainer AddPartial (TypeContainer nextPart)
+ public virtual TypeContainer AddPartial (TypeContainer nextPart, bool is_interface)
{
- return AddPartial (nextPart, nextPart.Basename);
+ return AddPartial (nextPart, nextPart.Basename, is_interface);
}
- protected TypeContainer AddPartial (TypeContainer nextPart, string name)
+ protected TypeContainer AddPartial (TypeContainer nextPart, string name, bool is_interface)
{
nextPart.ModFlags |= Modifiers.PARTIAL;
TypeContainer tc = defined_names [name] as TypeContainer;
- if (tc == null) {
- if (nextPart is Interface)
- AddInterface (nextPart);
- else
- AddClassOrStruct (nextPart);
- return nextPart;
- }
+ if (tc == null)
+ return AddTypeContainer (nextPart, is_interface);
if ((tc.ModFlags & Modifiers.PARTIAL) == 0) {
Report.SymbolRelatedToPreviousError (tc);
return tc;
}
+ if (tc.MemberName.IsGeneric) {
+ TypeParameter[] tc_names = tc.TypeParameters;
+ TypeParameterName[] part_names = nextPart.MemberName.TypeArguments.GetDeclarations ();
+
+ for (int i = 0; i < tc_names.Length; ++i) {
+ if (tc_names[i].Name == part_names[i].Name)
+ continue;
+
+ Report.SymbolRelatedToPreviousError (part_names[i].Location, "");
+ Report.Error (264, tc.Location, "Partial declarations of `{0}' must have the same type parameter names in the same order",
+ tc.GetSignatureForError ());
+ return tc;
+ }
+ }
+
if (tc.partial_parts == null)
tc.partial_parts = new ArrayList (1);
public void AddDelegate (Delegate d)
{
- if (!AddToTypeContainer (d))
+ if (!AddMemberType (d))
return;
if (delegates == null)
delegates = new MemberCoreArrayList ();
-
+
delegates.Add (d);
}
public void AddMethod (Method method)
{
- if (!AddToMemberContainer (method))
+ if (!AddMember (method))
return;
if (methods == null)
//
public void AppendMethod (Method method)
{
- if (!AddToMemberContainer (method))
+ if (!AddMember (method))
return;
if (methods == null)
return "`{0}' is already defined. Rename this member or use different parameter types";
}
}
-
- public bool AddInterface (TypeContainer iface)
- {
- if (!AddToTypeContainer (iface))
- return false;
-
- if (interfaces == null) {
- interfaces = new MemberCoreArrayList ();
- }
-
- RootContext.Tree.RecordDecl (iface.NamespaceEntry.NS, iface.MemberName, iface);
- interfaces.Add (iface);
- return true;
- }
public void AddField (FieldMember field)
{
- if (!AddToMemberContainer (field))
+ if (!AddMember (field))
return;
if (fields == null)
public void AddProperty (Property prop)
{
- if (!AddToMemberContainer (prop) ||
- !AddToMemberContainer (prop.Get) || !AddToMemberContainer (prop.Set))
+ if (!AddMember (prop) ||
+ !AddMember (prop.Get) || !AddMember (prop.Set))
return;
if (properties == null)
public void AddEvent (Event e)
{
- if (!AddToMemberContainer (e))
+ if (!AddMember (e))
return;
if (e is EventProperty) {
- if (!AddToMemberContainer (e.Add))
+ if (!AddMember (e.Add))
return;
- if (!AddToMemberContainer (e.Remove))
+ if (!AddMember (e.Remove))
return;
}
public void AddOperator (Operator op)
{
- if (!AddToMemberContainer (op))
+ if (!AddMember (op))
return;
if (operators == null)
operators.Add (op);
}
- public void AddIterator (Iterator i)
+ public void AddCompilerGeneratedClass (CompilerGeneratedClass c)
{
- if (iterators == null)
- iterators = new ArrayList ();
+ Report.Debug (64, "ADD COMPILER GENERATED CLASS", this, c);
- iterators.Add (i);
+ if (compiler_generated == null)
+ compiler_generated = new ArrayList ();
+
+ compiler_generated.Add (c);
}
public override void ApplyAttributeBuilder (Attribute a, CustomAttributeBuilder cb)
}
}
- public ArrayList Iterators {
+ public ArrayList CompilerGenerated {
get {
- return iterators;
+ return compiler_generated;
}
}
return base.GetClsCompliantAttributeValue ();
}
+ public void AddBasesForPart (DeclSpace part, ArrayList bases)
+ {
+ // FIXME: get rid of partial_parts and store lists of bases of each part here
+ // assumed, not verified: 'part' is in 'partial_parts'
+ ((TypeContainer) part).Bases = bases;
+ }
+
TypeExpr[] GetNormalBases (out TypeExpr base_class)
{
base_class = null;
TypeExpr [] ifaces = new TypeExpr [count-start];
for (i = start, j = 0; i < count; i++, j++){
- TypeExpr resolved = ((Expression) Bases [i]).ResolveAsTypeTerminal (this, false);
+ TypeExpr resolved = ((Expression) Bases [i]).ResolveAsBaseTerminal (this, false);
if (resolved == null) {
return null;
}
// Let's do it as soon as possible, since code below can call DefineType() on classes
// that depend on us to be populated before they are.
//
- if (!(this is Iterator))
+ if (!(this is CompilerGeneratedClass))
RootContext.RegisterOrder (this);
if (base_type != null) {
foreach (Type itype in ifaces)
TypeBuilder.AddInterfaceImplementation (itype);
+ foreach (TypeExpr ie in iface_exprs) {
+ ObsoleteAttribute oa = AttributeTester.GetObsoleteAttribute (ie.Type);
+ if ((oa != null) && !IsInObsoleteScope)
+ AttributeTester.Report_ObsoleteMessage (
+ oa, ie.GetSignatureForError (), Location);
+ }
+
if (!CheckGenericInterfaces (ifaces)) {
return false;
}
TypeManager.RegisterBuilder (TypeBuilder, ifaces);
}
- if (this is Iterator && !ResolveType ()) {
- return false;
- }
-
return true;
}
part.TypeBuilder = TypeBuilder;
}
- DefineNestedTypes ();
+ if (!(this is CompilerGeneratedClass)) {
+ if (!ResolveMembers ()) {
+ error = true;
+ return null;
+ }
+ }
+
+ if (!DefineNestedTypes ()) {
+ error = true;
+ return null;
+ }
return TypeBuilder;
}
+ public bool ResolveMembers ()
+ {
+ if (members_resolved)
+ return members_resolved_ok;
+
+ members_resolved_ok = DoResolveMembers ();
+ members_resolved = true;
+
+ return members_resolved_ok;
+ }
+
+ protected virtual bool DoResolveMembers ()
+ {
+ if (methods != null) {
+ foreach (Method method in methods) {
+ if (!method.ResolveMembers ())
+ return false;
+ }
+ }
+
+ if (instance_constructors != null) {
+ foreach (Constructor c in instance_constructors) {
+ if (!c.ResolveMembers ())
+ return false;
+ }
+ }
+
+ if (default_static_constructor != null) {
+ if (!default_static_constructor.ResolveMembers ())
+ return false;
+ }
+
+ if (operators != null) {
+ foreach (Operator o in operators) {
+ if (!o.ResolveMembers ())
+ return false;
+ }
+ }
+
+ if (properties != null) {
+ foreach (PropertyBase p in properties) {
+ if (!p.Get.IsDummy && !p.Get.ResolveMembers ())
+ return false;
+ if (!p.Set.IsDummy && !p.Set.ResolveMembers ())
+ return false;
+ }
+ }
+
+ if (indexers != null) {
+ foreach (PropertyBase p in indexers) {
+ if (!p.Get.IsDummy && !p.Get.ResolveMembers ())
+ return false;
+ if (!p.Set.IsDummy && !p.Set.ResolveMembers ())
+ return false;
+ }
+ }
+
+ return true;
+ }
+
Constraints [] constraints;
public override void SetParameterInfo (ArrayList constraints_list)
{
bool UpdateTypeParameterConstraints ()
{
- bool ok = true;
- TypeParameter[] current_params = PartialContainer.CurrentTypeParameters;
-
if (constraints == null)
return true;
+ TypeParameter[] current_params = PartialContainer.CurrentTypeParameters;
for (int i = 0; i < current_params.Length; i++) {
if (!current_params [i].UpdateConstraints (this, constraints [i])) {
- Report.Error (265, Location, "Partial declarations of `{0}' have " +
- "inconsistent constraints for type parameter `{1}'.",
- MemberName.GetTypeName (), current_params [i].Name);
- ok = false;
+ Report.SymbolRelatedToPreviousError (Location, "");
+ Report.Error (265, PartialContainer.Location,
+ "Partial declarations of `{0}' have inconsistent constraints for type parameter `{1}'",
+ PartialContainer.GetSignatureForError (), current_params [i].Name);
+ return false;
}
}
- return ok;
+ return true;
}
public bool ResolveType ()
+ {
+ if (!DoResolveType ())
+ return false;
+
+ if (compiler_generated != null) {
+ foreach (CompilerGeneratedClass c in compiler_generated)
+ if (!c.ResolveType ())
+ return false;
+ }
+
+ return true;
+ }
+
+ protected virtual bool DoResolveType ()
{
if ((base_type != null) &&
(base_type.ResolveAsTypeTerminal (this, false) == null)) {
return false;
}
+ if (compiler_generated != null) {
+ foreach (CompilerGeneratedClass c in compiler_generated) {
+ if (c.DefineType () == null)
+ return false;
+ }
+ }
+
return true;
}
}
}
+ if (!IsTopLevel && !Parent.PartialContainer.CheckRecursiveDefinition (this))
+ return false;
+
InTransit = null;
return true;
}
}
if (!IsTopLevel) {
- MemberInfo conflict_symbol = Parent.MemberCache.FindMemberWithSameName (Basename, false, TypeBuilder);
+ MemberInfo conflict_symbol = Parent.PartialContainer.FindBaseMemberWithSameName (Basename, false);
if (conflict_symbol == null) {
if ((RootContext.WarningLevel >= 4) && ((ModFlags & Modifiers.NEW) != 0))
Report.Warning (109, 4, Location, "The member `{0}' does not hide an inherited member. The new keyword is not required", GetSignatureForError ());
part.member_cache = member_cache;
}
#endif
- if (iterators != null) {
- foreach (Iterator iterator in iterators) {
- if (iterator.DefineType () == null)
- return false;
- }
-
- foreach (Iterator iterator in iterators) {
- if (!iterator.DefineMembers ())
- return false;
- }
- }
return true;
}
public override bool Define ()
{
- if (iterators != null) {
- foreach (Iterator iterator in iterators) {
- if (!iterator.Define ())
+ if (compiler_generated != null) {
+ foreach (CompilerGeneratedClass c in compiler_generated) {
+ if (!c.Define ())
return false;
}
}
public MemberInfo FindBaseMemberWithSameName (string name, bool ignore_methods)
{
- return BaseCache.FindMemberWithSameName (name, ignore_methods, null);
+ return BaseCache == null ? null : BaseCache.FindMemberWithSameName (name, ignore_methods, null);
}
/// <summary>
for (int i = 0; i < len; i++) {
Operator o = (Operator) operators [i];
- members.Add (o.OperatorMethodBuilder);
+ members.Add (o.MethodBuilder);
}
}
// Indicated whether container has StructLayout attribute set Explicit
public bool HasExplicitLayout {
- get {
- return (caching_flags & Flags.HasExplicitLayout) != 0;
- }
- set {
- caching_flags |= Flags.HasExplicitLayout;
- }
+ get { return (caching_flags & Flags.HasExplicitLayout) != 0; }
+ set { caching_flags |= Flags.HasExplicitLayout; }
}
- public override Type FindNestedType (string name)
+ //
+ // Return the nested type with name @name. Ensures that the nested type
+ // is defined if necessary. Do _not_ use this when you have a MemberCache handy.
+ //
+ public Type FindNestedType (string name)
{
if (PartialContainer != this)
- return PartialContainer.FindNestedType (name);
+ throw new InternalErrorException ("should not happen");
ArrayList [] lists = { types, enums, delegates, interfaces };
if ((o.ModFlags & static_mask) != static_flags)
continue;
- MethodBuilder ob = o.OperatorMethodBuilder;
+ MethodBuilder ob = o.MethodBuilder;
if (ob != null && filter (ob, criteria) == true) {
if (members == null)
members = new ArrayList ();
}
}
+ if (events != null) {
+ foreach (Event e in events) {
+ if ((e.ModFlags & modflags) == 0)
+ continue;
+ if ((e.ModFlags & static_mask) != static_flags)
+ continue;
+
+ MethodBuilder b = e.AddBuilder;
+ if (b != null && filter (b, criteria)) {
+ if (members == null)
+ members = new ArrayList (4);
+
+ members.Add (b);
+ }
+
+ b = e.RemoveBuilder;
+ if (b != null && filter (b, criteria)) {
+ if (members == null)
+ members = new ArrayList (4);
+
+ members.Add (b);
+ }
+ }
+ }
+
if (properties != null) {
int len = properties.Count;
for (int i = 0; i < len; i++) {
if (default_static_constructor != null)
default_static_constructor.Emit ();
-
+
if (methods != null){
foreach (Method m in methods)
m.Emit ();
if (pending.VerifyPendingMethods ())
return;
- if (iterators != null)
- foreach (Iterator iterator in iterators)
- iterator.EmitType ();
+ if (compiler_generated != null) {
+ foreach (CompilerGeneratedClass c in compiler_generated) {
+ if (!c.DefineMembers ())
+ throw new InternalErrorException ();
+ }
+ foreach (CompilerGeneratedClass c in compiler_generated)
+ c.EmitType ();
+ }
}
public override void CloseType ()
foreach (Delegate d in Delegates)
d.CloseType ();
- if (Iterators != null)
- foreach (Iterator i in Iterators)
- i.CloseType ();
+ if (CompilerGenerated != null)
+ foreach (CompilerGeneratedClass c in CompilerGenerated)
+ c.CloseType ();
types = null;
properties = null;
events = null;
indexers = null;
operators = null;
- iterators = null;
+ compiler_generated = null;
default_constructor = null;
default_static_constructor = null;
type_bases = null;
return;
}
+ if (a.Type == TypeManager.comimport_attr_type &&
+ !attributes.Contains (TypeManager.guid_attr_type)) {
+ a.Error_MissingGuidAttribute ();
+ return;
+ }
+
if (AttributeTester.IsAttributeExcluded (a.Type))
return;
}
return base.DefineType ();
- }
+ }
protected override bool DoDefineMembers ()
{
this.ModFlags = Modifiers.Check (AllowedModifiers, mod, accmods, name.Location);
}
+ public override void ApplyAttributeBuilder (Attribute a, CustomAttributeBuilder cb)
+ {
+ if (a.Type == TypeManager.comimport_attr_type &&
+ !attributes.Contains (TypeManager.guid_attr_type)) {
+ a.Error_MissingGuidAttribute ();
+ return;
+ }
+ base.ApplyAttributeBuilder (a, cb);
+ }
+
+
public override AttributeTargets AttributeTargets {
get {
return AttributeTargets.Interface;
public abstract class MethodCore : MemberBase {
public readonly Parameters Parameters;
protected ToplevelBlock block;
-
- // Whether this is an operator method.
- public Operator IsOperator;
//
// The method we're overriding if this is an override method.
//
protected MethodInfo base_method = null;
- static string[] attribute_targets = new string [] { "method", "return" };
-
public MethodCore (DeclSpace parent, GenericMethod generic,
Expression type, int mod, int allowed_mod, bool is_iface,
MemberName name, Attributes attrs, Parameters parameters)
}
}
- public void SetYields ()
+ public virtual void SetYields ()
{
ModFlags |= Modifiers.METHOD_YIELDS;
}
return true;
// Is null for System.Object while compiling corlib and base interfaces
- if (ParentContainer.BaseCache == null) {
+ if (Parent.PartialContainer.BaseCache == null) {
if ((RootContext.WarningLevel >= 4) && ((ModFlags & Modifiers.NEW) != 0)) {
Report.Warning (109, 4, Location, "The member `{0}' does not hide an inherited member. The new keyword is not required", GetSignatureForError ());
}
}
Type base_ret_type = null;
- if (IsOperator == null)
- base_method = FindOutBaseMethod (ref base_ret_type);
+ base_method = FindOutBaseMethod (ref base_ret_type);
// method is override
if (base_method != null) {
}
if (Name == "Equals" && Parameters.Count == 1 && ParameterTypes [0] == TypeManager.object_type)
- ParentContainer.Mark_HasEquals ();
+ Parent.PartialContainer.Mark_HasEquals ();
else if (Name == "GetHashCode" && Parameters.Empty)
- ParentContainer.Mark_HasGetHashCode ();
+ Parent.PartialContainer.Mark_HasGetHashCode ();
if ((ModFlags & Modifiers.OVERRIDE) != 0) {
ObsoleteAttribute oa = AttributeTester.GetMethodObsoleteAttribute (base_method);
return true;
}
- MemberInfo conflict_symbol = ParentContainer.FindBaseMemberWithSameName (Name, !(this is Property));
+ MemberInfo conflict_symbol = Parent.PartialContainer.FindBaseMemberWithSameName (Name, !(this is Property));
if ((ModFlags & Modifiers.OVERRIDE) != 0) {
if (conflict_symbol != null) {
Report.SymbolRelatedToPreviousError (conflict_symbol);
public bool CheckAbstractAndExtern (bool has_block)
{
- if (ParentContainer.Kind == Kind.Interface)
+ if (Parent.PartialContainer.Kind == Kind.Interface)
return true;
if (has_block) {
foreach (Type partype in parameters){
if (partype == TypeManager.void_type) {
- Report.Error (
- 1547, Location, "Keyword 'void' cannot " +
- "be used in this context");
+ // TODO: location is wrong
+ Expression.Error_VoidInvalidInTheContext (Location);
return false;
}
if (ds.AsAccessible (partype, ModFlags))
continue;
+ Report.SymbolRelatedToPreviousError (partype);
if (this is Indexer)
Report.Error (55, Location,
"Inconsistent accessibility: parameter type `" +
TypeManager.CSharpName (partype) + "' is less " +
"accessible than indexer `" + GetSignatureForError () + "'");
- else if ((this is Method) && ((Method) this).IsOperator != null)
+ else if (this is Operator)
Report.Error (57, Location,
"Inconsistent accessibility: parameter type `" +
TypeManager.CSharpName (partype) + "' is less " +
return !error;
}
- public override string[] ValidAttributeTargets {
- get {
- return attribute_targets;
- }
- }
-
protected override bool VerifyClsCompliance ()
{
if (!base.VerifyClsCompliance ()) {
}
- public class SourceMethod : ISourceMethod
+ public abstract class MethodOrOperator : MethodCore, IMethodData
{
- DeclSpace parent;
- MethodBase builder;
+ public MethodBuilder MethodBuilder;
+ ReturnParameter return_attributes;
+ ListDictionary declarative_security;
+ protected MethodData MethodData;
- protected SourceMethod (DeclSpace parent, MethodBase builder,
- ISourceFile file, Location start, Location end)
+ Iterator iterator;
+ ArrayList anonymous_methods;
+
+ static string[] attribute_targets = new string [] { "method", "return" };
+
+ protected MethodOrOperator (DeclSpace parent, GenericMethod generic, Expression type, int mod,
+ int allowed_mod, bool is_interface, MemberName name,
+ Attributes attrs, Parameters parameters)
+ : base (parent, generic, type, mod, allowed_mod, is_interface, name,
+ attrs, parameters)
{
- this.parent = parent;
- this.builder = builder;
-
- CodeGen.SymbolWriter.OpenMethod (file, this, start.Row, start.Column, end.Row, start.Column);
}
- public string Name {
- get { return builder.Name; }
- }
+ public override void ApplyAttributeBuilder (Attribute a, CustomAttributeBuilder cb)
+ {
+ if (a.Target == AttributeTargets.ReturnValue) {
+ if (return_attributes == null)
+ return_attributes = new ReturnParameter (MethodBuilder, Location);
- public int NamespaceID {
- get { return parent.NamespaceEntry.SymbolFileID; }
+ return_attributes.ApplyAttributeBuilder (a, cb);
+ return;
+ }
+
+ if (a.Type == TypeManager.methodimpl_attr_type &&
+ (a.GetMethodImplOptions () & MethodImplOptions.InternalCall) != 0) {
+ MethodBuilder.SetImplementationFlags (MethodImplAttributes.InternalCall | MethodImplAttributes.Runtime);
+ }
+
+ if (a.Type == TypeManager.dllimport_type) {
+ const int extern_static = Modifiers.EXTERN | Modifiers.STATIC;
+ if ((ModFlags & extern_static) != extern_static) {
+ Report.Error (601, a.Location, "The DllImport attribute must be specified on a method marked `static' and `extern'");
+ }
+
+ return;
+ }
+
+ if (a.Type.IsSubclassOf (TypeManager.security_attr_type) && a.CheckSecurityActionValidity (false)) {
+ if (declarative_security == null)
+ declarative_security = new ListDictionary ();
+ a.ExtractSecurityPermissionSet (declarative_security);
+ return;
+ }
+
+ MethodBuilder.SetCustomAttribute (cb);
}
- public int Token {
+ public override AttributeTargets AttributeTargets {
get {
- if (builder is MethodBuilder)
- return ((MethodBuilder) builder).GetToken ().Token;
- else if (builder is ConstructorBuilder)
- return ((ConstructorBuilder) builder).GetToken ().Token;
- else
- throw new NotSupportedException ();
+ return AttributeTargets.Method;
}
}
- public void CloseMethod ()
+ public virtual EmitContext CreateEmitContext (DeclSpace tc, ILGenerator ig)
{
- if (CodeGen.SymbolWriter != null)
- CodeGen.SymbolWriter.CloseMethod ();
+ return new EmitContext (
+ this, tc, this.ds, Location, ig, MemberType, ModFlags, false);
}
- public static SourceMethod Create (DeclSpace parent, MethodBase builder, Block block)
+ public void AddAnonymousMethod (AnonymousMethodExpression anonymous)
{
- if (CodeGen.SymbolWriter == null)
- return null;
- if (block == null)
- return null;
+ if (anonymous_methods == null)
+ anonymous_methods = new ArrayList ();
+ anonymous_methods.Add (anonymous);
+ }
- Location start_loc = block.StartLocation;
- if (start_loc.IsNull)
- return null;
+ protected bool DefineGenericMethod ()
+ {
+ if (!DoDefineBase ())
+ return false;
- Location end_loc = block.EndLocation;
- if (end_loc.IsNull)
- return null;
+ if (GenericMethod != null) {
+ string method_name = MemberName.Name;
- ISourceFile file = start_loc.SourceFile;
- if (file == null)
- return null;
+ if (IsExplicitImpl) {
+ method_name = TypeManager.CSharpName (InterfaceType) +
+ '.' + method_name;
+ }
+
+ MethodBuilder = Parent.TypeBuilder.DefineMethod (method_name, flags);
+
+ if (!GenericMethod.Define (MethodBuilder, block))
+ return false;
+ }
+
+ return true;
+ }
+
+ public bool ResolveMembers ()
+ {
+ if (!DefineGenericMethod ())
+ return false;
+
+ if ((ModFlags & Modifiers.METHOD_YIELDS) != 0) {
+ iterator = Iterator.CreateIterator (
+ this, Parent.PartialContainer, GenericMethod, ModFlags);
+
+ if (iterator == null)
+ return false;
+ }
+
+ if (anonymous_methods != null) {
+ foreach (AnonymousMethodExpression ame in anonymous_methods) {
+ if (!ame.CreateAnonymousHelpers ())
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ public override bool Define ()
+ {
+ if (!DoDefine ())
+ return false;
+
+ if (!CheckAbstractAndExtern (block != null))
+ return false;
+
+ if (!CheckBase ())
+ return false;
+
+ MethodData = new MethodData (
+ this, ModFlags, flags, this, MethodBuilder, GenericMethod, base_method);
+
+ if (!MethodData.Define (Parent.PartialContainer))
+ return false;
+
+ MethodBuilder = MethodData.MethodBuilder;
+
+ if (MemberType.IsAbstract && MemberType.IsSealed) {
+ Report.Error (722, Location, Error722, TypeManager.CSharpName (MemberType));
+ return false;
+ }
+
+ return true;
+ }
+
+ public override void Emit ()
+ {
+ if (OptAttributes != null)
+ OptAttributes.Emit ();
+
+ if (declarative_security != null) {
+ foreach (DictionaryEntry de in declarative_security) {
+ MethodBuilder.AddDeclarativeSecurity ((SecurityAction)de.Key, (PermissionSet)de.Value);
+ }
+ }
+
+ base.Emit ();
+ }
+
+ protected void Error_ConditionalAttributeIsNotValid ()
+ {
+ Report.Error (577, Location,
+ "Conditional not valid on `{0}' because it is a constructor, destructor, operator or explicit interface implementation",
+ GetSignatureForError ());
+ }
+
+ public override bool MarkForDuplicationCheck ()
+ {
+ caching_flags |= Flags.TestMethodDuplication;
+ return true;
+ }
+
+ public override string[] ValidAttributeTargets {
+ get {
+ return attribute_targets;
+ }
+ }
+
+ #region IMethodData Members
+
+ public CallingConventions CallingConventions {
+ get {
+ CallingConventions cc = Parameters.CallingConvention;
+ if (Parameters.HasArglist)
+ block.HasVarargs = true;
+
+ if (!IsInterface)
+ if ((ModFlags & Modifiers.STATIC) == 0)
+ cc |= CallingConventions.HasThis;
+
+ // FIXME: How is `ExplicitThis' used in C#?
+
+ return cc;
+ }
+ }
+
+ public Type ReturnType {
+ get {
+ return MemberType;
+ }
+ }
+
+ public MemberName MethodName {
+ get {
+ return MemberName;
+ }
+ }
+
+ public Iterator Iterator {
+ get { return iterator; }
+ }
+
+ public new Location Location {
+ get {
+ return base.Location;
+ }
+ }
+
+ protected override bool CheckBase() {
+ if (!base.CheckBase ())
+ return false;
+
+ // TODO: Destructor should derive from MethodCore
+ if (base_method != null && (ModFlags & Modifiers.OVERRIDE) != 0 && Name == "Finalize" &&
+ base_method.DeclaringType == TypeManager.object_type && !(this is Destructor)) {
+ Report.Error (249, Location, "Do not override object.Finalize. Instead, provide a destructor");
+ return false;
+ }
+
+ return true;
+ }
+
+ /// <summary>
+ /// Returns true if method has conditional attribute and the conditions is not defined (method is excluded).
+ /// </summary>
+ public bool IsExcluded () {
+ if ((caching_flags & Flags.Excluded_Undetected) == 0)
+ return (caching_flags & Flags.Excluded) != 0;
+
+ caching_flags &= ~Flags.Excluded_Undetected;
+
+ if (base_method == null) {
+ if (OptAttributes == null)
+ return false;
+
+ Attribute[] attrs = OptAttributes.SearchMulti (TypeManager.conditional_attribute_type);
+
+ if (attrs == null)
+ return false;
+
+ foreach (Attribute a in attrs) {
+ string condition = a.GetConditionalAttributeValue ();
+ if (condition == null)
+ return false;
+
+ if (RootContext.AllDefines.Contains (condition))
+ return false;
+ }
+
+ caching_flags |= Flags.Excluded;
+ return true;
+ }
+
+ IMethodData md = TypeManager.GetMethod (base_method);
+ if (md == null) {
+ if (AttributeTester.IsConditionalMethodExcluded (base_method)) {
+ caching_flags |= Flags.Excluded;
+ return true;
+ }
+ return false;
+ }
+
+ if (md.IsExcluded ()) {
+ caching_flags |= Flags.Excluded;
+ return true;
+ }
+ return false;
+ }
+
+ GenericMethod IMethodData.GenericMethod {
+ get {
+ return GenericMethod;
+ }
+ }
+
+ #endregion
- return new SourceMethod (
- parent, builder, file, start_loc, end_loc);
- }
}
- public class Method : MethodCore, IIteratorContainer, IMethodData {
- public MethodBuilder MethodBuilder;
- public MethodData MethodData;
- ReturnParameter return_attributes;
- ListDictionary declarative_security;
+ public class SourceMethod : ISourceMethod
+ {
+ DeclSpace parent;
+ MethodBase builder;
+
+ protected SourceMethod (DeclSpace parent, MethodBase builder,
+ ISourceFile file, Location start, Location end)
+ {
+ this.parent = parent;
+ this.builder = builder;
+
+ CodeGen.SymbolWriter.OpenMethod (file, this, start.Row, start.Column, end.Row, start.Column);
+ }
+
+ public string Name {
+ get { return builder.Name; }
+ }
+
+ public int NamespaceID {
+ get { return parent.NamespaceEntry.SymbolFileID; }
+ }
+
+ public int Token {
+ get {
+ if (builder is MethodBuilder)
+ return ((MethodBuilder) builder).GetToken ().Token;
+ else if (builder is ConstructorBuilder)
+ return ((ConstructorBuilder) builder).GetToken ().Token;
+ else
+ throw new NotSupportedException ();
+ }
+ }
+
+ public void CloseMethod ()
+ {
+ if (CodeGen.SymbolWriter != null)
+ CodeGen.SymbolWriter.CloseMethod ();
+ }
+
+ public static SourceMethod Create (DeclSpace parent, MethodBase builder, Block block)
+ {
+ if (CodeGen.SymbolWriter == null)
+ return null;
+ if (block == null)
+ return null;
+
+ Location start_loc = block.StartLocation;
+ if (start_loc.IsNull)
+ return null;
+
+ Location end_loc = block.EndLocation;
+ if (end_loc.IsNull)
+ return null;
+
+ ISourceFile file = start_loc.SourceFile;
+ if (file == null)
+ return null;
+
+ return new SourceMethod (
+ parent, builder, file, start_loc, end_loc);
+ }
+ }
+
+ public class Method : MethodOrOperator, IAnonymousHost {
/// <summary>
/// Modifiers allowed in a class declaration
Modifiers.OVERRIDE |
Modifiers.ABSTRACT |
Modifiers.UNSAFE |
- Modifiers.METHOD_YIELDS |
+ Modifiers.METHOD_YIELDS |
+ Modifiers.ANONYMOUS_HOST |
Modifiers.EXTERN;
const int AllowedInterfaceModifiers =
is_iface, name, attrs, parameters)
{
}
-
- public override AttributeTargets AttributeTargets {
- get {
- return AttributeTargets.Method;
- }
- }
public override string GetSignatureForError()
{
- if (IsOperator != null)
- return IsOperator.GetSignatureForError ();
-
return base.GetSignatureForError () + Parameters.GetSignatureForError ();
}
- void DuplicateEntryPoint (MethodInfo b, Location location)
- {
- Report.Error (
- 17, location,
- "Program `" + CodeGen.FileName +
- "' has more than one entry point defined: `" +
- TypeManager.CSharpSignature(b) + "'");
- }
-
- bool IsEntryPoint (MethodBuilder b, Parameters pinfo)
- {
- if (b.ReturnType != TypeManager.void_type &&
- b.ReturnType != TypeManager.int32_type)
- return false;
-
- if (pinfo.Count == 0)
- return true;
-
- if (pinfo.Count > 1)
- return false;
-
- Type t = pinfo.ParameterType(0);
- if (t.IsArray &&
- (t.GetArrayRank() == 1) &&
- (TypeManager.GetElementType(t) == TypeManager.string_type) &&
- (pinfo.ParameterModifier(0) == Parameter.Modifier.NONE))
- return true;
- else
- return false;
- }
-
- public override void ApplyAttributeBuilder (Attribute a, CustomAttributeBuilder cb)
+ void Error_DuplicateEntryPoint (MethodInfo b, Location location)
{
- if (a.Target == AttributeTargets.ReturnValue) {
- if (return_attributes == null)
- return_attributes = new ReturnParameter (MethodBuilder, Location);
-
- return_attributes.ApplyAttributeBuilder (a, cb);
- return;
- }
+ Report.Error (17, location,
+ "Program `{0}' has more than one entry point defined: `{1}'",
+ CodeGen.FileName, TypeManager.CSharpSignature(b));
+ }
- if (a.Type == TypeManager.methodimpl_attr_type &&
- (a.GetMethodImplOptions () & MethodImplOptions.InternalCall) != 0) {
- MethodBuilder.SetImplementationFlags (MethodImplAttributes.InternalCall | MethodImplAttributes.Runtime);
- }
+ bool IsEntryPoint (Parameters pinfo)
+ {
+ if (ReturnType != TypeManager.void_type &&
+ ReturnType != TypeManager.int32_type)
+ return false;
- if (a.Type == TypeManager.dllimport_type) {
- const int extern_static = Modifiers.EXTERN | Modifiers.STATIC;
- if ((ModFlags & extern_static) != extern_static) {
- Report.Error (601, a.Location, "The DllImport attribute must be specified on a method marked `static' and `extern'");
- }
+ if (pinfo.Count == 0)
+ return true;
- return;
- }
+ if (pinfo.Count > 1)
+ return false;
- if (a.Type.IsSubclassOf (TypeManager.security_attr_type) && a.CheckSecurityActionValidity (false)) {
- if (declarative_security == null)
- declarative_security = new ListDictionary ();
- a.ExtractSecurityPermissionSet (declarative_security);
- return;
- }
+ Type t = pinfo.ParameterType (0);
+ if (t.IsArray &&
+ (t.GetArrayRank () == 1) &&
+ (TypeManager.GetElementType (t) == TypeManager.string_type) &&
+ (pinfo.ParameterModifier (0) == Parameter.Modifier.NONE))
+ return true;
+ else
+ return false;
+ }
+ public override void ApplyAttributeBuilder (Attribute a, CustomAttributeBuilder cb)
+ {
if (a.Type == TypeManager.conditional_attribute_type) {
- if (IsOperator != null || IsExplicitImpl) {
- Report.Error (577, Location, "Conditional not valid on `{0}' because it is a constructor, destructor, operator or explicit interface implementation",
- GetSignatureForError ());
+ if (IsExplicitImpl) {
+ Error_ConditionalAttributeIsNotValid ();
return;
}
}
}
- MethodBuilder.SetCustomAttribute (cb);
+ base.ApplyAttributeBuilder (a, cb);
}
protected override bool CheckForDuplications ()
{
- ArrayList ar = ParentContainer.Methods;
+ ArrayList ar = Parent.PartialContainer.Methods;
if (ar != null) {
int arLen = ar.Count;
}
}
- ar = ParentContainer.Properties;
+ ar = Parent.PartialContainer.Properties;
if (ar != null) {
for (int i = 0; i < ar.Count; ++i) {
PropertyBase pb = (PropertyBase) ar [i];
}
}
- ar = ParentContainer.Indexers;
+ ar = Parent.PartialContainer.Indexers;
if (ar != null) {
for (int i = 0; i < ar.Count; ++i) {
PropertyBase pb = (PropertyBase) ar [i];
}
}
- ar = ParentContainer.Events;
+ ar = Parent.PartialContainer.Events;
if (ar != null) {
for (int i = 0; i < ar.Count; ++i) {
Event ev = (Event) ar [i];
if (ev.AreAccessorsDuplicateImplementation (this))
- return false;
- }
- }
-
- return true;
- }
-
- //
- // Creates the type
- //
- public override bool Define ()
- {
- if (!DoDefineBase ())
- return false;
-
- MethodBuilder mb = null;
- if (GenericMethod != null) {
- string method_name = MemberName.Name;
-
- if (IsExplicitImpl) {
- method_name = TypeManager.CSharpName (InterfaceType) +
- '.' + method_name;
- }
-
- mb = Parent.TypeBuilder.DefineMethod (method_name, flags);
-
- if (!GenericMethod.Define (mb))
- return false;
- }
-
- if (!DoDefine ())
- return false;
-
- if (!CheckAbstractAndExtern (block != null))
- return false;
-
- if (RootContext.StdLib && (ReturnType == TypeManager.arg_iterator_type || ReturnType == TypeManager.typed_reference_type)) {
- Error1599 (Location, ReturnType);
- return false;
- }
-
- if (!CheckBase ())
- return false;
-
- if (IsOperator != null)
- flags |= MethodAttributes.SpecialName | MethodAttributes.HideBySig;
-
- MethodData = new MethodData (this, ModFlags, flags, this, mb, GenericMethod, base_method);
-
- if (!MethodData.Define (ParentContainer))
- return false;
-
- if (ReturnType == TypeManager.void_type && ParameterTypes.Length == 0 &&
- Name == "Finalize" && !(this is Destructor)) {
- Report.Warning (465, 1, Location, "Introducing a 'Finalize' method can interfere with destructor invocation. Did you intend to declare a destructor?");
- }
-
- //
- // Setup iterator if we are one
- //
- if ((ModFlags & Modifiers.METHOD_YIELDS) != 0){
- Iterator iterator = new Iterator (
- this, Parent, GenericMethod, ModFlags);
-
- if (!iterator.DefineIterator ())
- return false;
- }
-
- MethodBuilder = MethodData.MethodBuilder;
-
- //
- // This is used to track the Entry Point,
- //
- if (Name == "Main" &&
- ((ModFlags & Modifiers.STATIC) != 0) && RootContext.NeedsEntryPoint &&
- (RootContext.MainClass == null ||
- RootContext.MainClass == Parent.TypeBuilder.FullName)){
- if (IsEntryPoint (MethodBuilder, ParameterInfo)) {
- IMethodData md = TypeManager.GetMethod (MethodBuilder);
- md.SetMemberIsUsed ();
-
- if (RootContext.EntryPoint == null) {
- if (Parent.IsGeneric){
- Report.Error (-201, Location,
- "Entry point can not be defined in a generic class");
- }
-
- RootContext.EntryPoint = MethodBuilder;
- RootContext.EntryPointLocation = Location;
- } else {
- DuplicateEntryPoint (RootContext.EntryPoint, RootContext.EntryPointLocation);
- DuplicateEntryPoint (MethodBuilder, Location);
- }
- } else {
- if (RootContext.WarningLevel >= 4)
- Report.Warning (28, 4, Location, "`{0}' has the wrong signature to be an entry point", TypeManager.CSharpSignature(MethodBuilder));
- }
- }
-
- if (MemberType.IsAbstract && MemberType.IsSealed) {
- Report.Error (722, Location, Error722, TypeManager.CSharpName (MemberType));
- return false;
- }
-
- return true;
- }
-
- //
- // Emits the code
- //
- public override void Emit ()
- {
- MethodData.Emit (Parent);
- base.Emit ();
-
- if (declarative_security != null) {
- foreach (DictionaryEntry de in declarative_security) {
- MethodBuilder.AddDeclarativeSecurity ((SecurityAction)de.Key, (PermissionSet)de.Value);
- }
- }
-
- Block = null;
- MethodData = null;
- }
-
- public static void Error1599 (Location loc, Type t)
- {
- Report.Error (1599, loc, "Method or delegate cannot return type `{0}'", TypeManager.CSharpName (t));
- }
-
- protected override MethodInfo FindOutBaseMethod (ref Type base_ret_type)
- {
- MethodInfo mi = (MethodInfo) ParentContainer.BaseCache.FindMemberToOverride (
- Parent.TypeBuilder, Name, ParameterTypes, GenericMethod, false);
-
- if (mi == null)
- return null;
-
- base_ret_type = mi.ReturnType;
- return mi;
- }
-
- public override bool MarkForDuplicationCheck ()
- {
- caching_flags |= Flags.TestMethodDuplication;
- return true;
- }
-
- protected override bool VerifyClsCompliance ()
- {
- if (!base.VerifyClsCompliance ())
- return false;
-
- if (ParameterInfo.Count > 0) {
- ArrayList al = (ArrayList)ParentContainer.MemberCache.Members [Name];
- if (al.Count > 1)
- MemberCache.VerifyClsParameterConflict (al, this, MethodBuilder);
- }
-
- return true;
- }
-
- #region IMethodData Members
-
- public CallingConventions CallingConventions {
- get {
- CallingConventions cc = Parameters.CallingConvention;
- if (Parameters.HasArglist)
- block.HasVarargs = true;
-
- if (!IsInterface)
- if ((ModFlags & Modifiers.STATIC) == 0)
- cc |= CallingConventions.HasThis;
-
- // FIXME: How is `ExplicitThis' used in C#?
-
- return cc;
- }
- }
-
- public Type ReturnType {
- get {
- return MemberType;
- }
- }
-
- public MemberName MethodName {
- get {
- return MemberName;
- }
- }
-
- public new Location Location {
- get {
- return base.Location;
+ return false;
+ }
}
+
+ return true;
}
- protected override bool CheckBase() {
- if (!base.CheckBase ())
+ //
+ // Creates the type
+ //
+ public override bool Define ()
+ {
+ Report.Debug (64, "METHOD DEFINE", this, Name);
+
+ if (!base.Define ())
return false;
- // TODO: Destructor should derive from MethodCore
- if (base_method != null && (ModFlags & Modifiers.OVERRIDE) != 0 && Name == "Finalize" &&
- base_method.DeclaringType == TypeManager.object_type && !(this is Destructor)) {
- Report.Error (249, Location, "Do not override object.Finalize. Instead, provide a destructor");
+ if (RootContext.StdLib && (ReturnType == TypeManager.arg_iterator_type || ReturnType == TypeManager.typed_reference_type)) {
+ Error1599 (Location, ReturnType);
return false;
}
- return true;
- }
+ if (ReturnType == TypeManager.void_type && ParameterTypes.Length == 0 &&
+ Name == "Finalize" && !(this is Destructor)) {
+ Report.Warning (465, 1, Location, "Introducing a 'Finalize' method can interfere with destructor invocation. Did you intend to declare a destructor?");
+ }
- public EmitContext CreateEmitContext (DeclSpace tc, ILGenerator ig)
- {
- EmitContext ec = new EmitContext (this,
- tc, this.ds, Location, ig, ReturnType, ModFlags, false);
+ //
+ // This is used to track the Entry Point,
+ //
+ if (RootContext.NeedsEntryPoint && ((ModFlags & Modifiers.STATIC) != 0) &&
+ Name == "Main" &&
+ (RootContext.MainClass == null ||
+ RootContext.MainClass == Parent.TypeBuilder.FullName)){
+ if (IsEntryPoint (ParameterInfo)) {
+
+ if (RootContext.EntryPoint == null) {
+ if (Parent.IsGeneric || MemberName.IsGeneric) {
+ Report.Warning (402, 4, Location, "`{0}': an entry point cannot be generic or in a generic type",
+ GetSignatureForError ());
+ } else {
+ IMethodData md = TypeManager.GetMethod (MethodBuilder);
+ md.SetMemberIsUsed ();
- Iterator iterator = tc as Iterator;
- if (iterator != null)
- ec.CurrentAnonymousMethod = iterator.Host;
+ RootContext.EntryPoint = MethodBuilder;
+ RootContext.EntryPointLocation = Location;
+ }
+ } else {
+ Error_DuplicateEntryPoint (RootContext.EntryPoint, RootContext.EntryPointLocation);
+ Error_DuplicateEntryPoint (MethodBuilder, Location);
+ }
+ } else {
+ Report.Warning (28, 4, Location, "`{0}' has the wrong signature to be an entry point",
+ GetSignatureForError ());
+ }
+ }
- return ec;
+ return true;
}
- /// <summary>
- /// Returns true if method has conditional attribute and the conditions is not defined (method is excluded).
- /// </summary>
- public bool IsExcluded ()
+ //
+ // Emits the code
+ //
+ public override void Emit ()
{
- if ((caching_flags & Flags.Excluded_Undetected) == 0)
- return (caching_flags & Flags.Excluded) != 0;
-
- caching_flags &= ~Flags.Excluded_Undetected;
+ Report.Debug (64, "METHOD EMIT", this, MethodBuilder, Location, Block, MethodData);
+ MethodData.Emit (Parent);
+ base.Emit ();
- if (base_method == null) {
- if (OptAttributes == null)
- return false;
+ Block = null;
+ MethodData = null;
+ }
- Attribute[] attrs = OptAttributes.SearchMulti (TypeManager.conditional_attribute_type);
+ public static void Error1599 (Location loc, Type t)
+ {
+ Report.Error (1599, loc, "Method or delegate cannot return type `{0}'", TypeManager.CSharpName (t));
+ }
- if (attrs == null)
- return false;
+ protected override MethodInfo FindOutBaseMethod (ref Type base_ret_type)
+ {
+ MethodInfo mi = (MethodInfo) Parent.PartialContainer.BaseCache.FindMemberToOverride (
+ Parent.TypeBuilder, Name, ParameterTypes, GenericMethod, false);
- foreach (Attribute a in attrs) {
- string condition = a.GetConditionalAttributeValue ();
- if (condition == null)
- return false;
+ if (mi == null)
+ return null;
- if (RootContext.AllDefines.Contains (condition))
- return false;
- }
+ if (mi.IsSpecialName)
+ return null;
- caching_flags |= Flags.Excluded;
- return true;
- }
+ base_ret_type = mi.ReturnType;
+ return mi;
+ }
- IMethodData md = TypeManager.GetMethod (base_method);
- if (md == null) {
- if (AttributeTester.IsConditionalMethodExcluded (base_method)) {
- caching_flags |= Flags.Excluded;
- return true;
- }
+ protected override bool VerifyClsCompliance ()
+ {
+ if (!base.VerifyClsCompliance ())
return false;
- }
- if (md.IsExcluded ()) {
- caching_flags |= Flags.Excluded;
- return true;
+ if (ParameterInfo.Count > 0) {
+ ArrayList al = (ArrayList)Parent.PartialContainer.MemberCache.Members [Name];
+ if (al.Count > 1)
+ MemberCache.VerifyClsParameterConflict (al, this, MethodBuilder);
}
- return false;
- }
- GenericMethod IMethodData.GenericMethod {
- get {
- return GenericMethod;
- }
+ return true;
}
-
- #endregion
}
public abstract class ConstructorInitializer {
}
if (error) {
+ Report.SymbolRelatedToPreviousError (base_constructor);
Expression.ErrorIsInaccesible (loc, TypeManager.CSharpSignature (base_constructor));
base_constructor = null;
return false;
}
}
- public class Constructor : MethodCore, IMethodData {
+ public class Constructor : MethodCore, IMethodData, IAnonymousHost {
public ConstructorBuilder ConstructorBuilder;
public ConstructorInitializer Initializer;
ListDictionary declarative_security;
+ ArrayList anonymous_methods;
// <summary>
// Modifiers allowed for a constructor.
Modifiers.EXTERN |
Modifiers.PRIVATE;
+ static string[] attribute_targets = new string [] { "method" };
+
+ public Iterator Iterator {
+ get { return null; }
+ }
+
bool has_compliant_args = false;
//
// The spec claims that static is not permitted, but
ConstructorBuilder.SetCustomAttribute (cb);
}
+ public void AddAnonymousMethod (AnonymousMethodExpression anonymous)
+ {
+ if (anonymous_methods == null)
+ anonymous_methods = new ArrayList ();
+ anonymous_methods.Add (anonymous);
+ }
+
+ public bool ResolveMembers ()
+ {
+ if (anonymous_methods != null) {
+ foreach (AnonymousMethodExpression ame in anonymous_methods) {
+ if (!ame.CreateAnonymousHelpers ())
+ return false;
+ }
+ }
+
+ return true;
+ }
+
protected override bool CheckForDuplications ()
{
- ArrayList ar = ParentContainer.InstanceConstructors;
+ ArrayList ar = Parent.PartialContainer.InstanceConstructors;
if (ar != null) {
int arLen = ar.Count;
if (!CheckForDuplications ())
return false;
- if (ParentContainer.Kind == Kind.Struct) {
+ if (Parent.PartialContainer.Kind == Kind.Struct) {
if (ParameterTypes.Length == 0) {
Report.Error (568, Location,
"Structs cannot contain explicit parameterless constructors");
if ((ModFlags & Modifiers.UNSAFE) != 0)
ConstructorBuilder.InitLocals = false;
- if (ParentContainer.IsComImport) {
+ if (Parent.PartialContainer.IsComImport) {
if (!IsDefault ()) {
Report.Error (669, Location, "`{0}': A class with the ComImport attribute cannot have a user-defined constructor",
Parent.GetSignatureForError ());
//
public override void Emit ()
{
+ if (OptAttributes != null)
+ OptAttributes.Emit ();
+
EmitContext ec = CreateEmitContext (null, null);
if (block != null) {
// If this is a non-static `struct' constructor and doesn't have any
// initializer, it must initialize all of the struct's fields.
- if ((ParentContainer.Kind == Kind.Struct) &&
- ((ModFlags & Modifiers.STATIC) == 0) && (Initializer == null))
+ if ((Parent.PartialContainer.Kind == Kind.Struct) &&
+ ((ModFlags & Modifiers.STATIC) == 0) && (Initializer == null))
block.AddThisVariable (Parent, Location);
if (!block.ResolveMeta (ec, ParameterInfo))
}
if ((ModFlags & Modifiers.STATIC) == 0){
- if (ParentContainer.Kind == Kind.Class && Initializer == null)
+ if (Parent.PartialContainer.Kind == Kind.Class && Initializer == null)
Initializer = new GeneratedBaseInitializer (Location);
//
// Classes can have base initializers and instance field initializers.
//
- if (ParentContainer.Kind == Kind.Class){
+ if (Parent.PartialContainer.Kind == Kind.Class){
if ((ModFlags & Modifiers.STATIC) == 0){
//
// do not emit field initializers, they are initialized in the other constructor
//
if (!(Initializer != null && Initializer is ConstructorThisInitializer))
- ParentContainer.EmitFieldInitializers (ec);
+ Parent.PartialContainer.EmitFieldInitializers (ec);
}
}
+
+ bool unreachable = false;
+ if (block != null) {
+ ec.ResolveTopBlock (null, block, ParameterInfo, this, out unreachable);
+ ec.EmitMeta (block);
+ }
+
if (Initializer != null) {
Initializer.Emit (ec);
}
if ((ModFlags & Modifiers.STATIC) != 0)
- ParentContainer.EmitFieldInitializers (ec);
-
- if (OptAttributes != null)
- OptAttributes.Emit ();
+ Parent.PartialContainer.EmitFieldInitializers (ec);
- ec.EmitTopBlock (this, block);
+ if (block != null)
+ ec.EmitResolvedTopBlock (block, unreachable);
if (source != null)
source.CloseMethod ();
return base.GetSignatureForError () + Parameters.GetSignatureForError ();
}
+ public override string[] ValidAttributeTargets {
+ get {
+ return attribute_targets;
+ }
+ }
+
protected override bool VerifyClsCompliance ()
{
if (!base.VerifyClsCompliance () || !IsExposedFromAssembly ()) {
get {
CallingConventions cc = Parameters.CallingConvention;
- if (ParentContainer.Kind == Kind.Class)
+ if (Parent.PartialContainer.Kind == Kind.Class)
if ((ModFlags & Modifiers.STATIC) == 0)
cc |= CallingConventions.HasThis;
GenericMethod GenericMethod { get; }
Parameters ParameterInfo { get; }
+ Iterator Iterator { get; }
+
Attributes OptAttributes { get; }
ToplevelBlock Block { get; set; }
string name = method.MethodName.Basename;
string method_name = method.MethodName.FullName;
- TypeContainer container = ((TypeContainer) parent).PartialContainer;
+ TypeContainer container = parent.PartialContainer;
PendingImplementation pending = container.PendingImplementations;
if (pending != null){
} else {
if (implementing != null) {
AbstractPropertyEventMethod prop_method = method as AbstractPropertyEventMethod;
- if (prop_method != null) {
+ if (prop_method == null) {
+ if (implementing.IsSpecialName) {
+ Report.SymbolRelatedToPreviousError (implementing);
+ Report.Error (470, method.Location, "Method `{0}' cannot implement interface accessor `{1}.{2}'",
+ method.GetSignatureForError (), TypeManager.CSharpSignature (implementing),
+ implementing.Name.StartsWith ("get_") ? "get" : "set");
+ return false;
+ }
+ } else if (implementing.DeclaringType.IsInterface) {
if (!implementing.IsSpecialName) {
Report.SymbolRelatedToPreviousError (implementing);
Report.Error (686, method.Location, "Accessor `{0}' cannot implement interface member `{1}' for type `{2}'. Use an explicit interface implementation",
Modifiers.Error_InvalidModifier (method.Location, "public, virtual or abstract");
implementing = null;
}
+ if (method.ParameterInfo.HasParams && !TypeManager.GetParameterData (implementing).HasParams) {
+ Report.SymbolRelatedToPreviousError (implementing);
+ Report.Error (466, method.Location, "`{0}': the explicit interface implementation cannot introduce the params modifier",
+ method.GetSignatureForError ());
+ return false;
+ }
} else if ((flags & MethodAttributes.MemberAccessMask) != MethodAttributes.Public){
if (TypeManager.IsInterfaceType (implementing.DeclaringType)){
//
method.ParameterInfo.ApplyAttributes (MethodBuilder);
- Attributes OptAttributes = method.OptAttributes;
-
- if (OptAttributes != null)
- OptAttributes.Emit ();
-
if (GenericMethod != null)
GenericMethod.EmitAttributes ();
// TODO: Should derive from MethodCore
public class Destructor : Method {
+ static string[] attribute_targets = new string [] { "method" };
+
public Destructor (DeclSpace parent, Expression return_type, int mod,
string name, Parameters parameters, Attributes attrs,
Location l)
public override void ApplyAttributeBuilder(Attribute a, CustomAttributeBuilder cb)
{
if (a.Type == TypeManager.conditional_attribute_type) {
- Report.Error (577, Location, "Conditional not valid on `{0}' because it is a constructor, destructor, operator or explicit interface implementation",
- GetSignatureForError ());
+ Error_ConditionalAttributeIsNotValid ();
return;
}
return Parent.GetSignatureForError () + ".~" + Parent.MemberName.Name + "()";
}
+ public override string[] ValidAttributeTargets {
+ get {
+ return attribute_targets;
+ }
+ }
}
abstract public class MemberBase : MemberCore {
set { SetMemberName (new MemberName (MemberName.Left, value, Location)); }
}
- public TypeContainer ParentContainer {
- get { return ((TypeContainer) Parent).PartialContainer; }
- }
-
//
// The type of this property / indexer / event
//
protected virtual bool CheckBase ()
{
- if ((ModFlags & Modifiers.PROTECTED) != 0 && ParentContainer.Kind == Kind.Struct) {
+ if ((ModFlags & Modifiers.PROTECTED) != 0 && Parent.PartialContainer.Kind == Kind.Struct) {
Report.Error (666, Location, "`{0}': new protected member declared in struct", GetSignatureForError ());
return false;
}
MethodAttributes.NewSlot |
MethodAttributes.Virtual;
} else {
- if (!ParentContainer.MethodModifiersValid (this))
+ if (!Parent.PartialContainer.MethodModifiersValid (this))
return false;
flags = Modifiers.MethodAttr (ModFlags);
return false;
}
- if (!ParentContainer.VerifyImplements (this))
+ if (!Parent.PartialContainer.VerifyImplements (this))
return false;
Modifiers.Check (Modifiers.AllowedExplicitImplFlags, explicit_mod_flags, 0, Location);
return false;
}
- if (!ParentContainer.VerifyImplements (this))
+ if (!Parent.PartialContainer.VerifyImplements (this))
return false;
Modifiers.Check (Modifiers.AllowedExplicitImplFlags, explicit_mod_flags, 0, Location);
if (IsInterface)
return true;
- conflict_symbol = ParentContainer.FindBaseMemberWithSameName (Name, false);
+ conflict_symbol = Parent.PartialContainer.FindBaseMemberWithSameName (Name, false);
if (conflict_symbol == null) {
if ((RootContext.WarningLevel >= 4) && ((ModFlags & Modifiers.NEW) != 0)) {
Report.Warning (109, 4, Location, "The member `{0}' does not hide an inherited member. The new keyword is not required", GetSignatureForError ());
set {
if (value != null) {
this.initializer = value;
- ParentContainer.RegisterFieldForInitialization (this);
+ Parent.PartialContainer.RegisterFieldForInitialization (this);
}
}
}
initializer = initializer.Resolve (ec);
if (initializer == null)
return null;
+ if (FieldBuilder == null)
+ return null;
FieldExpr fe = new FieldExpr (FieldBuilder, Location, true);
if ((ModFlags & Modifiers.STATIC) == 0)
if (c == null)
return false;
- if (MemberType == c.Type)
- return c.IsDefaultValue;
-
- if (c.Type == TypeManager.null_type)
- return true;
-
- return false;
+ return c.IsDefaultInitializer (MemberType);
}
}
{
status |= Status.HAS_OFFSET;
- if (!ParentContainer.HasExplicitLayout) {
+ if (!Parent.PartialContainer.HasExplicitLayout) {
Report.Error (636, Location, "The FieldOffset attribute can only be placed on members of types marked with the StructLayout(LayoutKind.Explicit)");
return;
}
return false;
if (MemberType == TypeManager.void_type) {
- Report.Error (1547, Location, "Keyword 'void' cannot be used in this context");
+ // TODO: wrong location
+ Expression.Error_VoidInvalidInTheContext (Location);
return false;
}
OptAttributes.Emit ();
}
- if (((status & Status.HAS_OFFSET) == 0) && (ModFlags & Modifiers.STATIC) == 0 && ParentContainer.HasExplicitLayout) {
+ if (((status & Status.HAS_OFFSET) == 0) && (ModFlags & Modifiers.STATIC) == 0 && Parent.PartialContainer.HasExplicitLayout) {
Report.Error (625, Location, "`{0}': Instance field types marked with StructLayout(LayoutKind.Explicit) must have a FieldOffset attribute.", GetSignatureForError ());
}
Report.Warning (-23, 1, Location, "Only private or internal fixed sized buffers are supported by .NET 1.x");
#endif
- if (ParentContainer.Kind != Kind.Struct) {
+ if (Parent.PartialContainer.Kind != Kind.Struct) {
Report.Error (1642, Location, "`{0}': Fixed size buffer fields may only be members of structs",
GetSignatureForError ());
return false;
FieldAttributes fa = Modifiers.FieldAttr (ModFlags);
- if (ParentContainer.Kind == Kind.Struct &&
+ if (Parent.PartialContainer.Kind == Kind.Struct &&
((fa & FieldAttributes.Static) == 0) &&
MemberType == Parent.TypeBuilder &&
!TypeManager.IsBuiltinType (MemberType)){
//
// `set' and `get' accessors are represented with an Accessor.
//
- public class Accessor : IIteratorContainer {
+ public class Accessor : IAnonymousHost {
//
// Null if the accessor is empty, or a Block if not
//
public Location Location;
public int ModFlags;
public bool Yields;
+ public ArrayList AnonymousMethods;
public Accessor (ToplevelBlock b, int mod, Attributes attrs, Location loc)
{
{
Yields = true;
}
+
+ public void AddAnonymousMethod (AnonymousMethodExpression ame)
+ {
+ if (AnonymousMethods == null)
+ AnonymousMethods = new ArrayList ();
+ AnonymousMethods.Add (ame);
+ }
}
// Ooouh Martin, templates are missing here.
#region IMethodData Members
+ public abstract Iterator Iterator {
+ get;
+ }
+
public ToplevelBlock Block {
get {
return block;
throw new NotSupportedException ();
}
- public virtual void Emit (DeclSpace parent)
+ public void Emit (DeclSpace parent)
{
EmitMethod (parent);
+ if (OptAttributes != null)
+ OptAttributes.Emit ();
+
if (declarative_security != null) {
foreach (DictionaryEntry de in declarative_security) {
method_data.MethodBuilder.AddDeclarativeSecurity ((SecurityAction)de.Key, (PermissionSet)de.Value);
{
protected readonly MethodCore method;
protected MethodAttributes flags;
+ Iterator iterator;
+ ArrayList anonymous_methods;
bool yields;
public PropertyMethod (MethodCore method, string prefix)
this.method = method;
this.ModFlags = accessor.ModFlags;
yields = accessor.Yields;
+ anonymous_methods = accessor.AnonymousMethods;
if (accessor.ModFlags != 0 && RootContext.Version == LanguageVersion.ISO_1) {
Report.FeatureIsNotStandardized (Location, "access modifiers on properties");
}
}
+ public override Iterator Iterator {
+ get { return iterator; }
+ }
+
public override AttributeTargets AttributeTargets {
get {
return AttributeTargets.Method;
return method.IsClsComplianceRequired ();
}
+ public bool ResolveMembers ()
+ {
+ TypeContainer container = ((TypeContainer) Parent).PartialContainer;
+
+ if (yields) {
+ iterator = Iterator.CreateIterator (
+ this, container, null, ModFlags);
+
+ if (iterator == null)
+ return false;
+ }
+
+ if (anonymous_methods != null) {
+ foreach (AnonymousMethodExpression ame in anonymous_methods) {
+ if (!ame.CreateAnonymousHelpers ())
+ return false;
+ }
+ }
+
+ return true;
+ }
+
public virtual MethodBuilder Define (DeclSpace parent)
{
if (!method.CheckAbstractAndExtern (block != null))
return null;
- TypeContainer container = ((TypeContainer) parent).PartialContainer;
+ TypeContainer container = parent.PartialContainer;
//
// Check for custom access modifier
flags |= (method.flags & (~MethodAttributes.MemberAccessMask));
}
- //
- // Setup iterator if we are one
- //
- if (yields) {
- Iterator iterator = new Iterator (this, Parent as TypeContainer, null, ModFlags);
-
- if (!iterator.DefineIterator ())
- return null;
- }
-
return null;
}
protected override bool CheckForDuplications ()
{
- ArrayList ar = ParentContainer.Indexers;
+ ArrayList ar = Parent.PartialContainer.Indexers;
if (ar != null) {
int arLen = ar.Count;
}
}
- ar = ParentContainer.Properties;
+ ar = Parent.PartialContainer.Properties;
if (ar != null) {
int arLen = ar.Count;
// TODO: rename to Resolve......
protected override MethodInfo FindOutBaseMethod (ref Type base_ret_type)
{
- PropertyInfo base_property = ParentContainer.BaseCache.FindMemberToOverride (
+ PropertyInfo base_property = Parent.PartialContainer.BaseCache.FindMemberToOverride (
Parent.TypeBuilder, Name, ParameterTypes, null, true) as PropertyInfo;
if (base_property == null)
this.method = method;
}
+ public override Iterator Iterator {
+ get { return null; }
+ }
+
protected override void ApplyToExtraTarget(Attribute a, CustomAttributeBuilder cb)
{
if (a.Target == AttributeTargets.Parameter) {
}
- public class Indexer : PropertyBase, IIteratorContainer {
+ public class Indexer : PropertyBase {
class GetIndexerMethod : GetMethod
{
ShortName = base_IndexerName;
}
- if (!ParentContainer.AddToMemberContainer (this) ||
- !ParentContainer.AddToMemberContainer (Get) || !ParentContainer.AddToMemberContainer (Set))
+ if (!Parent.PartialContainer.AddMember (this) ||
+ !Parent.PartialContainer.AddMember (Get) || !Parent.PartialContainer.AddMember (Set))
return false;
if (!CheckBase ())
// Setup iterator if we are one
//
if ((ModFlags & Modifiers.METHOD_YIELDS) != 0){
- Iterator iterator = new Iterator (
- Get, Parent, null, ModFlags);
+ Iterator iterator = Iterator.CreateIterator (
+ Get, (TypeContainer) Parent, null, ModFlags);
- if (!iterator.DefineIterator ())
+ if (iterator == null)
return false;
}
}
}
}
- public class Operator : MethodCore, IIteratorContainer {
+ public class Operator : MethodOrOperator, IAnonymousHost {
const int AllowedModifiers =
Modifiers.PUBLIC |
};
public readonly OpType OperatorType;
- public MethodBuilder OperatorMethodBuilder;
- public Method OperatorMethod;
-
- static string[] attribute_targets = new string [] { "method", "return" };
-
public Operator (DeclSpace parent, OpType type, Expression ret_type,
int mod_flags, Parameters parameters,
ToplevelBlock block, Attributes attrs, Location loc)
public override void ApplyAttributeBuilder (Attribute a, CustomAttributeBuilder cb)
{
- OperatorMethod.ApplyAttributeBuilder (a, cb);
- }
-
- public override AttributeTargets AttributeTargets {
- get {
- return AttributeTargets.Method;
+ if (a.Type == TypeManager.conditional_attribute_type) {
+ Error_ConditionalAttributeIsNotValid ();
+ return;
}
+
+ base.ApplyAttributeBuilder (a, cb);
}
protected override bool CheckForDuplications ()
{
- ArrayList ar = ParentContainer.Operators;
+ ArrayList ar = Parent.PartialContainer.Operators;
if (ar != null) {
int arLen = ar.Count;
}
}
- ar = ParentContainer.Methods;
+ ar = Parent.PartialContainer.Methods;
if (ar != null) {
int arLen = ar.Count;
return false;
}
- if (!DoDefine ())
+ if (!base.Define ())
return false;
if (MemberType == TypeManager.void_type) {
return false;
}
- OperatorMethod = new Method (
- Parent, null, Type, ModFlags, false, MemberName,
- Parameters, OptAttributes);
-
- OperatorMethod.Block = Block;
- OperatorMethod.IsOperator = this;
- OperatorMethod.flags |= MethodAttributes.SpecialName | MethodAttributes.HideBySig;
- OperatorMethod.Define ();
-
- if (OperatorMethod.MethodBuilder == null)
- return false;
-
- OperatorMethodBuilder = OperatorMethod.MethodBuilder;
-
- Type[] parameter_types = OperatorMethod.ParameterTypes;
- Type declaring_type = OperatorMethod.MethodData.DeclaringType;
- Type return_type = OperatorMethod.ReturnType;
- Type first_arg_type = parameter_types [0];
-
- if (!CheckBase ())
- return false;
+ Type declaring_type = MethodData.DeclaringType;
+ Type return_type = MemberType;
+ Type first_arg_type = ParameterTypes [0];
// Rules for conversion operators
return false;
}
- if (first_arg_type != declaring_type && return_type != declaring_type){
+ if ((first_arg_type != declaring_type) && (return_type != declaring_type) &&
+ !TypeManager.IsNullableTypeOf (first_arg_type, declaring_type) &&
+ !TypeManager.IsNullableTypeOf (return_type, declaring_type)) {
Report.Error (
556, Location,
"User-defined conversion must convert to or from the " +
return false;
}
} else if (OperatorType == OpType.LeftShift || OperatorType == OpType.RightShift) {
- if (first_arg_type != declaring_type || parameter_types [1] != TypeManager.int32_type) {
+ if (first_arg_type != declaring_type || ParameterTypes [1] != TypeManager.int32_type) {
Report.Error (564, Location, "Overloaded shift operator must have the type of the first operand be the containing type, and the type of the second operand must be int");
return false;
}
} else if (Parameters.Count == 1) {
// Checks for Unary operators
-
+
if (OperatorType == OpType.Increment || OperatorType == OpType.Decrement) {
- if (return_type != declaring_type && !return_type.IsSubclassOf (declaring_type)) {
+ if (return_type != declaring_type && !TypeManager.IsSubclassOf (return_type, declaring_type)) {
Report.Error (448, Location,
"The return type for ++ or -- operator must be the containing type or derived from the containing type");
return false;
}
if (first_arg_type != declaring_type){
- Report.Error (
+ Report.Error (
562, Location,
"The parameter of a unary operator must be the " +
"containing type");
- return false;
+ return false;
}
if (OperatorType == OpType.True || OperatorType == OpType.False) {
// Checks for Binary operators
if (first_arg_type != declaring_type &&
- parameter_types [1] != declaring_type){
+ ParameterTypes [1] != declaring_type){
Report.Error (
563, Location,
"One of the parameters of a binary operator must " +
return true;
}
+
+ protected override bool DoDefine ()
+ {
+ if (!base.DoDefine ())
+ return false;
+
+ flags |= MethodAttributes.SpecialName | MethodAttributes.HideBySig;
+ return true;
+ }
public override void Emit ()
{
+ base.Emit ();
+
+ Parameters.ApplyAttributes (MethodBuilder);
+
//
// abstract or extern methods have no bodies
//
if ((ModFlags & (Modifiers.ABSTRACT | Modifiers.EXTERN)) != 0)
return;
- OperatorMethod.Emit ();
+ EmitContext ec;
+ if ((flags & MethodAttributes.PinvokeImpl) == 0)
+ ec = CreateEmitContext (Parent, MethodBuilder.GetILGenerator ());
+ else
+ ec = CreateEmitContext (Parent, null);
+
+ SourceMethod source = SourceMethod.Create (Parent, MethodBuilder, Block);
+ ec.EmitTopBlock (this, Block);
+
+ if (source != null)
+ source.CloseMethod ();
+
Block = null;
}
sb.Append (Parameters.GetSignatureForError ());
return sb.ToString ();
}
-
- public override bool MarkForDuplicationCheck ()
- {
- caching_flags |= Flags.TestMethodDuplication;
- return true;
- }
-
- public override string[] ValidAttributeTargets {
- get {
- return attribute_targets;
- }
- }
}
//