//
// Authors: Miguel de Icaza (miguel@gnu.org)
// Martin Baulig (martin@gnome.org)
+// Anirban Bhattacharjee (banirban@novell.com)
//
// Licensed under the terms of the GNU GPL
//
// (C) 2001, 2002 Ximian, Inc (http://www.ximian.com)
//
//
+// 2002-10-11 Miguel de Icaza <miguel@ximian.com>
+//
+// * class.cs: Following the comment from 2002-09-26 to AddMethod, I
+// have fixed a remaining problem: not every AddXXXX was adding a
+// fully qualified name.
+//
+// Now everyone registers a fully qualified name in the DeclSpace as
+// being defined instead of the partial name.
+//
+// Downsides: we are slower than we need to be due to the excess
+// copies and the names being registered this way.
+//
+// The reason for this is that we currently depend (on the corlib
+// bootstrap for instance) that types are fully qualified, because
+// we dump all the types in the namespace, and we should really have
+// types inserted into the proper namespace, so we can only store the
+// basenames in the defined_names array.
+//
+//
#define CACHE
using System;
using System.Collections;
using System.Runtime.CompilerServices;
using System.Diagnostics.SymbolStore;
-namespace Mono.CSharp {
+namespace Mono.MonoBASIC {
/// <summary>
/// This is the base class for structs and classes.
// Holds the operators
ArrayList operators;
+ // Holds AddHandlers stements for events
+ ArrayList handlers;
+
// The emit context for toplevel objects.
EmitContext ec;
-
+
//
// Pointers to the default constructor and the default static constructor
//
public AdditionResult AddConstant (Const constant)
{
AdditionResult res;
- string name = constant.Name;
+ string basename = constant.Name;
- if ((res = IsValid (name)) != AdditionResult.Success)
+ if ((res = IsValid (basename)) != AdditionResult.Success)
return res;
if (constants == null)
constants = new ArrayList ();
constants.Add (constant);
- DefineName (name, constant);
+ DefineName (Name + "." + basename, constant);
return AdditionResult.Success;
}
- public AdditionResult AddEnum (Mono.CSharp.Enum e)
+ public AdditionResult AddEnum (Mono.MonoBASIC.Enum e)
{
AdditionResult res;
- string name = e.Name;
- if ((res = IsValid (name)) != AdditionResult.Success)
+ if ((res = IsValid (e.Basename)) != AdditionResult.Success)
return res;
if (enums == null)
enums = new ArrayList ();
enums.Add (e);
- DefineName (name, e);
+ DefineName (e.Name, e);
return AdditionResult.Success;
}
public AdditionResult AddClass (Class c)
{
AdditionResult res;
- string name = c.Name;
-
-
- if ((res = IsValid (name)) != AdditionResult.Success)
+
+ if ((res = IsValid (c.Basename)) != AdditionResult.Success)
return res;
-
- DefineName (name, c);
+
+
+
+ DefineName (c.Name, c);
types.Add (c);
-
+
+ // FIXME: Do we really need to explicitly add an empty default static constructor?
+ // Apparently we don't
+/* if (c.default_static_constructor == null)
+ {
+ bool isModule = c is Mono.MonoBASIC.Module;
+ Constructor dc = new Constructor ("New", Parameters.EmptyReadOnlyParameters, null, c.Location);
+ dc.ModFlags = isModule ? Modifiers.PUBLIC | Modifiers.STATIC : Modifiers.PUBLIC;
+ c.AddConstructor (dc);
+ }
+*/
+ //--------------------------------------------------------------
+
return AdditionResult.Success;
}
public AdditionResult AddStruct (Struct s)
{
AdditionResult res;
- string name = s.Name;
- if ((res = IsValid (name)) != AdditionResult.Success)
+ if ((res = IsValid (s.Basename)) != AdditionResult.Success)
return res;
- DefineName (name, s);
+ DefineName (s.Name, s);
types.Add (s);
return AdditionResult.Success;
public AdditionResult AddDelegate (Delegate d)
{
AdditionResult res;
- string name = d.Name;
- if ((res = IsValid (name)) != AdditionResult.Success)
+ if ((res = IsValid (d.Basename)) != AdditionResult.Success)
return res;
if (delegates == null)
delegates = new ArrayList ();
- DefineName (name, d);
+ DefineName (d.Name, d);
delegates.Add (d);
return AdditionResult.Success;
public AdditionResult AddMethod (Method method)
{
- string name = method.Name;
- Object value = defined_names [name];
-
+ string basename = method.Name;
+ string fullname = Name + "." + basename;
+
+ Object value = defined_names [fullname];
+
if (value != null && (!(value is Method)))
return AdditionResult.NameExists;
- if (name == Basename)
+ if (basename == Basename)
return AdditionResult.EnclosingClash;
-
+
if (methods == null)
methods = new ArrayList ();
else
methods.Add (method);
- if (value != null)
- DefineName (name, method);
+ if (value == null)
+ DefineName (fullname, method);
return AdditionResult.Success;
}
public AdditionResult AddConstructor (Constructor c)
{
- if (c.Name != Basename)
+ if (c.Name != "New")
return AdditionResult.NotAConstructor;
bool is_static = (c.ModFlags & Modifiers.STATIC) != 0;
-
+
if (is_static){
have_static_constructor = true;
if (default_static_constructor != null){
default_static_constructor = c;
} else {
if (c.IsDefault ()){
- if (default_constructor != null)
- return AdditionResult.MethodExists;
+ /*if (default_constructor != null)
+ return AdditionResult.MethodExists;*/
default_constructor = c;
}
public AdditionResult AddInterface (Interface iface)
{
AdditionResult res;
- string name = iface.Name;
- if ((res = IsValid (name)) != AdditionResult.Success)
+ if ((res = IsValid (iface.Basename)) != AdditionResult.Success)
return res;
if (interfaces == null)
interfaces = new ArrayList ();
interfaces.Add (iface);
- DefineName (name, iface);
+ DefineName (iface.Name, iface);
return AdditionResult.Success;
}
public AdditionResult AddField (Field field)
{
AdditionResult res;
- string name = field.Name;
+ string basename = field.Name;
- if ((res = IsValid (name)) != AdditionResult.Success)
+ if ((res = IsValid (basename)) != AdditionResult.Success)
return res;
if (fields == null)
fields.Add (field);
- if (field.HasInitializer){
- if ((field.ModFlags & Modifiers.STATIC) != 0){
+ if (field.HasInitializer){
+ if ((field.ModFlags & Modifiers.STATIC) != 0) {
if (initialized_static_fields == null)
initialized_static_fields = new ArrayList ();
if ((field.ModFlags & Modifiers.STATIC) == 0)
have_nonstatic_fields = true;
- DefineName (name, field);
+ DefineName (Name + "." + basename, field);
return AdditionResult.Success;
}
public AdditionResult AddProperty (Property prop)
{
AdditionResult res;
- string name = prop.Name;
+ string basename = prop.Name;
- if ((res = IsValid (name)) != AdditionResult.Success)
+ if ((res = IsValid (basename)) != AdditionResult.Success)
return res;
if (properties == null)
properties.Insert (0, prop);
else
properties.Add (prop);
- DefineName (name, prop);
+ DefineName (Name + "." + basename, prop);
return AdditionResult.Success;
}
public AdditionResult AddEvent (Event e)
{
AdditionResult res;
- string name = e.Name;
+ string basename = e.Name;
- if ((res = IsValid (name)) != AdditionResult.Success)
+ if ((res = IsValid (basename)) != AdditionResult.Success)
return res;
if (events == null)
events = new ArrayList ();
events.Add (e);
- DefineName (name, e);
+ DefineName (Name + "." + basename, e);
return AdditionResult.Success;
}
return AdditionResult.Success;
}
+ public AdditionResult AddEventHandler (Statement stmt)
+ {
+ if (handlers == null)
+ handlers = new ArrayList ();
+
+ handlers.Add (stmt);
+ return AdditionResult.Success;
+ }
+
public void RegisterOrder (Interface iface)
{
if (interface_order == null)
}
}
+ public ArrayList EventHandlers {
+ get {
+ return handlers;
+ }
+ }
+
//
// Emits the instance field initializers
//
Constructor c;
int mods = 0;
- c = new Constructor (Basename, Parameters.EmptyReadOnlyParameters,
- new ConstructorBaseInitializer (
- null, Parameters.EmptyReadOnlyParameters,
- Location.Null),
+ c = new Constructor ("New", Parameters.EmptyReadOnlyParameters,
+ null,
Location.Null);
- if (is_static)
+ if (is_static) {
mods = Modifiers.STATIC;
-
- c.ModFlags = mods;
+ c.ModFlags = mods;
+ }
+ else
+ c.Initializer = new ConstructorBaseInitializer (
+ null, Parameters.EmptyReadOnlyParameters,
+ Location.Null);
AddConstructor (c);
foreach (Field f in initialized_fields){
Report.Error (
- 573, Location,
+ 31049, Location,
"`" + n + "." + f.Name + "': can not have " +
"instance field initializers in structs");
}
start = 0;
}
+ if (parent.IsSealed )
+ Report.Error (30299, Location,
+ "Class " + Name + " cannot inherit " +
+ "'NotInheritable' class " + TypeManager.MonoBASIC_Name (parent));
+
if (!AsAccessible (parent, ModFlags))
- Report.Error (60, Location,
+ Report.Error (30389, Location,
"Inconsistent accessibility: base class `" +
- TypeManager.CSharpName (parent) + "' is less " +
+ TypeManager.MonoBASIC_Name (parent) + "' is less " +
"accessible than class `" +
Name + "'");
Expression resolved = ResolveTypeExpr (name, false, Location);
bases [i] = resolved;
Type t = resolved.Type;
-
+
if (t == null){
error = true;
return null;
error = true;
return null;
}
-
+
if (t.IsSealed) {
- string detail = "";
-
- if (t.IsValueType)
- detail = " (a class can not inherit from a struct/enum)";
+ if (t.IsValueType)\r
+ Report.Error (30258, "class `"+ Name +
+ "': a class can not inherit from a struct/enum");
- Report.Error (509, "class `"+ Name +
+ /*Report.Error (509, "class `"+ Name +
"': Cannot inherit from sealed class `"+
- bases [i]+"'"+detail);
+ bases [i]);*/
error = true;
return null;
}
if (t.IsClass) {
if (parent != null){
- Report.Error (527, "In Class `" + Name + "', type `"+
- name+"' is not an interface");
+ Report.Error (30121, Name + ": A class cannot inherit " +
+ "more than one class");
error = true;
return null;
}
else
is_class = false;
- ec = new EmitContext (this, Mono.CSharp.Location.Null, null, null, ModFlags);
+ ec = new EmitContext (this, Mono.MonoBASIC.Location.Null, null, null, ModFlags);
+ if (((ModFlags & Modifiers.ABSTRACT ) != 0) &&
+ ((ModFlags & Modifiers.SEALED) != 0)){
+ Report.Error (31408, Location,
+ "Class declared as 'MustInherit' cannot be declared as 'NotInheritable'");
+ }
+
ifaces = GetClassBases (is_class, out parent, out error);
if (error)
return null;
+ if (this is Interface)
+ parent = null;
+
if (is_class && parent != null){
if (parent == TypeManager.enum_type ||
(parent == TypeManager.value_type && RootContext.StdLib) ||
parent == TypeManager.array_type){
Report.Error (
644, Location, "`" + Name + "' cannot inherit from " +
- "special class `" + TypeManager.CSharpName (parent) + "'");
+ "special class `" + TypeManager.MonoBASIC_Name (parent) + "'");
return null;
}
}
if (!is_class && TypeManager.value_type == null)
throw new Exception ();
+ if (is_class && Parent.Parent == null && (!(this is Interface))) \r
+ {
+ if ((ModFlags & Modifiers.PRIVATE) != 0)
+ Report.Error (31089, Location,
+ "Only internal classes can be declared as 'Private'");
+
+ if ((ModFlags & Modifiers.PROTECTED) != 0)
+ Report.Error (31047, Location,
+ "Only internal classes can be declared as 'Protected'");
+ }
+
+ if ((Parent is Module) && ((ModFlags & Modifiers.PROTECTED) != 0))
+ Report.Error (30735, Location,
+ "'Type' inside a 'Module' can not be " +
+ "declared as 'Protected'");
+
+ if ((Parent is Struct) && ((ModFlags & Modifiers.PROTECTED) != 0))
+ Report.Error (30435, Location,
+ "'Type' inside a 'Structure' can not be " +
+ "declared as 'Protected'");
+
TypeAttributes type_attributes = TypeAttr;
// if (parent_builder is ModuleBuilder) {
if (IsTopLevel){
ModuleBuilder builder = CodeGen.ModuleBuilder;
+ TypeBuilder = builder.DefineType (
+ Name, type_attributes, parent, ifaces);
- //
- // Structs with no fields need to have a ".size 1"
- // appended
- //
-
- if (!is_class && !have_nonstatic_fields)
- TypeBuilder = builder.DefineType (Name,
- type_attributes,
- parent,
- PackingSize.Unspecified, 1);
- else
- //
- // classes or structs with fields
- //
- TypeBuilder = builder.DefineType (Name,
- type_attributes,
- parent,
- ifaces);
} else {
TypeBuilder builder = Parent.TypeBuilder;
+ TypeBuilder = builder.DefineNestedType (
+ Basename, type_attributes, parent, ifaces);
+ }
- //
- // Structs with no fields need to have a ".size 1"
- // appended
- //
- if (!is_class && !have_nonstatic_fields)
- TypeBuilder = builder.DefineNestedType (Basename,
- type_attributes,
- parent,
- PackingSize.Unspecified);
- else {
- //
- // classes or structs with fields
- //
- TypeBuilder = builder.DefineNestedType (Basename,
- type_attributes,
- parent,
- ifaces);
+ if (!is_class)
+ {
+ // structure must contain atleast one member variable
+ if(!have_nonstatic_fields){
+ Report.Error (
+ 30281, Location, "Structure `" + Name + "' do not " +
+ "contain any member Variable");
+
+ /*TypeBuilder.DefineField ("$PRIVATE$", TypeManager.byte_type,
+ FieldAttributes.Private);*/
}
- }
- // add interfaces that were not added at type creation (weird API issue)
- if (!is_class && !have_nonstatic_fields && (ifaces != null)) {
- foreach (Type i in ifaces)
- TypeBuilder.AddInterfaceImplementation (i);
+ // add interfaces that were not added at type creation (weird API issue)
+ if (!have_nonstatic_fields && (ifaces != null)) {
+ foreach (Type i in ifaces)
+ TypeBuilder.AddInterfaceImplementation (i);
+ }
}
+
//
// Finish the setup for the EmitContext
void DefineMembers (ArrayList list, MemberInfo [] defined_names)
{
int idx;
-
+
+ // if one of the overloaded method is having
+ // Shadows or Overloads modifier all other should
+ // have the same modifier
+ Hashtable members = new Hashtable();
+ int modval;
+ foreach (MemberCore mc in list)\r
+ {
+ modval = 0;
+ if(members[mc.Name] == null)
+ {
+ foreach (MemberCore m in list)
+ {
+ if(m.Name == mc.Name)
+ {
+ if ((m.ModFlags & Modifiers.SHADOWS) != 0)
+ {
+ modval = Modifiers.SHADOWS;
+ break;
+ }
+ else if((m.ModFlags & Modifiers.NEW) != 0)
+ {
+ modval = Modifiers.NEW;
+ }
+ }
+ }
+ members.Add(mc.Name, modval);
+ }
+
+ modval = (int)members[mc.Name];
+ if(modval != 0)
+ {
+ if(((modval & Modifiers.SHADOWS) != 0) && ((mc.ModFlags & Modifiers.SHADOWS) == 0))
+ Report.Error (
+ 30695, mc.Location,
+ "Function '" + mc.Name + "': must be declared 'Shadows' " +
+ "because another '" + mc.Name + "' declared 'Shadows'");
+ else if(((modval & Modifiers.NEW) != 0) && ((mc.ModFlags & Modifiers.NEW) == 0))
+ Report.Error (
+ 31409, mc.Location,
+ "Function '" + mc.Name + "': must be declared 'Overloads' " +
+ "because another '" + mc.Name + "' declared 'Overloads'");
+ }
+ }
+ members.Clear ();
remove_list.Clear ();
foreach (MemberCore mc in list){
if (RootContext.WarningLevel >= 4){
if ((mc.ModFlags & Modifiers.NEW) != 0)
Warning_KewywordNewNotRequired (mc.Location, mc);
+ if ((mc.ModFlags & Modifiers.SHADOWS) != 0)
+ Warning_KewywordShadowsNotRequired (mc.Location, mc);
}
continue;
}
if (match is MethodBase && mc is MethodCore)
continue;
- if ((mc.ModFlags & Modifiers.NEW) == 0)
- Warning_KeywordNewRequired (mc.Location, defined_names [idx]);
+ if (((mc.ModFlags & Modifiers.SHADOWS) == 0) && idx > 0)
+ Warning_KeywordShadowsRequired (mc.Location, defined_names [idx]);
+
}
foreach (object o in remove_list)
IndexerName = class_indexer_name;
}
- static void Report1530 (Location loc)
+ static void Error_KeywordNotAllowed (Location loc)
{
Report.Error (1530, loc, "Keyword new not allowed for namespace elements");
}
if ((iface.ModFlags & Modifiers.NEW) == 0)
iface.DefineMembers (this);
else
- Report1530 (iface.Location);
+ Error_KeywordNotAllowed (iface.Location);
}
if (RootContext.WarningLevel > 1){
if (fields != null)
DefineMembers (fields, defined_names);
- if (this is Class){
+ if (this is Class && (!(this is Interface))){
if (instance_constructors == null){
- if (default_constructor == null)
+ if (default_constructor == null) \r
DefineDefaultConstructor (false);
}
//
// Constructors are not in the defined_names array
//
- if (instance_constructors != null)
+ if (instance_constructors != null)\r
DefineMembers (instance_constructors, null);
if (default_static_constructor != null)
} else
IndexerName = "Item";
- if (operators != null)
+ if (operators != null){
DefineMembers (operators, null);
+ CheckPairedOperators ();
+ }
+
if (enums != null)
DefineMembers (enums, defined_names);
continue;
MemberInfo pb = p.PropertyBuilder;
+
if (pb != null && filter (pb, criteria) == true) {
members.Add (p.PropertyBuilder);
}
foreach (Indexer ix in indexers)
ix.Emit (this);
- CustomAttributeBuilder cb = Interface.EmitDefaultMemberAttr (
+ /*CustomAttributeBuilder cb = Interface.EmitDefaultMemberAttr (
this, IndexerName, ModFlags, Location);
- TypeBuilder.SetCustomAttribute (cb);
+ TypeBuilder.SetCustomAttribute (cb);*/
}
if (fields != null)
if (Delegates != null)
foreach (Delegate d in Delegates)
- d.CloseDelegate ();
+ d.CloseType ();
}
public string MakeName (string n)
return "`" + Name + "." + n + "'";
}
- public void Warning_KeywordNewRequired (Location l, MemberInfo mi)
+ public void Warning_KeywordShadowsRequired (Location l, MemberInfo mi)
{
Report.Warning (
- 108, l, "The keyword new is required on " +
- MakeName (mi.Name) + " because it hides `" +
+ 108, l, "The keyword 'Shadows' is required on " +
+ MakeName (mi.Name) + " because it shadows `" +
mi.ReflectedType.Name + "." + mi.Name + "'");
}
+ public void Warning_KewywordShadowsNotRequired (Location l, MemberCore mc)
+ {
+ Report.Warning (
+ 109, l, "The member " + MakeName (mc.Name) + " does not hide an " +
+ "inherited member, the keyword shadows is not required");
+ }
+
public void Warning_KewywordNewNotRequired (Location l, MemberCore mc)
{
Report.Warning (
{
const int vao = (Modifiers.VIRTUAL | Modifiers.ABSTRACT | Modifiers.OVERRIDE);
const int va = (Modifiers.VIRTUAL | Modifiers.ABSTRACT);
- const int nv = (Modifiers.NEW | Modifiers.VIRTUAL);
+ const int nv = (Modifiers.SHADOWS | Modifiers.VIRTUAL);
bool ok = true;
string name = MakeName (n);
if ((flags & Modifiers.STATIC) != 0){
if ((flags & vao) != 0){
Report.Error (
- 112, loc, "static method " + name + "can not be marked " +
- "as virtual, abstract or override");
+ 30501, loc, "Shared method " + name + " can not be " +
+ "declared as Overridable");
ok = false;
}
}
}
}
- if ((flags & Modifiers.OVERRIDE) != 0 && (flags & nv) != 0){
+ if ((flags & Modifiers.OVERRIDE) != 0 && (flags & Modifiers.VIRTUAL) != 0)\r
+ {
Report.Error (
- 113, loc, name +
- " marked as override cannot be marked as new or virtual");
+ 30730, loc, name +
+ ": Methods marked as Overrides cannot be made Overridable");
+ ok = false;
+ }
+
+ if ((flags & Modifiers.OVERRIDE) != 0 && (flags & Modifiers.SHADOWS) != 0){
+ Report.Error (
+ 31408, loc, name +
+ ": Methods marked as Overrides cannot be marked as Shadows");
ok = false;
}
ok = false;
}
- if ((ModFlags & Modifiers.ABSTRACT) == 0){
+ if((ModFlags & Modifiers.SEALED) != 0){
+ Report.Error (
+ 30607, loc,
+ "Class declared as 'NotInheritable' " +
+ "cannot have a 'MustOverride' member");
+ ok = false;
+ }
+ else if ((ModFlags & Modifiers.ABSTRACT) == 0){
Report.Error (
- 513, loc, name +
- " is abstract but its container class is not");
+ 31411, loc, name +
+ " is declared as 'MustOverride', hence its container " +
+ "class should be declared as 'MustInherit'");
ok = false;
}
if ((flags & Modifiers.PRIVATE) != 0){
if ((flags & vao) != 0){
Report.Error (
- 621, loc, name +
- " virtual or abstract members can not be private");
+ 31408, loc, name +
+ ": Members marked as Overridable or Overrides can not be Private");
ok = false;
}
}
if ((flags & Modifiers.OVERRIDE) == 0){
Report.Error (
238, loc, name +
- " cannot be sealed because it is not an override");
+ ": cannot be sealed because it is not an override");
+ ok = false;
+ }
+ }
+ if ((flags & Modifiers.NEW) != 0){
+ if ((flags & Modifiers.SHADOWS) != 0){
+ Report.Error (
+ 31408, loc,
+ " 'Overloads' and 'Shadows' cannot be combined ");
ok = false;
}
}
bool IMemberContainer.IsInterface {
get {
- return false;
+ return this is Interface;
}
}
{
return FindMembers (mt, bf | BindingFlags.DeclaredOnly, null, null);
}
+
+ //
+ // Operator pair checking
+ //
+
+ class OperatorEntry {
+ public int flags;
+ public Type ret_type;
+ public Type type1, type2;
+ public Operator op;
+ public Operator.OpType ot;
+
+ public OperatorEntry (int f, Operator o)
+ {
+ flags = f;
+
+ ret_type = o.OperatorMethod.GetReturnType ();
+ Type [] pt = o.OperatorMethod.ParameterTypes;
+ type1 = pt [0];
+ type2 = pt [1];
+ op = o;
+ ot = o.OperatorType;
+ }
+
+ public override int GetHashCode ()
+ {
+ return ret_type.GetHashCode ();
+ }
+
+ public override bool Equals (object o)
+ {
+ OperatorEntry other = (OperatorEntry) o;
+
+ if (other.ret_type != ret_type)
+ return false;
+ if (other.type1 != type1)
+ return false;
+ if (other.type2 != type2)
+ return false;
+ return true;
+ }
+ }
+
+ //
+ // Checks that some operators come in pairs:
+ // == and !=
+ // > and <
+ // >= and <=
+ //
+ // They are matched based on the return type and the argument types
+ //
+ void CheckPairedOperators ()
+ {
+ Hashtable pairs = new Hashtable (null, null);
+
+ // Register all the operators we care about.
+ foreach (Operator op in operators){
+ int reg = 0;
+
+ switch (op.OperatorType){
+ case Operator.OpType.Equality:
+ reg = 1; break;
+ case Operator.OpType.Inequality:
+ reg = 2; break;
+
+ case Operator.OpType.GreaterThan:
+ reg = 1; break;
+ case Operator.OpType.LessThan:
+ reg = 2; break;
+
+ case Operator.OpType.GreaterThanOrEqual:
+ reg = 1; break;
+ case Operator.OpType.LessThanOrEqual:
+ reg = 2; break;
+ }
+ if (reg == 0)
+ continue;
+
+ OperatorEntry oe = new OperatorEntry (reg, op);
+
+ object o = pairs [oe];
+ if (o == null)
+ pairs [oe] = oe;
+ else {
+ oe = (OperatorEntry) o;
+ oe.flags |= reg;
+ }
+ }
+
+ //
+ // Look for the mistakes.
+ //
+ foreach (DictionaryEntry de in pairs){
+ OperatorEntry oe = (OperatorEntry) de.Key;
+
+ if (oe.flags == 3)
+ continue;
+
+ string s = "";
+ switch (oe.ot){
+ case Operator.OpType.Equality:
+ s = "!=";
+ break;
+ case Operator.OpType.Inequality:
+ s = "==";
+ break;
+ case Operator.OpType.GreaterThan:
+ s = "<";
+ break;
+ case Operator.OpType.LessThan:
+ s = ">";
+ break;
+ case Operator.OpType.GreaterThanOrEqual:
+ s = "<=";
+ break;
+ case Operator.OpType.LessThanOrEqual:
+ s = ">=";
+ break;
+ }
+ Report.Error (216, oe.op.Location,
+ "The operator `" + oe.op + "' requires a matching operator `" + s + "' to also be defined");
+ }
+ }
+
+
}
public class Class : TypeContainer {
Modifiers.INTERNAL |
Modifiers.PRIVATE |
Modifiers.ABSTRACT |
- Modifiers.SEALED |
- Modifiers.UNSAFE;
-
+ Modifiers.SEALED ;
+
public Class (TypeContainer parent, string name, int mod, Attributes attrs, Location l)
: base (parent, name, l)
{
if (parent.Parent == null)
accmods = Modifiers.INTERNAL;
else
- accmods = Modifiers.PRIVATE;
+ accmods = Modifiers.PUBLIC;
this.ModFlags = Modifiers.Check (AllowedModifiers, mod, accmods, l);
this.attributes = attrs;
if (parent.Parent == null)
accmods = Modifiers.INTERNAL;
else
- accmods = Modifiers.PRIVATE;
+ accmods = Modifiers.PUBLIC;
this.ModFlags = Modifiers.Check (AllowedModifiers, mod, accmods, l);
}
public abstract class MethodCore : MemberBase {
- public readonly Parameters Parameters;
+ public /* readonly */ Parameters Parameters;
Block block;
//
//
protected InternalParameters parameter_info;
protected Type [] parameter_types;
+
+ // Whether this is an operator
+ public bool IsOperator;
public MethodCore (Expression type, int mod, int allowed_mod, string name,
Attributes attrs, Parameters parameters, Location loc)
}
public void LabelParameters (EmitContext ec, Type [] parameters, MethodBase builder)
+ {
+ LabelParameters (ec, parameters, builder, null);
+ }
+
+ public void LabelParameters (EmitContext ec, Type [] parameters, MethodBase builder, Parameters p_params)
{
//
// Define each type attribute (in/out/ref) and
// the argument names.
//
- Parameter [] p = Parameters.FixedParameters;
+ Parameter [] p = p_params == null ? Parameters.FixedParameters : p_params.FixedParameters;
int i = 0;
MethodBuilder mb = null;
Modifiers.PRIVATE |
Modifiers.STATIC |
Modifiers.VIRTUAL |
- Modifiers.SEALED |
+ Modifiers.NONVIRTUAL |
Modifiers.OVERRIDE |
Modifiers.ABSTRACT |
- Modifiers.UNSAFE |
- Modifiers.EXTERN;
+ Modifiers.UNSAFE |
+ Modifiers.EXTERN|
+ Modifiers.SHADOWS;
//
// return_type can be "null" for VOID values.
public Method (Expression return_type, int mod, string name, Parameters parameters,
Attributes attrs, Location l)
: base (return_type, mod, AllowedModifiers, name, attrs, parameters, l)
- { }
+ {
+ Implements = null;
+ }
+
+ public Method (Expression return_type, int mod, string name, Parameters parameters,
+ Attributes attrs, Expression impl_what, Location l)
+ : base (return_type, mod, AllowedModifiers, name, attrs, parameters, l)
+ {
+ Implements = impl_what;
+ }
//
// Returns the `System.Type' for the ReturnType of this
// function. Provides a nice cache. (used between semantic analysis
// and actual code generation
//
- public Type GetReturnType (TypeContainer parent)
+ public Type GetReturnType ()
{
return MemberType;
}
- // Whether this is an operator method.
- public bool IsOperator;
+ void DuplicateEntryPoint (MethodInfo b, Location location)
+ {
+ Report.Error (
+ 30738, location,
+ "Program `" + CodeGen.FileName +
+ "' has more than one entry point defined: `" +
+ TypeManager.MonoBASIC_Signature(b) + "'");
+ }
- void DuplicateEntryPoint (MethodInfo b, Location location)
- {
- Report.Error (
- 17, location,
- "Program `" + CodeGen.FileName +
- "' has more than one entry point defined: `" +
- TypeManager.CSharpSignature(b) + "'");
- }
-
- void Report28 (MethodInfo b)
- {
+ void Report28 (MethodInfo b)
+ {
if (RootContext.WarningLevel < 4)
return;
- Report.Warning (
- 28, Location,
- "`" + TypeManager.CSharpSignature(b) +
- "' has the wrong signature to be an entry point");
- }
-
- public bool IsEntryPoint (MethodBuilder b, InternalParameters 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) &&
- (t.GetElementType() == TypeManager.string_type) &&
- (pinfo.ParameterModifier(0) == Parameter.Modifier.NONE))
- return true;
- else
- return false;
- }
+ Report.Warning (
+ 28, Location,
+ "`" + TypeManager.MonoBASIC_Signature(b) +
+ "' has the wrong signature to be an entry point");
+ }
+
+ public bool IsEntryPoint (MethodBuilder b, InternalParameters 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) &&
+ (t.GetElementType() == TypeManager.string_type) &&
+ (pinfo.ParameterModifier(0) == Parameter.Modifier.NONE))
+ return true;
+ else
+ return false;
+ }
//
// Checks our base implementation if any
}
}
} else {
- if ((ModFlags & Modifiers.NEW) != 0)
- WarningNotHiding (parent);
+ /*if ((ModFlags & Modifiers.NEW) != 0)
+ WarningNotHiding (parent);*/
if ((ModFlags & Modifiers.OVERRIDE) != 0){
- Report.Error (115, Location,
+ Report.Error (30284, Location,
parent.MakeName (Name) +
- " no suitable methods found to override");
+ " : No suitable methods found to override");
}
+ if ((ModFlags & ( Modifiers.NEW | Modifiers.SHADOWS | Modifiers.OVERRIDE )) == 0) \r
+ {
+ if ((ModFlags & Modifiers.NONVIRTUAL) != 0)\r
+ {
+ Report.Error (31088, Location,
+ parent.MakeName (Name) + " : Cannot " +
+ "be declared NotOverridable since this method is " +
+ "not maked as Overrides");
+ }
+ }
+ // if a member of module is not inherited from Object class
+ // can not be declared protected
+ if ((parent is Module) && ((ModFlags & Modifiers.PROTECTED) != 0))
+ Report.Error (31066, Location,
+ "'Sub' or 'Function' inside a 'Module' can not be declared as " +
+ "'Protected' or 'Protected Friend'");
}
- } else if ((ModFlags & Modifiers.NEW) != 0)
+ }
+ /* else if ((ModFlags & Modifiers.NEW) != 0)
WarningNotHiding (parent);
+ */
return true;
}
if (!CheckBase (parent))
return false;
+ if ((parent is Struct) && ((ModFlags & Modifiers.PROTECTED) != 0))
+ Report.Error (31067, Location,
+ "'Sub' or 'Function' inside a 'Structure' can not be declared as " +
+ "'Protected' or 'Protected Friend'");
+
CallingConventions cc = GetCallingConvention (parent is Class);
MethodData = new MethodData (this, null, MemberType, ParameterTypes,
//
// This is used to track the Entry Point,
//
- if (Name == "Main" &&
+ if (Name.ToUpper() == "MAIN" &&
((ModFlags & Modifiers.STATIC) != 0) &&
(RootContext.MainClass == null ||
- RootContext.MainClass == parent.TypeBuilder.FullName)){
+ RootContext.MainClass == parent.TypeBuilder.FullName ||
+ (RootContext.RootNamespace != null &&
+ RootContext.RootNamespace.Length > 0 &&
+ (RootContext.RootNamespace + "." + RootContext.MainClass) == parent.TypeBuilder.FullName))) {
if (IsEntryPoint (MethodBuilder, ParameterInfo)) {
if (RootContext.EntryPoint == null) {
RootContext.EntryPoint = MethodBuilder;
ConstructorInfo parent_constructor;
Parameters parameters;
Location loc;
+ public bool implicit_initialization;
public ConstructorInitializer (ArrayList argument_list, Parameters parameters,
Location loc)
this.argument_list = argument_list;
this.parameters = parameters;
this.loc = loc;
+ this.implicit_initialization = false;
}
public ArrayList Arguments {
}
}
+ public ConstructorInfo ParentConstructor
+ {
+ get\r
+ {
+ return parent_constructor;
+ }
+ }
+
public bool Resolve (EmitContext ec)
{
Expression parent_constructor_group;
return true;
t = ec.ContainerType.BaseType;
- if (ec.ContainerType.IsValueType) {
+ if (ec.ContainerType.IsValueType){
Report.Error (522, loc,
"structs cannot call base class constructors");
return false;
}
- } else
+ }\r
+ else
t = ec.ContainerType;
-
+
parent_constructor_group = Expression.MemberLookup (
ec, t, t, ".ctor",
MemberTypes.Constructor,
loc);
if (parent_constructor_group == null){
- Report.Error (1501, loc,
- "Can not find a constructor for this argument list");
+ Report.Error (30455, loc, "Class '" + t + "' can not find a constructor for this argument list" );
return false;
}
-
+
parent_constructor = (ConstructorInfo) Invocation.OverloadResolve (ec,
(MethodGroupExpr) parent_constructor_group, argument_list, loc);
-
- if (parent_constructor == null){
- Report.Error (1501, loc,
- "Can not find a constructor for this argument list");
+
+ if (parent_constructor == null) {
+ if (this.implicit_initialization)
+ Report.Error (30148, loc, "Must declare 'MyBase.New' in the constructor " +\r
+ "of the class '" + ec.TypeContainer.Name + "' with appropriate arguments, since the base class '" +\r
+ t.FullName + "' does not contain a definition of 'New' without any parameter");
+ else
+ Report.Error (30455, loc, "Class '" + t + "' can not find a constructor for this argument list" );
+
return false;
}
-
+
return true;
}
public void Emit (EmitContext ec)
{
- if (parent_constructor != null)
- ec.ig.Emit (OpCodes.Ldarg_0);
- if (argument_list != null)
- Invocation.EmitArguments (ec, null, argument_list);
- if (parent_constructor != null)
- ec.ig.Emit (OpCodes.Call, parent_constructor);
+ if (parent_constructor != null){
+ if (ec.IsStatic)
+ Invocation.EmitCall (ec, true, true, null, parent_constructor, argument_list, loc);
+ else
+ Invocation.EmitCall (ec, true, false, ec.This, parent_constructor, argument_list, loc);
+ }
}
+
+
}
public class ConstructorBaseInitializer : ConstructorInitializer {
// <summary>
// Modifiers allowed for a constructor.
// </summary>
- const int AllowedModifiers =
+ public const int AllowedModifiers =
Modifiers.PUBLIC |
Modifiers.PROTECTED |
Modifiers.INTERNAL |
Modifiers.STATIC |
Modifiers.UNSAFE |
+ Modifiers.EXTERN |
Modifiers.PRIVATE;
//
Initializer = init;
}
+ public Constructor (string name, int mod, Parameters args, ConstructorInitializer init, Location l)
+ : base (null, mod, AllowedModifiers, name, null, args, l)
+ {
+ Initializer = init;
+ }
+
//
// Returns true if this is a default constructor
//
MethodAttributes ca = (MethodAttributes.RTSpecialName |
MethodAttributes.SpecialName);
+ if (parent.EventHandlers != null) {
+ ArrayList hdlrs = parent.EventHandlers;
+ foreach(Statement stmt in hdlrs)
+ this.Block.AddStatement (stmt);
+ }
+
+
// Check if arguments were correct.
if (!DoDefineParameters (parent))
return false;
- if ((ModFlags & Modifiers.STATIC) != 0)
+ if ((ModFlags & Modifiers.STATIC) != 0) {
ca |= MethodAttributes.Static;
+
+ if (this.Parameters != Parameters.EmptyReadOnlyParameters)
+ Report.Error (
+ 30479, Location,
+ "Shared constructor can not have parameters");
+
+ if ((ModFlags & Modifiers.Accessibility) != 0)
+ Report.Error (
+ 30480, Location,
+ "Shared constructor can not be declared " +
+ "explicitly as public, private, friend or protected");
+
+ if (this.Initializer != null)
+ Report.Error (
+ 30043, Location,
+ "Keywords like MyBase, MyClass, Me are not " +
+ "valid inside a Shared Constructor");
+ }
else {
- if (parent is Struct && ParameterTypes.Length == 0){
+ if (parent is Struct && ParameterTypes.Length == 0) {
Report.Error (
- 568, Location,
+ 30629, Location,
"Structs can not contain explicit parameterless " +
"constructors");
return false;
}
ca |= MethodAttributes.HideBySig;
- if ((ModFlags & Modifiers.PRIVATE) != 0)
- ca |= MethodAttributes.Private;
- else if ((ModFlags & Modifiers.PROTECTED) != 0){
+ if ((ModFlags & Modifiers.PUBLIC) != 0)
+ ca |= MethodAttributes.Public;
+ else if ((ModFlags & Modifiers.PROTECTED) != 0) {
if ((ModFlags & Modifiers.INTERNAL) != 0)
ca |= MethodAttributes.FamORAssem;
else
ca |= MethodAttributes.Family;
- } else if ((ModFlags & Modifiers.INTERNAL) != 0)
+ }\r
+ else if ((ModFlags & Modifiers.INTERNAL) != 0)
ca |= MethodAttributes.Assembly;
- else
+ else if (IsDefault ())
ca |= MethodAttributes.Public;
+ else
+ ca |= MethodAttributes.Private;
}
ConstructorBuilder = parent.TypeBuilder.DefineConstructor (
EmitContext ec = new EmitContext (parent, Location, ig, null, ModFlags, true);
if ((ModFlags & Modifiers.STATIC) == 0){
- if (parent is Class && Initializer == null)
+ if (parent is Class && Initializer == null) {
Initializer = new ConstructorBaseInitializer (
null, Parameters.EmptyReadOnlyParameters, parent.Location);
-
+ Initializer.implicit_initialization = true;
+ }
//
// Spec mandates that Initializers will not have
if ((ModFlags & Modifiers.STATIC) == 0)
parent.EmitFieldInitializers (ec);
}
- if (Initializer != null)
+
+ if (Initializer != null) {
+ if (this.ConstructorBuilder.Equals (Initializer.ParentConstructor))
+ Report.Error (
+ 30297, Location,
+ "A constructor can not call itself" );
+
Initializer.Emit (ec);
+ }
if ((ModFlags & Modifiers.STATIC) != 0)
parent.EmitFieldInitializers (ec);
else
name = member.ShortName;
method_name = prefix + name;
-
+
if (parent.Pending != null){
if (member is Indexer)
implementing = parent.Pending.IsInterfaceIndexer (
//
if (implementing.DeclaringType.IsInterface)
flags |= MethodAttributes.NewSlot;
-
+
flags |=
MethodAttributes.Virtual |
MethodAttributes.HideBySig;
if ((modifiers & Modifiers.ABSTRACT) != 0)
Report.Error (
500, Location, "Abstract method `" +
- TypeManager.CSharpSignature (builder) +
+ TypeManager.MonoBASIC_Signature (builder) +
"' can not have a body");
if ((modifiers & Modifiers.EXTERN) != 0)
Report.Error (
179, Location, "External method `" +
- TypeManager.CSharpSignature (builder) +
+ TypeManager.MonoBASIC_Signature (builder) +
"' can not have a body");
return;
if (block == null) {
Report.Error (
501, Location, "Method `" +
- TypeManager.CSharpSignature (builder) +
+ TypeManager.MonoBASIC_Signature (builder) +
"' must declare a body since it is not marked " +
"abstract or extern");
return;
Location end = block.EndLocation;
MethodToken token = MethodBuilder.GetToken ();
sw.OpenMethod (new SymbolToken (token.Token));
- sw.SetMethodSourceRange (Location.SymbolDocument,
- Location.Row, 0,
- end.SymbolDocument,
- end.Row, 0);
+ // Avoid error if we don't support debugging for the platform
+ try {
+ sw.SetMethodSourceRange (Location.SymbolDocument,
+ Location.Row, 0,
+ end.SymbolDocument,
+ end.Row, 0);
+ } catch (Exception) {
+ }
- ec.EmitTopBlock (block, ParameterInfo, Location);
+ ec.EmitTopBlock (block, member.Name, ParameterInfo, Location);
sw.CloseMethod ();
} else
- ec.EmitTopBlock (block, ParameterInfo, Location);
+ ec.EmitTopBlock (block, member.Name, ParameterInfo, Location);
}
}
abstract public class MemberBase : MemberCore {
public Expression Type;
public readonly Attributes OptAttributes;
+ public Expression Implements;
protected MethodAttributes flags;
: base (name, loc)
{
Type = type;
- ModFlags = Modifiers.Check (allowed_mod, mod, Modifiers.PRIVATE, loc);
+ ModFlags = Modifiers.Check (allowed_mod, mod, Modifiers.PUBLIC, loc);
OptAttributes = attrs;
}
if (this is Indexer)
Report.Error (55, Location,
"Inconsistent accessibility: parameter type `" +
- TypeManager.CSharpName (partype) + "' is less " +
+ TypeManager.MonoBASIC_Name (partype) + "' is less " +
"accessible than indexer `" + Name + "'");
else
Report.Error (51, Location,
"Inconsistent accessibility: parameter type `" +
- TypeManager.CSharpName (partype) + "' is less " +
+ TypeManager.MonoBASIC_Name (partype) + "' is less " +
"accessible than method `" + Name + "'");
error = true;
}
if (this is Property)
Report.Error (53, Location,
"Inconsistent accessibility: property type `" +
- TypeManager.CSharpName (MemberType) + "' is less " +
+ TypeManager.MonoBASIC_Name (MemberType) + "' is less " +
"accessible than property `" + Name + "'");
else if (this is Indexer)
Report.Error (54, Location,
"Inconsistent accessibility: indexer return type `" +
- TypeManager.CSharpName (MemberType) + "' is less " +
+ TypeManager.MonoBASIC_Name (MemberType) + "' is less " +
"accessible than indexer `" + Name + "'");
else if (this is Method)
Report.Error (50, Location,
"Inconsistent accessibility: return type `" +
- TypeManager.CSharpName (MemberType) + "' is less " +
+ TypeManager.MonoBASIC_Name (MemberType) + "' is less " +
"accessible than method `" + Name + "'");
else
Report.Error (52, Location,
"Inconsistent accessibility: field type `" +
- TypeManager.CSharpName (MemberType) + "' is less " +
+ TypeManager.MonoBASIC_Name (MemberType) + "' is less " +
"accessible than field `" + Name + "'");
return false;
}
//
// Check for explicit interface implementation
//
- if ((ExplicitInterfaceName == null) && (Name.IndexOf (".") != -1)){
+ if ((ExplicitInterfaceName == null) && (Name.IndexOf (".") != -1)) {
int pos = Name.LastIndexOf (".");
ExplicitInterfaceName = Name.Substring (0, pos);
return init_expr;
}
+
}
//
// Modifiers allowed in a class declaration
// </summary>
const int AllowedModifiers =
- Modifiers.NEW |
+ Modifiers.SHADOWS |
Modifiers.PUBLIC |
Modifiers.PROTECTED |
Modifiers.INTERNAL |
Modifiers.PRIVATE |
Modifiers.STATIC |
- Modifiers.VOLATILE |
- Modifiers.UNSAFE |
+ // Modifiers.VOLATILE |
+ // Modifiers.UNSAFE |
Modifiers.READONLY;
public Field (Expression type, int mod, string name, Object expr_or_array_init,
if (!parent.AsAccessible (t, ModFlags)) {
Report.Error (52, Location,
"Inconsistent accessibility: field type `" +
- TypeManager.CSharpName (t) + "' is less " +
+ TypeManager.MonoBASIC_Name (t) + "' is less " +
"accessible than field `" + Name + "'");
return false;
}
if (t.IsPointer && !UnsafeOK (parent))
return false;
- if (RootContext.WarningLevel > 1){
- Type ptype = parent.TypeBuilder.BaseType;
+ Type ptype = parent.TypeBuilder.BaseType;
- // ptype is only null for System.Object while compiling corlib.
- if (ptype != null){
- TypeContainer.FindMembers (
- ptype, MemberTypes.Method,
- BindingFlags.Public |
- BindingFlags.Static | BindingFlags.Instance,
- System.Type.FilterName, Name);
+ // ptype is only null for System.Object while compiling corlib.
+ if (ptype != null){
+ MemberList list = TypeContainer.FindMembers (
+ ptype, MemberTypes.Field,
+ BindingFlags.Public |
+ BindingFlags.Static | BindingFlags.Instance,
+ System.Type.FilterName, Name);
+
+ if (RootContext.WarningLevel > 1){
+ if ((list.Count > 0) && ((ModFlags & Modifiers.SHADOWS) == 0)) \r
+ {
+ Report.Warning (
+ 40004, 2, Location,
+ "Variable '" + Name + "' should be declared " +
+ "Shadows since the base type '" + ptype.Name +
+ "' has a variable with same name");
+
+ ModFlags |= Modifiers.SHADOWS;
+ }
}
+ if (list.Count == 0)
+ // if a member of module is not inherited from Object class
+ // can not be declared protected
+ if ((parent is Module) && ((ModFlags & Modifiers.PROTECTED) != 0))
+ Report.Error (30593, Location,
+ "'Variable' inside a 'Module' can not be " +
+ "declared as 'Protected'");
}
+
+ if ((parent is Struct) && ((ModFlags & Modifiers.PROTECTED) != 0))
+ Report.Error (30435, Location,
+ "'Variable' inside a 'Structure' can not be " +
+ "declared as 'Protected'");
if ((ModFlags & Modifiers.VOLATILE) != 0){
if (!t.IsClass){
Report.Error (
677, Location, parent.MakeName (Name) +
" A volatile field can not be of type `" +
- TypeManager.CSharpName (t) + "'");
+ TypeManager.MonoBASIC_Name (t) + "'");
return false;
}
}
}
-
+
+ FieldAttributes fa = Modifiers.FieldAttr (ModFlags);
+
+ if (parent is Struct &&
+ ((fa & FieldAttributes.Static) == 0) &&
+ t == parent.TypeBuilder &&
+ !TypeManager.IsBuiltinType (t)){
+ Report.Error (523, Location, "Struct member `" + parent.Name + "." + Name +
+ "' causes a cycle in the structure layout");
+ return false;
+ }
FieldBuilder = parent.TypeBuilder.DefineField (
Name, t, Modifiers.FieldAttr (ModFlags));
//
// Checks our base implementation if any
//
- protected override bool CheckBase (TypeContainer parent)
+ protected override bool CheckBase (TypeContainer container)
{
+ base.CheckBase (container);
+
// Check whether arguments were correct.
- if (!DoDefineParameters (parent))
+ if (!DoDefineParameters (container))
return false;
+ if (IsExplicitImpl)
+ return true;
+
MethodSignature ms = new MethodSignature (Name, null, ParameterTypes);
- MemberList props_this;
-
- props_this = TypeContainer.FindMembers (
- parent.TypeBuilder, MemberTypes.Property,
- BindingFlags.NonPublic | BindingFlags.Public |
- BindingFlags.Static | BindingFlags.Instance |
- BindingFlags.DeclaredOnly,
- MethodSignature.method_signature_filter, ms);
-
- if (props_this.Count > 0) {
- Report.Error (111, Location, "Class `" + parent.Name + "' " +
- "already defines a member called `" + Name + "' " +
- "with the same parameter types");
- return false;
+ if (!IsOperator) \r
+ {
+ MemberList mi_this;
+
+ mi_this = TypeContainer.FindMembers (
+ container.TypeBuilder, MemberTypes.Property,
+ BindingFlags.NonPublic | BindingFlags.Public |
+ BindingFlags.Static | BindingFlags.Instance |
+ BindingFlags.DeclaredOnly,
+ MethodSignature.method_signature_filter, ms);
+
+ if (mi_this.Count > 0) {
+ Report.Error (111, Location, "Class `" + container.Name + "' " +
+ "already defines a member called `" + Name + "' " +
+ "with the same parameter types");
+ return false;
+ }
+ }
+
+ if (container is Interface)
+ return true;
+
+ string report_name;
+ MethodSignature base_ms;
+ if (this is Indexer) {
+ string name, base_name;
+
+ report_name = "this";
+ name = TypeManager.IndexerPropertyName (container.TypeBuilder);
+ ms = new MethodSignature (name, null, ParameterTypes);
+ base_name = TypeManager.IndexerPropertyName (container.TypeBuilder.BaseType);
+ base_ms = new MethodSignature (base_name, null, ParameterTypes);
+ } else {
+ report_name = Name;
+ ms = base_ms = new MethodSignature (Name, null, ParameterTypes);
}
//
- // Find properties with the same name on the base class
+ // Verify if the parent has a type with the same name, and then
+ // check whether we have to create a new slot for it or not.
//
- MemberList props;
- MemberList props_static = TypeContainer.FindMembers (
- parent.TypeBuilder.BaseType, MemberTypes.Property,
+ Type ptype = container.TypeBuilder.BaseType;
+
+ MemberInfo parent_member = null;
+ MemberList mi, mi_static, mi_instance;
+
+ mi_static = TypeContainer.FindMembers (
+ ptype, MemberTypes.Property,
BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static,
- MethodSignature.inheritable_property_signature_filter, ms);
+ MethodSignature.inheritable_method_signature_filter, ms);
- MemberList props_instance = TypeContainer.FindMembers (
- parent.TypeBuilder.BaseType, MemberTypes.Property,
+ mi_instance = TypeContainer.FindMembers (
+ ptype, MemberTypes.Property,
BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance,
- MethodSignature.inheritable_property_signature_filter,
+ MethodSignature.inheritable_method_signature_filter,
ms);
- //
- // Find if we have anything
- //
- if (props_static.Count > 0)
- props = props_static;
- else if (props_instance.Count > 0)
- props = props_instance;
+ if (mi_instance.Count > 0) {
+ mi = mi_instance;
+ } else if (mi_static.Count > 0)
+ mi = mi_static;
else
- props = null;
+ mi = null;
- //
- // If we have something on the base.
- if (props != null && props.Count > 0){
- PropertyInfo pi = (PropertyInfo) props [0];
+ if (mi != null && mi.Count > 0)\r
+ parent_member = (MethodInfo) mi [0];
+\r
+ if (parent_member is PropertyInfo) {
+ PropertyInfo parent_property = (PropertyInfo)parent_member;
- MethodInfo inherited_get = TypeManager.GetPropertyGetter (pi);
- MethodInfo inherited_set = TypeManager.GetPropertySetter (pi);
+ string name = parent_property.DeclaringType.Name + "." +
+ parent_property.Name;
- MethodInfo reference = inherited_get == null ?
- inherited_set : inherited_get;
-
- if (reference != null) {
- string name = reference.DeclaringType.Name + "." + Name;
+ MethodInfo get, set, parent_method;
+ get = parent_property.GetGetMethod (true);
+ set = parent_property.GetSetMethod (true);
- if (!CheckMethodAgainstBase (parent, flags, reference, name))
- return false;
- }
+ if (get != null)
+ parent_method = get;
+ else if (set != null)
+ parent_method = set;
+ else
+ throw new Exception ("Internal error!");
- if (((ModFlags & Modifiers.NEW) == 0) && (pi.PropertyType != MemberType)) {
- Report.Error (508, parent.MakeName (Name) + ": cannot " +
- "change return type when overriding inherited " +
- "member `" + pi.DeclaringType + "." + pi.Name + "'");
+ if (!CheckMethodAgainstBase (container, flags, parent_method, name))
return false;
+
+ if ((ModFlags & Modifiers.NEW) == 0) {
+ Type parent_type = TypeManager.TypeToCoreType (
+ parent_property.PropertyType);
+
+ if (parent_type != MemberType) {
+ Report.Error (
+ 508, Location, container.MakeName (Name) + ": cannot " +
+ "change return type when overriding " +
+ "inherited member " + name);
+ return false;
+ }
}
- } else {
- if ((ModFlags & Modifiers.NEW) != 0)
- WarningNotHiding (parent);
-
- if ((ModFlags & Modifiers.OVERRIDE) != 0){
+ } else if (parent_member == null) {
+ /*if ((ModFlags & Modifiers.NEW) != 0)
+ WarningNotHiding (container);
+ */
+ if ((ModFlags & Modifiers.OVERRIDE) != 0) {
if (this is Indexer)
Report.Error (115, Location,
- parent.MakeName (Name) +
- " no suitable indexers found to override");
+ container.MakeName (Name) +
+ " no suitable indexers found to override");
else
Report.Error (115, Location,
- parent.MakeName (Name) +
- " no suitable properties found to override");
+ container.MakeName (Name) +
+ " no suitable properties found to override");
return false;
}
+
+ if ((ModFlags & ( Modifiers.NEW | Modifiers.SHADOWS | Modifiers.OVERRIDE )) == 0) {
+ if ((ModFlags & Modifiers.NONVIRTUAL) != 0) {
+ Report.Error (31088, Location,
+ container.MakeName (Name) + " : Cannot " +
+ "be declared NotOverridable since this method is " +
+ "not maked as Overrides");
+ }
+ }
+ // if a member of module is not inherited from Object class
+ // can not be declared protected
+ if ((container is Module) && ((ModFlags & Modifiers.PROTECTED) != 0))
+ Report.Error (31066, Location,
+ "'Property' inside a 'Module' can not be declared as " +
+ "'Protected' or 'Protected Friend'");
}
return true;
}
- public void Emit (TypeContainer tc)
+ public virtual void Emit (TypeContainer tc)
{
//
// The PropertyBuilder can be null for explicit implementations, in that
//
if (PropertyBuilder != null)
Attribute.ApplyAttributes (ec, PropertyBuilder, this, OptAttributes, Location);
-
+/*
if (GetData != null)
GetData.Emit (tc, Get.Block, Get);
if (SetData != null)
SetData.Emit (tc, Set.Block, Set);
+*/
}
}
Modifiers.SEALED |
Modifiers.OVERRIDE |
Modifiers.ABSTRACT |
- Modifiers.UNSAFE |
+ Modifiers.UNSAFE |
Modifiers.EXTERN |
- Modifiers.VIRTUAL;
-
+ Modifiers.VIRTUAL |
+ Modifiers.NONVIRTUAL |
+ Modifiers.DEFAULT |
+ Modifiers.READONLY |
+ Modifiers.WRITEONLY |
+ Modifiers.SHADOWS;
+
+ string set_parameter_name;
+ Parameters get_params;
+ Parameters set_params;
+
public Property (Expression type, string name, int mod_flags,
- Accessor get_block, Accessor set_block,
- Attributes attrs, Location loc)
+ Accessor get_block, Accessor set_block,
+ Attributes attrs, Location loc, string set_name,
+ Parameters p_get, Parameters p_set, Expression impl_what)
: base (type, name, mod_flags, AllowedModifiers,
- Parameters.EmptyReadOnlyParameters,
+ p_set,
get_block, set_block, attrs, loc)
+ {
+ set_parameter_name = set_name;
+ get_params = p_get;
+ set_params = p_set;
+ Implements = impl_what;
+ }
+
+ public Property (Expression type, string name, int mod_flags,
+ Accessor get_block, Accessor set_block,
+ Attributes attrs, Location loc)
+ : this (type, name, mod_flags, get_block, set_block, attrs, loc,
+ "Value", Parameters.EmptyReadOnlyParameters, Parameters.EmptyReadOnlyParameters, null)
{
}
public override bool Define (TypeContainer parent)
{
+ Type [] g_parameters=null, s_parameters=null;
+ Parameter [] g_parms, s_parms;
+ InternalParameters g_ip=null, s_ip=null;
+
+ if ((parent is Struct) && ((ModFlags & Modifiers.PROTECTED) != 0))
+ Report.Error (30435, Location,
+ "'Property' inside a 'Structure' can not be declared as " +
+ "'Protected' or 'Protected Friend'");
+
if (!DoDefine (parent))
return false;
flags |= MethodAttributes.HideBySig | MethodAttributes.SpecialName;
- if (Get != null) {
- Type [] parameters = TypeManager.NoTypes;
-
- InternalParameters ip = new InternalParameters (
- parent, Parameters.EmptyReadOnlyParameters);
+ if (Get == null) {
+ if ((ModFlags & Modifiers.WRITEONLY) == 0)
+ Report.Error (
+ 30124, Location,
+ "Property without 'Get' accessor must have a 'WriteOnly' modifier");
+ }
+ else {
+ if (get_params == Parameters.EmptyReadOnlyParameters) {
+ g_parameters = TypeManager.NoTypes;
+ g_ip = new InternalParameters (
+ parent, Parameters.EmptyReadOnlyParameters);
+ } else {
+ g_parameters = new Type [get_params.FixedParameters.Length];
+ for (int i = 0; i < get_params.FixedParameters.Length; i ++) {
+ g_parameters[i] = get_params.FixedParameters[i].ParameterType;
+ }
+ g_parms = new Parameter [get_params.FixedParameters.Length];
+ for (int i = 0; i < get_params.FixedParameters.Length; i ++) {
+ Parameter tp = get_params.FixedParameters[i];
+ g_parms[i] = new Parameter (tp.TypeName, tp.Name,
+ Parameter.Modifier.NONE, null);
+ }
+ g_ip = new InternalParameters (
+ parent, new Parameters (g_parms, null, Location));
+ }
GetData = new MethodData (this, "get", MemberType,
- parameters, ip, CallingConventions.Standard,
+ g_parameters, g_ip, CallingConventions.Standard,
Get.OptAttributes, ModFlags, flags, false);
if (!GetData.Define (parent))
GetBuilder = GetData.MethodBuilder;
}
- if (Set != null) {
- Type [] parameters = new Type [1];
- parameters [0] = MemberType;
+ if (Set == null) {
+ if ((ModFlags & Modifiers.READONLY) == 0)
+ Report.Error (
+ 30124, Location,
+ "Property without 'Set' accessor must have a 'ReadOnly' modifier");
+
+ }
+ else \r
+ {
+ if (set_params == Parameters.EmptyReadOnlyParameters)
+ {
+ s_parameters = new Type [1];
+ s_parameters [0] = MemberType;
+
+ s_parms = new Parameter [1];
+ s_parms [0] = new Parameter (Type, set_parameter_name,
+ Parameter.Modifier.NONE, null);
+ } else {
+ s_parameters = new Type [set_params.FixedParameters.Length];
+ for (int i = 0; i < set_params.FixedParameters.Length; i ++) {
+ s_parameters[i] = set_params.FixedParameters[i].ParameterType;
+ }
+
+ s_parms = new Parameter [set_params.FixedParameters.Length];
+ for (int i = 0; i < set_params.FixedParameters.Length; i ++) {
+ Parameter tp = set_params.FixedParameters[i];
+ s_parms[i] = new Parameter (tp.TypeName, tp.Name,
+ Parameter.Modifier.NONE, null);
+ }
+ }
- Parameter [] parms = new Parameter [1];
- parms [0] = new Parameter (Type, "value", Parameter.Modifier.NONE, null);
- InternalParameters ip = new InternalParameters (
- parent, new Parameters (parms, null, Location));
+ s_ip = new InternalParameters (
+ parent, new Parameters (s_parms, null, Location));
SetData = new MethodData (this, "set", TypeManager.void_type,
- parameters, ip, CallingConventions.Standard,
- Set.OptAttributes, ModFlags, flags, false);
+ s_parameters, s_ip, CallingConventions.Standard,
+ Set.OptAttributes, ModFlags, flags, false);
if (!SetData.Define (parent))
return false;
SetBuilder = SetData.MethodBuilder;
- SetBuilder.DefineParameter (1, ParameterAttributes.None, "value");
+ SetBuilder.DefineParameter (1, ParameterAttributes.None,
+ set_parameter_name);
}
// FIXME - PropertyAttributes.HasDefault ?
PropertyBuilder = parent.TypeBuilder.DefineProperty (
Name, prop_attr, MemberType, null);
- if (Get != null)
- PropertyBuilder.SetGetMethod (GetBuilder);
-
- if (Set != null)
- PropertyBuilder.SetSetMethod (SetBuilder);
+ PropertyBuilder.SetGetMethod (GetBuilder);
+ PropertyBuilder.SetSetMethod (SetBuilder);
//
// HACK for the reasons exposed above
}
return true;
}
+
+ public override void Emit (TypeContainer tc)
+ {
+ base.Emit (tc);
+
+ if (GetData != null)
+ {
+ Parameters = get_params;
+ GetData.Emit (tc, Get.Block, Get);
+ }
+
+ if (SetData != null)
+ {
+ Parameters = set_params;
+ SetData.Emit (tc, Set.Block, Set);
+ }
+
+ }
}
/// </summary>
return false;
if (!MemberType.IsSubclassOf (TypeManager.delegate_type)) {
- Report.Error (66, Location, "'" + parent.Name + "." + Name +
+ Report.Error (31044, Location, "'" + parent.Name + "." + Name +
"' : event must be of a delegate type");
return false;
}
parameter_types [0] = MemberType;
Parameter [] parms = new Parameter [1];
- parms [0] = new Parameter (Type, "value", Parameter.Modifier.NONE, null);
+ parms [0] = new Parameter (Type, /* was "value" */ this.Name, Parameter.Modifier.NONE, null);
InternalParameters ip = new InternalParameters (
parent, new Parameters (parms, null, Location));
return false;
AddBuilder = AddData.MethodBuilder;
- AddBuilder.DefineParameter (1, ParameterAttributes.None, "value");
+ AddBuilder.DefineParameter (1, ParameterAttributes.None, /* was "value" */ this.Name);
RemoveData = new MethodData (this, "remove", TypeManager.void_type,
parameter_types, ip, CallingConventions.Standard,
return false;
RemoveBuilder = RemoveData.MethodBuilder;
- RemoveBuilder.DefineParameter (1, ParameterAttributes.None, "value");
+ RemoveBuilder.DefineParameter (1, ParameterAttributes.None, /* was "value" */ this.Name);
if (!IsExplicitImpl){
EventBuilder = new MyEventBuilder (
if (Add == null && Remove == null) {
FieldBuilder = parent.TypeBuilder.DefineField (
- Name, MemberType, FieldAttributes.FamANDAssem);
+ Name, MemberType,
+ FieldAttributes.FamANDAssem | ((ModFlags & Modifiers.STATIC) != 0 ? FieldAttributes.Static : 0));
TypeManager.RegisterPrivateFieldOfEvent (
(EventInfo) EventBuilder, FieldBuilder);
TypeManager.RegisterFieldBase (FieldBuilder, this);
fixed_parms.CopyTo (tmp, 0);
tmp [fixed_parms.Length] = new Parameter (
- Type, "value", Parameter.Modifier.NONE, null);
+ Type, /* was "value" */ this.Name, Parameter.Modifier.NONE, null);
Parameters set_formal_params = new Parameters (tmp, null, Location);
SetBuilder.DefineParameter (
i + 1, p [i].Attributes, p [i].Name);
}
+
if (Set != null)
SetBuilder.DefineParameter (
- i + 1, ParameterAttributes.None, "value");
+ i + 1, ParameterAttributes.None, /* was "value" */ this.Name);
if (i != ParameterTypes.Length) {
Parameter array_param = Parameters.ArrayParameter;
OperatorMethod = new Method (ReturnType, ModFlags, MethodName,
new Parameters (param_list, null, Location),
- OptAttributes, Mono.CSharp.Location.Null);
+ OptAttributes, Mono.MonoBASIC.Location.Null);
OperatorMethod.IsOperator = true;
OperatorMethod.Define (parent);
Type [] param_types = OperatorMethod.ParameterTypes;
Type declaring_type = OperatorMethodBuilder.DeclaringType;
- Type return_type = OperatorMethod.GetReturnType (parent);
+ Type return_type = OperatorMethod.GetReturnType ();
Type first_arg_type = param_types [0];
// Rules for conversion operators
OperatorMethod.Block = Block;
OperatorMethod.Emit (parent);
}
+
+ public static string GetName (OpType ot)
+ {
+ switch (ot){
+ case OpType.LogicalNot:
+ return "!";
+ case OpType.OnesComplement:
+ return "~";
+ case OpType.Increment:
+ return "++";
+ case OpType.Decrement:
+ return "--";
+ case OpType.True:
+ return "true";
+ case OpType.False:
+ return "false";
+ case OpType.Addition:
+ return "+";
+ case OpType.Subtraction:
+ return "-";
+ case OpType.UnaryPlus:
+ return "+";
+ case OpType.UnaryNegation:
+ return "-";
+ case OpType.Multiply:
+ return "*";
+ case OpType.Division:
+ return "/";
+ case OpType.Modulus:
+ return "%";
+ case OpType.BitwiseAnd:
+ return "&";
+ case OpType.BitwiseOr:
+ return "|";
+ case OpType.ExclusiveOr:
+ return "^";
+ case OpType.LeftShift:
+ return "<<";
+ case OpType.RightShift:
+ return ">>";
+ case OpType.Equality:
+ return "==";
+ case OpType.Inequality:
+ return "!=";
+ case OpType.GreaterThan:
+ return ">";
+ case OpType.LessThan:
+ return "<";
+ case OpType.GreaterThanOrEqual:
+ return ">=";
+ case OpType.LessThanOrEqual:
+ return "<=";
+ case OpType.Implicit:
+ return "implicit";
+ case OpType.Explicit:
+ return "explicit";
+ default: return "";
+ }
+ }
+
+ public override string ToString ()
+ {
+ Type return_type = OperatorMethod.GetReturnType();
+ Type [] param_types = OperatorMethod.ParameterTypes;
+
+ if (SecondArgType == null)
+ return String.Format (
+ "{0} operator {1}({2})",
+ TypeManager.MonoBASIC_Name (return_type),
+ GetName (OperatorType),
+ param_types [0]);
+ else
+ return String.Format (
+ "{0} operator {1}({2}, {3})",
+ TypeManager.MonoBASIC_Name (return_type),
+ GetName (OperatorType),
+ param_types [0], param_types [1]);
+ }
}
//
/// </summary>
public static MemberFilter method_signature_filter;
+ /// <summary>
+ /// This delegate is used to extract methods which have the
+ /// same signature as the argument except for the name
+ /// </summary>
+ public static MemberFilter method_signature_noname_filter;
+
/// <summary>
/// This delegate is used to extract inheritable methods which
/// have the same signature as the argument. By inheritable,
static MethodSignature ()
{
method_signature_filter = new MemberFilter (MemberSignatureCompare);
+ method_signature_noname_filter = new MemberFilter (MemberSignatureCompareNoName);
inheritable_method_signature_filter = new MemberFilter (
InheritableMemberSignatureCompare);
inheritable_property_signature_filter = new MemberFilter (
return true;
}
+ static bool MemberSignatureCompareNoName (MemberInfo m, object filter_criteria)
+ {
+ return MemberSignatureCompare (m, filter_criteria, false);
+ }
+
static bool MemberSignatureCompare (MemberInfo m, object filter_criteria)
+ {
+ return MemberSignatureCompare (m, filter_criteria, true);
+ }
+
+ static bool MemberSignatureCompare (MemberInfo m, object filter_criteria, bool use_name)
{
MethodSignature sig = (MethodSignature) filter_criteria;
- if (m.Name != sig.Name)
+ if (use_name && (m.Name != sig.Name))
return false;
Type ReturnType;