3 // Mono.MonoBASIC.Parser.cs (from .jay): The Parser for the MonoBASIC compiler
5 // Authors: A Rafael D Teixeira (rafaelteixeirabr@hotmail.com)
6 // Anirban Bhattacharjee (banirban@novell.com)
7 // Jambunathan K (kjambunathan@novell.com)
9 // Licensed under the terms of the GNU GPL
11 // Copyright (C) 2001, 2002, 2003, 2004 A Rafael D Teixeira
12 // Copyright (C) 2003, 2004 Novell
20 using System.Reflection;
21 using System.Collections;
25 /// The MonoBASIC Parser
28 // public class Parser : GenericParser
33 // /// Current block is used to add statements as we find
36 // Block current_block;
39 // /// Tmp block is used to store block endings in if/select's
44 // /// Tmp block is used to store tmp copies of expressions
46 // Expression tmp_expr;
49 // /// Tmp catch is used to store catch clauses in try..catch..finally
51 // ArrayList tmp_catch_clauses;
54 // /// Current interface is used by the various declaration
55 // /// productions in the interface declaration to "add"
56 // /// the interfaces as we find them.
58 // Interface current_interface;
61 // /// This is used by the unary_expression code to resolve
62 // /// a name against a parameter.
64 // Parameters current_local_parameters;
67 // /// This are used when parsing parameters in property
70 // Parameters set_parameters;
71 // Parameters get_parameters;
74 // /// This is used by the sub_header parser to store modifiers
75 // /// to be passed to sub/constructor
77 // int current_modifiers;
80 // /// This is used by the sub_header parser to store attributes
81 // /// to be passed to sub/constructor
83 // Attributes current_attributes;
86 // /// Using during property parsing to describe the implicit
87 // /// value parameter that is passed to the "set" accessor
90 // string get_implicit_value_parameter_name;
93 // // Using during property parsing to describe the implicit
94 // // value parameter that is passed to the "set" and "get"accesor
95 // // methods (properties and indexers).
97 // Expression get_implicit_value_parameter_type;
100 // /// Using during property parsing to describe the implicit
101 // /// value parameter that is passed to the "set" accessor
104 // string set_implicit_value_parameter_name;
107 // // Using during property parsing to describe the implicit
108 // // value parameter that is passed to the "set" and "get"accesor
109 // // methods (properties and indexers).
111 // Expression set_implicit_value_parameter_type;
113 // Location member_location;
115 // // An out-of-band stack.
119 // ArrayList current_rank_specifiers;
121 // DoOptions do_type;
125 // Stack switch_stack;
127 // // Expression stack for nested ifs
131 // Stack statement_stack;
133 // // A stack for With expressions.
138 // static public bool InitialOptionExplicit = false;
139 // static public bool InitialOptionStrict = false;
140 // static public bool InitialOptionCompareBinary = true;
141 // static public ArrayList ImportsList = null;
143 // bool OptionExplicit;
144 // bool OptionStrict;
145 // bool OptionCompareBinary;
147 // static public bool UseExtendedSyntax; // for ".mbs" files
149 // bool implicit_modifiers;
151 // public override string[] extensions()
153 // string [] list = { ".vb", ".mbs" };
161 public class CSharpParser {
162 NamespaceEntry current_namespace;
163 TypeContainer current_container;
164 TypeContainer current_class;
166 IIteratorContainer iterator_container;
169 /// Current block is used to add statements as we find
172 Block current_block, top_current_block;
175 /// This is used by the unary_expression code to resolve
176 /// a name against a parameter.
178 Parameters current_local_parameters;
181 /// Using during property parsing to describe the implicit
182 /// value parameter that is passed to the "set" and "get"accesor
183 /// methods (properties and indexers).
185 Expression implicit_value_parameter_type;
186 Parameters indexer_parameters;
189 /// Used to determine if we are parsing the get/set pair
190 /// of an indexer or a property
192 bool parsing_indexer;
195 /// An out-of-band stack.
204 static public int yacc_verbose_flag;
206 // Name of the file we are parsing
210 /// The current file.
214 /// This is used by the sub_header parser to store modifiers
215 /// to be passed to sub/constructor
216 int current_modifiers;
218 /// This is used by the sub_header parser to store attributes
219 /// to be passed to sub/constructor
220 Attributes current_attributes;
222 /// This is used by the attributes parser to syntactically
223 /// validate the attribute rules
224 bool allow_global_attribs = true;
226 bool expecting_global_attribs = false;
227 bool expecting_local_attribs = false;
229 bool local_attrib_section_added = false;
232 ArrayList current_rank_specifiers;
235 /// Using during property parsing to describe the implicit
236 /// value parameter that is passed to the "set" accessor
239 string get_implicit_value_parameter_name;
242 // Using during property parsing to describe the implicit
243 // value parameter that is passed to the "set" and "get"accesor
244 // methods (properties and indexers).
246 Expression get_implicit_value_parameter_type;
249 /// Using during property parsing to describe the implicit
250 /// value parameter that is passed to the "set" accessor
253 string set_implicit_value_parameter_name;
256 // Using during property parsing to describe the implicit
257 // value parameter that is passed to the "set" and "get"accesor
258 // methods (properties and indexers).
260 Expression set_implicit_value_parameter_type;
263 /// This are used when parsing parameters in property
266 Parameters set_parameters;
267 Parameters get_parameters;
269 // static public ArrayList ImportsList = null;
271 bool implicit_modifiers;
275 /// This is used as a helper class for handling of
276 /// pre-processor statements.
279 // FIXME: This class MBASException is actually a kludge
280 // It can be done away with a more elegant replacement.
282 public class MBASException : ApplicationException
287 public MBASException(int code, Location loc, string text) : base(text)
296 public class IfElseStateMachine {
320 public static Hashtable errStrings = new Hashtable();
323 static int[,] errTable = new int[(int)State.MAX, (int)Token.MAX];
325 static IfElseStateMachine()
327 // FIXME: Fix both the error nos and the error strings.
328 // Currently the error numbers and the error strings are
329 // just placeholders for getting the state-machine going.
331 errStrings.Add(0, "");
332 errStrings.Add(30012, "#If must end with a matching #End If");
333 errStrings.Add(30013, "#ElseIf, #Else or #End If must be preceded by a matching #If");
334 errStrings.Add(30014, "#ElseIf must be preceded by a matching #If or #ElseIf");
335 errStrings.Add(30028, "#Else must be preceded by a matching #If or #ElseIf");
336 errStrings.Add(32030, "#ElseIf cannot follow #Else as part of #If block");
338 errTable[(int)State.START, (int)Token.IF] = 0;
339 errTable[(int)State.START, (int)Token.ELSEIF] = 30014;
340 errTable[(int)State.START, (int)Token.ELSE] = 30028;
341 errTable[(int)State.START, (int)Token.ENDIF] = 30013;
342 errTable[(int)State.START, (int)Token.EOF] = 0;
344 errTable[(int)State.IF_SEEN, (int)Token.IF] = 0;
345 errTable[(int)State.IF_SEEN, (int)Token.ELSEIF] = 0;
346 errTable[(int)State.IF_SEEN, (int)Token.ELSE] = 0;
347 errTable[(int)State.IF_SEEN, (int)Token.ENDIF] = 0;
348 errTable[(int)State.IF_SEEN, (int)Token.EOF] = 30012;
350 errTable[(int)State.ELSEIF_SEEN, (int)Token.IF] = 0;
351 errTable[(int)State.ELSEIF_SEEN, (int)Token.ELSEIF] = 0;
352 errTable[(int)State.ELSEIF_SEEN, (int)Token.ELSE] = 0;
353 errTable[(int)State.ELSEIF_SEEN, (int)Token.ENDIF] = 0;
354 errTable[(int)State.ELSEIF_SEEN, (int)Token.EOF] = 30012;
356 errTable[(int)State.ELSE_SEEN, (int)Token.IF] = 0;
357 errTable[(int)State.ELSE_SEEN, (int)Token.ELSEIF] = 32030;
358 errTable[(int)State.ELSE_SEEN, (int)Token.ELSE] = 32030;
359 errTable[(int)State.ELSE_SEEN, (int)Token.ENDIF] = 0;
360 errTable[(int)State.ELSE_SEEN, (int)Token.EOF] = 30012;
362 errTable[(int)State.ENDIF_SEEN, (int)Token.IF] = 0;
363 errTable[(int)State.ENDIF_SEEN, (int)Token.ELSEIF] = 30014;
364 errTable[(int)State.ENDIF_SEEN, (int)Token.ELSE] = 30028;
365 errTable[(int)State.ENDIF_SEEN, (int)Token.ENDIF] = 30013;
366 errTable[(int)State.ENDIF_SEEN, (int)Token.EOF] = 0;
369 public IfElseStateMachine()
373 stateStack = new Stack();
374 stateStack.Push(state);
377 // The parameter here need not be qualified with IfElseStateMachine
378 // But it hits a bug in mcs. So temporarily scoping it so that builds
381 public void HandleToken(IfElseStateMachine.Token tok)
383 err = (int) errTable[(int)state, (int)tok];
386 throw new ApplicationException("Unexpected pre-processor directive #"+tok);
388 if(tok == Token.IF) {
389 stateStack.Push(state);
392 else if(tok == Token.ENDIF) {
393 state = (State)stateStack.Pop();
405 public string ErrString {
407 return (string) errStrings[err];
413 public class TokenizerController {
417 public bool CanAcceptTokens;
418 public bool CanSelectBlock;
426 public TokenizerController(Tokenizer lexer)
429 stateStack = new Stack();
431 currentState.CanAcceptTokens = true;
432 currentState.CanSelectBlock = true;
434 stateStack.Push(currentState);
439 return (State)stateStack.Peek();
443 public bool IsAcceptingTokens {
445 return currentState.CanAcceptTokens;
449 public void PositionCursorAtNextPreProcessorDirective()
451 lexer.PositionCursorAtNextPreProcessorDirective();
454 public void PositionTokenizerCursor(IfElseStateMachine.Token tok, BoolLiteral expr)
456 if(tok == IfElseStateMachine.Token.ENDIF) {
457 currentState = (State)stateStack.Pop();
459 if(currentState.CanAcceptTokens)
462 PositionCursorAtNextPreProcessorDirective();
467 if(tok == IfElseStateMachine.Token.IF) {
468 stateStack.Push(currentState);
470 currentState.CanAcceptTokens = parentState.CanAcceptTokens;
471 currentState.CanSelectBlock = true;
474 if(parentState.CanAcceptTokens &&
475 currentState.CanSelectBlock && (bool)(expr.GetValue()) ) {
477 currentState.CanAcceptTokens = true;
478 currentState.CanSelectBlock = false;
482 currentState.CanAcceptTokens = false;
483 PositionCursorAtNextPreProcessorDirective();
489 bool in_external_source = false;
490 int in_marked_region = 0;
492 TokenizerController tokenizerController;
493 IfElseStateMachine ifElseStateMachine;
500 %token NONE /* This token is never returned by our lexer */
501 %token ERROR // This is used not by the parser, but by the tokenizer.
505 *These are the MonoBASIC keywords
597 %token NOTINHERITABLE
598 %token NOTOVERRIDABLE
654 %token YIELD // MonoBASIC extension
658 /* MonoBASIC single character operators/punctuation. */
660 %token OPEN_BRACKET "["
661 %token CLOSE_BRACKET "]"
662 %token OPEN_PARENS "("
663 %token OPEN_BRACE "{"
664 %token CLOSE_BRACE "}"
665 %token CLOSE_PARENS ")"
679 %token OP_IDIV "\\" //FIXME: This should be "\"
681 %token EXCLAMATION "!"
684 %token LONGTYPECHAR "&"
686 %token SINGLETYPECHAR "!"
687 %token NUMBER_SIGN "#"
688 %token DOLAR_SIGN "$"
690 %token ATTR_ASSIGN ":="
692 /* MonoBASIC multi-character operators. */
697 //%token OP_MODULUS //"mod"
699 /* VB.NET 2003 new bit-shift operators */
700 %token OP_SHIFT_LEFT "<<"
701 %token OP_SHIFT_RIGHT ">>"
704 %token LITERAL_INTEGER "int literal"
705 %token LITERAL_SINGLE "float literal"
706 %token LITERAL_DOUBLE "double literal"
707 %token LITERAL_DECIMAL "decimal literal"
708 %token LITERAL_CHARACTER "character literal"
709 %token LITERAL_STRING "string literal"
710 %token LITERAL_DATE "datetime literal"
714 /* Add precedence rules to solve dangling else s/r conflict */
723 %left OP_SHIFT_LEFT OP_SHIFT_RIGHT
725 %left STAR DIV PERCENT
726 %right BITWISE_NOT CARRET UMINUS
727 %nonassoc OP_INC OP_DEC
729 %left OPEN_BRACKET OPEN_BRACE
734 %start compilation_unit
738 : logical_end_of_line
744 | logical_end_of_line pp_directive
748 : logical_end_of_line
749 opt_option_directives
750 opt_imports_directives
757 opt_option_directives
758 opt_imports_directives
766 opt_option_directives
773 | option_directives option_directive
777 : option_explicit_directive
778 | option_strict_directive
779 | option_compare_directive
808 option_explicit_directive
809 : OPTION EXPLICIT on_off logical_end_of_line
811 // if (!UseExtendedSyntax)
812 // OptionExplicit = (bool)$3;
815 // 9999, lexer.Location,
816 // "In MonoBASIC extended syntax explicit declaration is always required. So OPTION EXPLICIT is deprecated");
821 option_strict_directive
822 : OPTION STRICT on_off logical_end_of_line
824 // if (!UseExtendedSyntax)
825 // OptionStrict = (bool)$3;
828 // 9999, lexer.Location,
829 // "In MonoBASIC extended syntax strict assignability is always required. So OPTION STRICT is deprecated");
833 option_compare_directive
834 : OPTION COMPARE text_or_binary logical_end_of_line
836 // OptionCompareBinary = (bool)$3;
847 | declarations declaration
851 : declaration_qualifiers
853 // FIXME: Need to check declaration qualifiers for multi-file compilation
854 // FIXME: Qualifiers cannot be applied to namespaces
855 allow_global_attribs = false;
857 namespace_declaration
859 current_namespace.DeclarationFound = true;
861 | declaration_qualifiers
863 // FIXME: Need to check declaration qualifiers for multi-file compilation
864 allow_global_attribs = false;
866 type_spec_declaration
872 Class c = (Class) $3;
873 mod_flags = c.ModFlags;
875 } else if ($3 is Struct){
876 Struct s = (Struct) $3;
877 mod_flags = s.ModFlags;
882 if ((mod_flags & (Modifiers.PRIVATE|Modifiers.PROTECTED)) != 0){
884 1527, lexer.Location,
885 "Namespace elements cant be explicitly " +
886 "declared private or protected in `" + name + "'");
888 current_namespace.DeclarationFound = true;
902 : PERCENT { $$ = TypeManager.system_int32_expr; }
903 | LONGTYPECHAR { $$ = TypeManager.system_int64_expr; }
904 | AT_SIGN { $$ = TypeManager.system_decimal_expr; }
905 | SINGLETYPECHAR { $$ = TypeManager.system_single_expr; }
906 | NUMBER_SIGN { $$ = TypeManager.system_double_expr; }
907 | DOLAR_SIGN { $$ = TypeManager.system_string_expr; }
911 : /* empty */ { $$ = null; }
912 | type_character { $$ = $1; }
919 $$ = new MemberName ((string) $1);
921 | qualified_identifier DOT identifier // FIXME: It should be qualified_identifier DOT identifier-or-keyword
923 $$ = new MemberName ((MemberName) $1, (string) $3, null);
927 opt_imports_directives
934 | imports_directives imports_directive
938 : IMPORTS imports_terms logical_end_of_line
943 | imports_terms COMMA imports_term
947 : namespace_or_type_name
949 MemberName ns_name = (MemberName) $1;
950 current_namespace.Using (ns_name.GetTypeExpression (lexer.Location), lexer.Location);
952 | identifier ASSIGN namespace_or_type_name
954 MemberName name = (MemberName) $3;
955 current_namespace.UsingAlias ((string) $1, name.GetTypeExpression (lexer.Location), lexer.Location);
961 : /* empty */ { $$ = Parameters.EmptyReadOnlyParameters; }
962 | OPEN_PARENS CLOSE_PARENS { $$ = Parameters.EmptyReadOnlyParameters; }
963 | OPEN_PARENS opt_formal_parameter_list CLOSE_PARENS { $$ = $2; }
969 current_attributes = null;
974 local_attrib_section_added = false;
975 current_attributes = (Attributes) $1;
984 expecting_local_attribs = false;
985 expecting_global_attribs = false;
989 if (expecting_local_attribs) {
990 local_attrib_section_added = true;
991 allow_global_attribs = false;
993 $$ = new Attributes ((ArrayList) $1);
996 if (expecting_global_attribs) {
998 CodeGen.AddGlobalAttributes ((ArrayList) $1);
1001 expecting_local_attribs = false;
1002 expecting_global_attribs = false;
1004 | attribute_sections
1006 $$ = lexer.Location;
1012 ArrayList attrs = (ArrayList) $3;
1014 if (expecting_local_attribs) {
1015 if (local_attrib_section_added) {
1016 expecting_local_attribs = false;
1017 expecting_global_attribs = false;
1018 Report.Error (30205, (Location) $2, "Multiple attribute sections may not be used; Coalesce multiple attribute sections in to a single attribute section");
1023 $$ = new Attributes (attrs);
1025 ((Attributes) $1).AddAttributes (attrs);
1027 local_attrib_section_added = true;
1028 allow_global_attribs = false;
1031 if (expecting_global_attribs) {
1033 CodeGen.AddGlobalAttributes ((ArrayList) $3);
1037 expecting_local_attribs = false;
1038 expecting_global_attribs = false;
1043 : OP_LT attribute_list OP_GT opt_end_of_stmt
1047 if (expecting_global_attribs && !(bool) $4) {
1048 Report.Error (30205, lexer.Location, "End of statement expected");
1052 if (expecting_local_attribs) {
1054 Report.Error (32035, lexer.Location, "Use a line continuation after the attribute specifier to apply it to the following statement.");
1065 : /* empty */ { $$ = false; }
1066 | end_of_stmt { $$ = true; }
1072 ArrayList attrs = null;
1074 attrs = new ArrayList ();
1079 | attribute_list COMMA attribute
1081 ArrayList attrs = null;
1084 attrs = ($1 == null) ? new ArrayList () : (ArrayList) $1;
1093 : namespace_or_type_name
1095 $$ = lexer.Location;
1097 opt_attribute_arguments
1101 if (expecting_global_attribs)
1102 Report.Error (32015, (Location) $2, "Expecting Assembly or Module attribute specifiers");
1104 expecting_local_attribs = true;
1105 MemberName mname = (MemberName) $1;
1107 MemberName left = mname.Left;
1108 string identifier = mname.Name;
1110 Expression left_expr = left == null ? null : left.GetTypeExpression ((Location)$2);
1112 $$ = new Attribute (null, left_expr, identifier, (ArrayList) $3, (Location)$2);
1115 | attribute_target_specifier
1117 $$ = lexer.Location;
1120 namespace_or_type_name
1122 $$ = lexer.Location;
1124 opt_attribute_arguments
1128 string attribute_target = (string) $1;
1129 if (attribute_target != "assembly" && attribute_target != "module") {
1130 Report.Error (29999, lexer.Location, "`" + (string)$1 + "' is an invalid attribute modifier");
1133 if (!allow_global_attribs) {
1134 Report.Error (30637, (Location) $2, "Global attribute statements must precede any declarations in a file");
1138 if (expecting_local_attribs) {
1139 Report.Error (30183, (Location) $2, "Global attributes cannot be combined with local attributes");
1143 expecting_global_attribs = true;
1145 MemberName mname = (MemberName) $4;
1146 MemberName left = mname.Left;
1147 string identifier = mname.Name;
1149 Expression left_expr = left == null ? null : left.GetTypeExpression ((Location) $5);
1151 $$ = new GlobalAttribute (current_container, attribute_target, left_expr, identifier, (ArrayList) $6, (Location) $5);
1156 attribute_target_specifier
1157 : ASSEMBLY { $$ = "assembly"; }
1158 | MODULE { $$ = "module"; }
1159 | namespace_or_type_name
1163 opt_attribute_arguments
1164 : /* empty */ { $$ = null; }
1165 | OPEN_PARENS opt_attribute_arguments_list CLOSE_PARENS
1171 opt_attribute_arguments_list
1173 | attribute_arguments_list
1176 attribute_arguments_list
1177 : positional_argument_list
1179 ArrayList args = new ArrayList (4);
1184 | positional_argument_list COMMA named_argument_list
1186 ArrayList args = new ArrayList (4);
1192 | named_argument_list
1194 ArrayList args = new ArrayList (4);
1202 positional_argument_list
1203 : constant_expression
1205 ArrayList args = new ArrayList ();
1206 args.Add (new Argument ((Expression) $1, Argument.AType.Expression));
1210 | positional_argument_list COMMA constant_expression
1212 ArrayList args = (ArrayList) $1;
1213 args.Add (new Argument ((Expression) $3, Argument.AType.Expression));
1222 ArrayList args = new ArrayList ();
1227 | named_argument_list COMMA named_argument
1229 ArrayList args = (ArrayList) $1;
1237 : identifier ATTR_ASSIGN constant_expression //FIXME: It should be identifier_or_keyword ATTR_ASSIGN constant_expression
1239 $$ = new DictionaryEntry (
1241 new Argument ((Expression) $3, Argument.AType.Expression));
1245 namespace_declaration
1246 : NAMESPACE qualified_identifier logical_end_of_line
1248 if (current_attributes != null) {
1249 Report.Error(1518, Lexer.Location, "Attributes cannot be applied to namespaces."
1250 + " Expected class, delegate, enum, interface, or struct");
1253 MemberName name = (MemberName) $2;
1255 if ((current_namespace.Parent != null) && (name.Left != null)) {
1256 Report.Error (134, lexer.Location,
1257 "Cannot use qualified namespace names in nested " +
1258 "namespace declarations");
1261 current_namespace = new NamespaceEntry (
1262 current_namespace, file, name.GetName (), lexer.Location);
1265 END NAMESPACE logical_end_of_line
1267 current_namespace = current_namespace.Parent;
1272 declaration_qualifiers
1273 : opt_attributes opt_modifiers
1276 type_spec_declaration
1278 | module_declaration
1279 | interface_declaration
1280 | delegate_declaration
1281 | struct_declaration
1286 : CLASS identifier logical_end_of_line
1288 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
1289 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
1291 MemberName name = MakeName (new MemberName ((string) $2));
1292 int mod_flags = current_modifiers;
1295 current_class = new Class (current_namespace, current_container, name,
1296 mod_flags, (Attributes) current_attributes, lexer.Location);
1299 current_container = current_class;
1300 RootContext.Tree.RecordDecl (name.GetName (true), current_class);
1302 opt_inherits opt_implements
1305 ArrayList bases = (ArrayList) $5;
1306 ArrayList ifaces = (ArrayList) $6;
1308 if (ifaces != null){
1310 bases.AddRange(ifaces);
1315 if (bases != null) {
1316 if (current_class.Name == "System.Object") {
1317 Report.Error (537, current_class.Location,
1318 "The class System.Object cannot have a base " +
1319 "class or implement an interface.");
1321 current_class.Bases = (ArrayList) bases;
1324 current_class.Register ();
1326 opt_class_member_declarations
1327 END CLASS logical_end_of_line
1331 current_container = current_container.Parent;
1332 current_class = current_container;
1337 : /* empty */ { $$ = null; }
1338 | INHERITS type_list logical_end_of_line { $$ = $2; }
1342 : /* empty */ { $$ = null; }
1343 | IMPLEMENTS type_list logical_end_of_line { $$ = $2; }
1350 current_modifiers = 0;
1355 current_modifiers = (int) $1;
1361 | modifiers modifier
1366 if ((m1 & m2) != 0) {
1367 Location l = lexer.Location;
1368 Report.Error (1004, l, "Duplicate modifier: `" + Modifiers.Name (m2) + "'");
1370 $$ = (int) (m1 | m2);
1375 : PUBLIC { $$ = Modifiers.PUBLIC; }
1376 | PROTECTED { $$ = Modifiers.PROTECTED; }
1377 | PRIVATE { $$ = Modifiers.PRIVATE; }
1378 | SHARED { $$ = Modifiers.STATIC; }
1379 | FRIEND { $$ = Modifiers.INTERNAL; }
1380 | NOTINHERITABLE { $$ = Modifiers.SEALED; }
1381 | OVERRIDABLE { $$ = Modifiers.VIRTUAL; }
1382 | NOTOVERRIDABLE { $$ = Modifiers.NONVIRTUAL; }
1383 | OVERRIDES { $$ = Modifiers.OVERRIDE; }
1384 | OVERLOADS { $$ = Modifiers.NEW; }
1385 | SHADOWS { $$ = Modifiers.SHADOWS; }
1386 | MUSTINHERIT { $$ = Modifiers.ABSTRACT; }
1387 | READONLY { $$ = Modifiers.READONLY; }
1388 | DEFAULT { $$ = Modifiers.DEFAULT; }
1389 | WRITEONLY { $$ = Modifiers.WRITEONLY; }
1393 : MODULE identifier logical_end_of_line
1395 MemberName name = MakeName(new MemberName ((string) $2));
1396 current_class = new VBModule (current_namespace, current_container, name,
1397 current_modifiers, current_attributes, lexer.Location);
1399 current_container = current_class;
1400 RootContext.Tree.RecordDecl(name.GetName (true), current_class);
1402 current_class.Register ();
1404 opt_module_member_declarations
1405 END MODULE logical_end_of_line
1409 // TypeManager.AddStandardModule (current_class);
1411 current_container = current_container.Parent;
1412 current_class = current_container;
1416 opt_module_member_declarations
1418 | module_member_declarations
1421 module_member_declarations
1422 : module_member_declaration
1423 | module_member_declarations module_member_declaration
1426 module_member_declaration
1430 current_modifiers = ((int)$2) | Modifiers.STATIC;
1431 bool explicit_static = (((int) $2 & Modifiers.STATIC) > 0);
1432 implicit_modifiers = (!explicit_static);
1435 module_member_declarator
1437 implicit_modifiers = false;
1442 module_member_declarator
1443 : constructor_declaration
1444 | method_declaration
1446 // | withevents_declaration /* This is a field but must be treated specially, see below */
1447 | constant_declaration
1448 | property_declaration
1450 | type_spec_declaration
1454 constant_declaration
1455 : CONST constant_declarators logical_end_of_line
1457 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
1458 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
1460 int modflags = (int) current_modifiers;
1462 // Structure members are Public by default
1463 if ((current_container is Struct) && (modflags == 0))
1464 modflags = Modifiers.PUBLIC;
1466 ArrayList consts = (ArrayList) $2;
1467 if(consts.Count > 0)
1469 VariableDeclaration.FixupTypes ((ArrayList) $2);
1470 VariableDeclaration.FixupArrayTypes ((ArrayList) $2);
1472 foreach (VariableDeclaration constant in (ArrayList) $2){
1473 Location l = constant.Location;
1474 Const c = new Const (current_class,
1475 (Expression) constant.type,
1476 (String) constant.identifier,
1477 (Expression) constant.expression_or_array_initializer,
1478 modflags, current_attributes, l);
1480 current_container.AddConstant (c);
1486 opt_class_member_declarations
1488 | class_member_declarations
1491 class_member_declarations
1492 : class_member_declaration
1493 | class_member_declarations class_member_declaration
1496 class_member_declaration
1499 class_member_declarator
1505 class_member_declarator
1507 | constant_declaration
1508 | method_declaration
1509 | constructor_declaration
1510 | property_declaration
1512 // | withevents_declaration /* This is a field but must be treated specially, see below */
1513 | type_spec_declaration
1520 // | must_override_declaration
1523 // must_override_declaration
1524 // : must_override_sub_declaration
1525 // | must_override_func_declaration
1528 // must_override_sub_declaration
1529 // : MUSTOVERRIDE SUB identifier opt_params opt_implement_clause logical_end_of_line
1531 // // if (current_container is Module)
1532 // // Report.Error (433, "Methods in a Module cannot be declared 'MustOverride'.");
1534 // if (current_container is Struct)
1535 // Report.Error (435, "Methods in a Structure cannot be declared 'MustOverride'.");
1537 // current_modifiers |= Modifiers.ABSTRACT;
1539 // Method method = new Method (TypeManager.system_void_expr, (int) current_modifiers, (string) $3,
1540 // (Parameters) $4, null, (ArrayList) $5, lexer.Location);
1542 // if (!(current_container is Class))
1543 // Report.Error (9999, "THIS SHOULD NEVER HAPPEN!");
1550 // must_override_func_declaration
1551 // : MUSTOVERRIDE FUNCTION identifier opt_type_character opt_params opt_type_with_ranks opt_implement_clause logical_end_of_line
1553 // Expression ftype = ($6 == null) ? (($4 == null) ? TypeManager.
1554 // system_object_expr : (Expression) $4 ) : (Expression) $6;
1556 // if (current_container is Module)
1557 // Report.Error (433, "Methods in a Module cannot be declared 'MustOverride'.");
1559 // if (current_container is Struct)
1560 // Report.Error (435, "Methods in a Structure cannot be declared 'MustOverride'.");
1562 // current_modifiers |= Modifiers.ABSTRACT;
1564 // Method method = new Method ((Expression) ftype, (int) current_modifiers,
1565 // (string) $3,(Parameters) $5, null, (ArrayList) $7,
1568 // if (!(current_container is Class))
1569 // Report.Error (9999, "THIS SHOULD NEVER HAPPEN!");
1577 : SUB identifier opt_params
1579 MemberName name = new MemberName ((string) $2);
1581 if ((current_container is Struct) && (current_modifiers == 0))
1582 current_modifiers = Modifiers.PUBLIC;
1585 GenericMethod generic = null;
1586 Method method = new Method (current_class, generic, TypeManager.system_void_expr,
1587 (int) current_modifiers, false, name,
1588 (Parameters) $3, (Attributes) current_attributes,
1591 current_local_parameters = (Parameters) $3;
1594 iterator_container = (IIteratorContainer) method;
1596 opt_evt_handler opt_implement_clause logical_end_of_line
1597 // FIXME: opt_event_handler and opt_implements_clause are yet to be handled
1601 END SUB logical_end_of_line
1603 Method method = (Method) $4;
1604 Block b = (Block) $10;
1605 const int extern_abstract = (Modifiers.EXTERN | Modifiers.ABSTRACT);
1608 if ((method.ModFlags & extern_abstract) == 0){
1610 501, lexer.Location, current_container.MakeName (method.Name) +
1611 "must declare a body because it is not marked abstract or extern");
1614 if ((method.ModFlags & Modifiers.EXTERN) != 0){
1616 179, lexer.Location, current_container.MakeName (method.Name) +
1617 " is declared extern, but has a body");
1621 method.Block = (ToplevelBlock) $10;
1622 current_container.AddMethod (method);
1624 current_local_parameters = null;
1625 iterator_container = null;
1630 : FUNCTION identifier opt_type_character
1631 opt_params opt_type_with_ranks
1633 MemberName name = new MemberName ((string) $2);
1634 Expression rettype = ($5 == null) ? (($3 == null) ? TypeManager.system_object_expr : (Expression) $3 ) : (Expression) $5;
1636 GenericMethod generic = null;
1638 Method method = new Method (current_class, generic, rettype, current_modifiers,
1639 false, name, (Parameters) $4, current_attributes,
1642 current_local_parameters = (Parameters) $4;
1645 iterator_container = method;
1647 // FIXME: opt_implement_clauses needs to be taken care of
1648 opt_implement_clause logical_end_of_line
1651 Method method = (Method) $6;
1653 ArrayList retval = new ArrayList ();
1654 retval.Add (new VariableDeclaration ((string) $2, method.Type, lexer.Location));
1655 declare_local_variables (method.Type, retval, lexer.Location);
1659 END FUNCTION logical_end_of_line
1661 Method method = (Method) $6;
1662 Block b = (Block) $12;
1663 const int extern_abstract = (Modifiers.EXTERN | Modifiers.ABSTRACT);
1666 if ((method.ModFlags & extern_abstract) == 0){
1668 501, lexer.Location, current_container.MakeName (method.Name) +
1669 "must declare a body because it is not marked abstract or extern");
1672 if ((method.ModFlags & Modifiers.EXTERN) != 0){
1674 179, lexer.Location, current_container.MakeName (method.Name) +
1675 " is declared extern, but has a body");
1679 method.Block = (ToplevelBlock) b;
1680 current_container.AddMethod (method);
1682 current_local_parameters = null;
1683 iterator_container = null;
1688 : STRUCTURE identifier logical_end_of_line
1689 opt_implement_clause
1691 MemberName name = MakeName (new MemberName ((string) $2));
1693 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
1694 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
1696 current_class = new Struct (current_namespace, current_container, name, current_modifiers,
1697 current_attributes, lexer.Location);
1699 current_container = current_class;
1700 RootContext.Tree.RecordDecl (name.GetName (true), current_class);
1703 current_class.Bases = (ArrayList) $4;
1705 current_class.Register ();
1707 opt_struct_member_declarations
1711 current_container = current_container.Parent;
1712 current_class = current_container;
1714 END STRUCTURE logical_end_of_line
1719 // FIXME: logical_end_of_line is actually part of the opt_implements_clause
1720 // This rule is temporary
1722 opt_logical_end_of_line
1724 | logical_end_of_line
1728 opt_struct_member_declarations
1730 | struct_member_declarations
1733 struct_member_declarations
1734 : struct_member_declaration
1735 | struct_member_declarations struct_member_declaration
1738 struct_member_declaration
1740 struct_member_declarator
1743 struct_member_declarator
1745 | constant_declaration
1746 | constructor_declaration
1747 | method_declaration
1748 // | property_declaration
1750 | type_spec_declaration
1753 // * This is only included so we can flag error 575:
1754 // * destructors only allowed on class types
1755 // | destructor_declaration
1758 // event_declaration
1759 // : EVENT identifier AS type opt_implement_clause logical_end_of_line
1761 // VariableDeclaration var = new VariableDeclaration ((string) $2, (Expression) $4, lexer.Location);
1763 // Event e = new Event ((Expression) $4, var.identifier,
1764 // null, current_modifiers,
1765 // current_attributes, (ArrayList) $5,
1768 // CheckDef (current_container.AddEvent (e), e.Name, e.Location);
1770 // | EVENT identifier opt_params opt_implement_clause logical_end_of_line
1772 // string delName = null;
1774 // if ($4 == null) {
1775 // delName = (string) $2;
1776 // delName = delName + "EventHandler";
1777 // Mono.MonoBASIC.Delegate del = new Mono.MonoBASIC.Delegate
1778 // (current_container, TypeManager.system_void_expr,
1779 // (int) current_modifiers, MakeName(delName), (Parameters) $3,
1780 // (Attributes) current_attributes, lexer.Location);
1782 // del.Namespace = current_namespace;
1783 // CheckDef (current_container.AddDelegate (del), del.Name, lexer.Location);
1785 // ArrayList impls = (ArrayList) $4;
1786 // if (impls.Count > 1) {
1787 // string expstr = "Event '" + ((Expression) impls[1]).ToString () +
1788 // "' can not be implemented with Event '" +
1789 // (string) $2 + "', since it's delegate type does not match " +
1790 // "with the delegate type of '" + ((Expression) impls[0]).ToString () + "'";
1791 // Report.Error (31407, lexer.Location, expstr);
1793 // Expression impl = (Expression) impls[0];
1794 // delName = impl.ToString();
1795 // delName = delName.Substring (delName.LastIndexOf(".") + 1);
1796 // delName = delName + "EventHandler";
1799 // Event e = new Event (DecomposeQI (delName, lexer.Location),
1801 // null, current_modifiers,
1802 // current_attributes, (ArrayList) $4,
1805 // CheckDef (current_container.AddEvent (e), e.Name, e.Location);
1812 : EVENT identifier AS type opt_implement_clause logical_end_of_line
1814 VariableDeclaration var = new VariableDeclaration ((string) $2, (Expression) $4, lexer.Location);
1816 MemberName name = new MemberName ((string) $2);
1818 Event e = new EventField (current_class, (Expression) $4, current_modifiers, false, name,
1819 var.expression_or_array_initializer, current_attributes,
1822 current_container.AddEvent (e);
1825 // | EVENT identifier opt_params opt_implement_clause logical_end_of_line
1827 // string delName = null;
1829 // if ($4 == null) {
1830 // delName = (string) $2;
1831 // delName = delName + "EventHandler";
1832 // Mono.MonoBASIC.Delegate del = new Mono.MonoBASIC.Delegate
1833 // (current_container, TypeManager.system_void_expr,
1834 // (int) current_modifiers, MakeName(delName), (Parameters) $3,
1835 // (Attributes) current_attributes, lexer.Location);
1837 // del.Namespace = current_namespace;
1838 // CheckDef (current_container.AddDelegate (del), del.Name, lexer.Location);
1840 // ArrayList impls = (ArrayList) $4;
1841 // if (impls.Count > 1) {
1842 // string expstr = "Event '" + ((Expression) impls[1]).ToString () +
1843 // "' can not be implemented with Event '" +
1844 // (string) $2 + "', since it's delegate type does not match " +
1845 // "with the delegate type of '" + ((Expression) impls[0]).ToString () + "'";
1846 // Report.Error (31407, lexer.Location, expstr);
1848 // Expression impl = (Expression) impls[0];
1849 // delName = impl.ToString();
1850 // delName = delName.Substring (delName.LastIndexOf(".") + 1);
1851 // delName = delName + "EventHandler";
1854 // Event e = new Event (DecomposeQI (delName, lexer.Location),
1856 // null, current_modifiers,
1857 // current_attributes, (ArrayList) $4,
1860 // CheckDef (current_container.AddEvent (e), e.Name, e.Location);
1865 : ENUM identifier opt_type_spec logical_end_of_line
1866 opt_enum_member_declarations
1868 Location enum_location = lexer.Location;
1870 Expression base_type = TypeManager.system_int32_expr;
1871 if ((Expression) $3 != null)
1872 base_type = (Expression) $3;
1874 ArrayList enum_members = (ArrayList) $5;
1875 if (enum_members.Count == 0)
1876 Report.Error (30280, enum_location,
1877 "Enum can not have empty member list");
1880 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
1881 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
1883 MemberName full_name = MakeName (new MemberName ((string) $2));
1884 Enum e = new Enum (current_namespace, current_container, base_type,
1885 (int) current_modifiers, full_name,
1886 (Attributes) current_attributes, enum_location);
1888 foreach (VariableDeclaration ev in (ArrayList) $5) {
1889 e.AddEnumMember (ev.identifier,
1890 (Expression) ev.expression_or_array_initializer,
1891 ev.Location, ev.OptAttributes, ev.DocComment);
1894 string name = full_name.GetName ();
1895 current_container.AddEnum (e);
1896 RootContext.Tree.RecordDecl (name, e);
1899 END ENUM logical_end_of_line
1902 opt_enum_member_declarations
1903 : /* empty */ { $$ = new ArrayList (4); }
1904 | enum_member_declarations { $$ = $1; }
1907 enum_member_declarations
1908 : enum_member_declaration
1910 ArrayList l = new ArrayList ();
1915 | enum_member_declarations enum_member_declaration
1917 ArrayList l = (ArrayList) $1;
1925 enum_member_declaration
1926 : opt_attributes identifier logical_end_of_line
1928 $$ = new VariableDeclaration ((string) $2, null, lexer.Location, (Attributes) $1);
1930 | opt_attributes identifier
1932 $$ = lexer.Location;
1934 ASSIGN expression logical_end_of_line
1936 $$ = new VariableDeclaration ((string) $2, $5, lexer.Location, (Attributes) $1);
1940 // interface_property_declaration
1941 // : PROPERTY identifier opt_type_character opt_property_parameters opt_type_with_ranks logical_end_of_line
1943 // Expression ftype = ($5 == null) ? (($3 == null) ?
1944 // TypeManager.system_object_expr : (Expression) $3 ) : (Expression) $5;
1946 // current_local_parameters = (Parameters) $4;
1947 // if (current_local_parameters != Parameters.EmptyReadOnlyParameters) {
1948 // get_parameters = current_local_parameters.Copy (lexer.Location);
1949 // set_parameters = current_local_parameters.Copy (lexer.Location);
1951 // Parameter implicit_value_parameter = new Parameter (
1952 // ftype, "Value", Parameter.Modifier.NONE, null);
1954 // set_parameters.AppendParameter (implicit_value_parameter);
1958 // get_parameters = Parameters.EmptyReadOnlyParameters;
1959 // set_parameters = new Parameters (null, null ,lexer.Location);
1961 // Parameter implicit_value_parameter = new Parameter (
1962 // ftype, "Value", Parameter.Modifier.NONE, null);
1964 // set_parameters.AppendParameter (implicit_value_parameter);
1966 // lexer.PropertyParsing = true;
1968 // Accessor get_block = new Accessor (null, null);
1969 // Accessor set_block = new Accessor (null, null);
1971 // Property prop = new Property ((Expression) ftype, (string) $2, current_modifiers,
1972 // get_block, set_block, current_attributes, lexer.Location,
1973 // null, get_parameters, set_parameters, null);
1975 // CheckDef (current_interface.AddProperty (prop), prop.Name, lexer.Location);
1977 // get_implicit_value_parameter_type = null;
1978 // set_implicit_value_parameter_type = null;
1979 // get_parameters = null;
1980 // set_parameters = null;
1981 // current_local_parameters = null;
1985 // interface_event_declaration
1986 // : EVENT identifier AS type logical_end_of_line
1988 // VariableDeclaration var = new VariableDeclaration ((string) $2, (Expression) $4, lexer.Location);
1990 // Event e = new Event ((Expression) $4, var.identifier,
1991 // null, current_modifiers,
1992 // current_attributes, lexer.Location);
1994 // CheckDef (current_interface.AddEvent (e), e.Name, e.Location);
1997 // | EVENT identifier opt_params logical_end_of_line
1999 // string delName = (string) $2;
2000 // delName = delName + "EventHandler";
2001 // int delModifiers = (current_modifiers & ~Modifiers.ABSTRACT);
2002 // Mono.MonoBASIC.Delegate del = new Mono.MonoBASIC.Delegate
2003 // (current_container, TypeManager.system_void_expr,
2004 // (int) delModifiers, MakeName(delName), (Parameters) $3,
2005 // (Attributes) current_attributes, lexer.Location);
2007 // del.Namespace = current_namespace;
2008 // CheckDef (current_interface.AddDelegate (del), del.Name, lexer.Location);
2010 // Event e = new Event (DecomposeQI (delName, lexer.Location),
2012 // null, current_modifiers,
2013 // current_attributes, lexer.Location);
2015 // CheckDef (current_interface.AddEvent (e), e.Name, e.Location);
2021 //FIXME: This apparently doesn't seem to emit the right code with property
2022 //having opt_property_parameters defined
2024 interface_property_declaration
2025 : PROPERTY identifier opt_type_character opt_property_parameters opt_type_with_ranks logical_end_of_line
2027 get_implicit_value_parameter_type =
2028 ($5 == null) ? (($3 == null) ?
2029 TypeManager.system_object_expr : (Expression) $3 ) : (Expression) $5;
2031 current_local_parameters = (Parameters) $4;
2032 if (current_local_parameters != Parameters.EmptyReadOnlyParameters) {
2033 get_parameters = current_local_parameters.Copy (lexer.Location);
2034 set_parameters = current_local_parameters.Copy (lexer.Location);
2036 Parameter implicit_value_parameter = new Parameter (
2037 get_implicit_value_parameter_type, "Value", Parameter.Modifier.NONE, null);
2039 set_parameters.AppendParameter (implicit_value_parameter);
2043 get_parameters = Parameters.EmptyReadOnlyParameters;
2044 set_parameters = new Parameters (null, null ,lexer.Location);
2046 Parameter implicit_value_parameter = new Parameter (
2047 get_implicit_value_parameter_type, "Value", Parameter.Modifier.NONE, null);
2049 set_parameters.AppendParameter (implicit_value_parameter);
2051 lexer.PropertyParsing = true;
2053 Location loc = lexer.Location;
2054 MemberName name = new MemberName ((string) $2);
2056 Accessor get_block = new Accessor (null, 0, null, loc);
2057 Accessor set_block = new Accessor (null, 0, null, loc);
2059 Property prop = new Property (current_class, get_implicit_value_parameter_type,
2060 (int) current_modifiers, true,
2061 name, current_attributes,
2062 get_parameters, get_block,
2063 set_parameters, set_block, lexer.Location);
2065 current_container.AddProperty (prop);
2067 get_implicit_value_parameter_type = null;
2068 set_implicit_value_parameter_type = null;
2069 get_parameters = null;
2070 set_parameters = null;
2071 current_local_parameters = null;
2076 // interface_event_declaration
2077 // : EVENT identifier AS type logical_end_of_line
2079 // VariableDeclaration var = new VariableDeclaration ((string) $2, (Expression) $4, lexer.Location);
2081 // Event e = new Event ((Expression) $4, var.identifier,
2082 // null, current_modifiers,
2083 // current_attributes, lexer.Location);
2085 // CheckDef (current_interface.AddEvent (e), e.Name, e.Location);
2088 // | EVENT identifier opt_params logical_end_of_line
2090 // string delName = (string) $2;
2091 // delName = delName + "EventHandler";
2092 // int delModifiers = (current_modifiers & ~Modifiers.ABSTRACT);
2093 // Mono.MonoBASIC.Delegate del = new Mono.MonoBASIC.Delegate
2094 // (current_container, TypeManager.system_void_expr,
2095 // (int) delModifiers, MakeName(delName), (Parameters) $3,
2096 // (Attributes) current_attributes, lexer.Location);
2098 // del.Namespace = current_namespace;
2099 // CheckDef (current_interface.AddDelegate (del), del.Name, lexer.Location);
2101 // Event e = new Event (DecomposeQI (delName, lexer.Location),
2103 // null, current_modifiers,
2104 // current_attributes, lexer.Location);
2106 // CheckDef (current_interface.AddEvent (e), e.Name, e.Location);
2110 interface_declaration
2111 : INTERFACE identifier logical_end_of_line
2113 MemberName name = new MemberName ((string) $2);
2115 current_class = new Interface (current_namespace, current_container,
2116 name, (int) current_modifiers,
2117 (Attributes) current_attributes, lexer.Location);
2119 current_container = current_class;
2120 RootContext.Tree.RecordDecl (name.GetName (true), current_class);
2125 current_class.Bases = (ArrayList) $5;
2126 current_class.Register ();
2132 current_container = current_container.Parent;
2133 current_class = current_container;
2135 END INTERFACE logical_end_of_line
2139 : /* empty */ { $$ = null; }
2140 | interface_bases { $$ = $1; }
2145 | interface_bases interface_base
2147 ArrayList bases = (ArrayList) $1;
2148 bases.AddRange ((ArrayList) $2);
2154 : INHERITS type_list logical_end_of_line { $$ = $2; }
2158 : opt_interface_member_declarations
2161 opt_interface_member_declarations
2163 | interface_member_declarations
2166 interface_member_declarations
2167 : interface_member_declaration
2168 | interface_member_declarations interface_member_declaration
2171 interface_member_declaration
2172 : opt_attributes opt_modifiers interface_member_declarator
2175 interface_member_declarator
2176 : interface_method_declaration
2178 Method m = (Method) $1;
2180 current_container.AddMethod (m);
2182 | interface_property_declaration
2183 // | interface_event_declaration
2186 interface_method_declaration
2187 : SUB identifier opt_params logical_end_of_line
2189 MemberName name = (MemberName) new MemberName ((string) $2);
2191 GenericMethod generic = null;
2193 $$ = new Method (current_class, generic, TypeManager.system_void_expr,
2194 (int) current_modifiers, true, name, (Parameters) $3,
2195 (Attributes) current_attributes, lexer.Location);
2198 | FUNCTION identifier opt_type_character opt_params opt_type_with_ranks logical_end_of_line
2200 MemberName name = new MemberName ((string) $2);
2201 Expression return_type = ($5 == null) ?
2202 (($3 == null) ? TypeManager.system_object_expr : (Expression) $3 )
2205 GenericMethod generic = null;
2206 $$ = new Method (current_class, generic, return_type, (int) current_modifiers,
2207 true, name, (Parameters) $4, (Attributes) current_attributes,
2212 property_declaration
2213 : non_abstract_propery_declaration
2214 // | abstract_propery_declaration
2217 // abstract_propery_declaration
2218 // : MUSTOVERRIDE PROPERTY identifier opt_type_character opt_property_parameters opt_type_with_ranks logical_end_of_line
2220 // Expression ftype = ($6 == null) ? (($4 == null) ?
2221 // TypeManager.system_object_expr : (Expression) $4 ) : (Expression) $6;
2223 // if (current_container is Module)
2224 // Report.Error (30503, "Properties in a Module cannot be declared 'MustOverride'.");
2226 // if (current_container is Struct)
2227 // Report.Error (435, "Methods in a Structure cannot be declared 'MustOverride'.");
2229 // current_modifiers |= Modifiers.ABSTRACT;
2231 // current_local_parameters = (Parameters) $5;
2232 // if (current_local_parameters != Parameters.EmptyReadOnlyParameters) {
2233 // get_parameters = current_local_parameters.Copy (lexer.Location);
2234 // set_parameters = current_local_parameters.Copy (lexer.Location);
2236 // Parameter implicit_value_parameter = new Parameter (
2237 // ftype, "Value", Parameter.Modifier.NONE, null);
2239 // set_parameters.AppendParameter (implicit_value_parameter);
2243 // get_parameters = Parameters.EmptyReadOnlyParameters;
2244 // set_parameters = new Parameters (null, null ,lexer.Location);
2246 // Parameter implicit_value_parameter = new Parameter (
2247 // ftype, "Value", Parameter.Modifier.NONE, null);
2249 // set_parameters.AppendParameter (implicit_value_parameter);
2251 // lexer.PropertyParsing = true;
2253 // Accessor get_block = new Accessor (null, null);
2254 // Accessor set_block = new Accessor (null, null);
2256 // Property prop = new Property ((Expression) ftype, (string) $3, current_modifiers,
2257 // get_block, set_block, current_attributes, lexer.Location,
2258 // null, get_parameters, set_parameters, null);
2260 // if (!(current_container is Class))
2261 // Report.Error (9999, "THIS SHOULD NEVER HAPPEN!");
2263 // CheckDef (current_container.AddProperty (prop), prop.Name, lexer.Location);
2265 // get_implicit_value_parameter_type = null;
2266 // set_implicit_value_parameter_type = null;
2267 // get_parameters = null;
2268 // set_parameters = null;
2269 // current_local_parameters = null;
2273 non_abstract_propery_declaration
2274 : PROPERTY identifier opt_type_character opt_property_parameters opt_type_with_ranks opt_implement_clause logical_end_of_line
2276 get_implicit_value_parameter_type =
2277 ($5 == null) ? (($3 == null) ?
2278 TypeManager.system_object_expr : (Expression) $3 ) : (Expression) $5;
2279 get_implicit_value_parameter_name = (string) $2;
2281 current_local_parameters = (Parameters) $4;
2282 if (current_local_parameters != Parameters.EmptyReadOnlyParameters) {
2283 get_parameters = current_local_parameters.Copy (lexer.Location);
2284 set_parameters = current_local_parameters.Copy (lexer.Location);
2288 get_parameters = Parameters.EmptyReadOnlyParameters;
2289 set_parameters = new Parameters (null, null ,lexer.Location);
2291 lexer.PropertyParsing = true;
2293 $$ = lexer.Location;
2295 accessor_declarations
2296 END PROPERTY logical_end_of_line
2298 lexer.PropertyParsing = false;
2301 Pair pair = (Pair) $9;
2303 Accessor get_block = (Accessor) pair.First;
2304 Accessor set_block = (Accessor) pair.Second;
2306 Location loc = lexer.Location;
2307 MemberName name = new MemberName ((string) $2);
2309 // FIXME: Implements Clause needs to be taken care of.
2311 if ((current_container is Struct) && (current_modifiers == 0))
2312 current_modifiers = Modifiers.PUBLIC;
2315 prop = new Property (current_class, get_implicit_value_parameter_type,
2316 (int) current_modifiers, false,
2317 name, (Attributes) current_attributes,
2318 get_parameters, get_block,
2319 set_parameters, set_block, lexer.Location);
2321 current_container.AddProperty (prop);
2322 get_implicit_value_parameter_type = null;
2323 set_implicit_value_parameter_type = null;
2324 get_parameters = null;
2325 set_parameters = null;
2326 current_local_parameters = null;
2330 opt_property_parameters
2333 $$ = Parameters.EmptyReadOnlyParameters;
2335 | OPEN_PARENS opt_formal_parameter_list CLOSE_PARENS
2341 opt_implement_clause
2346 | IMPLEMENTS implement_clause_list
2352 implement_clause_list
2353 : qualified_identifier
2355 MemberName mname = (MemberName) $1;
2356 ArrayList impl_list = new ArrayList ();
2357 impl_list.Add (mname.GetTypeExpression (lexer.Location));
2360 | implement_clause_list COMMA qualified_identifier
2362 MemberName mname = (MemberName) $3;
2363 ArrayList impl_list = (ArrayList) $1;
2364 impl_list.Add (mname.GetTypeExpression (lexer.Location));
2369 accessor_declarations
2370 : get_accessor_declaration opt_set_accessor_declaration
2372 $$ = new Pair ($1, $2);
2374 | set_accessor_declaration opt_get_accessor_declaration
2376 $$ = new Pair ($2, $1);
2380 opt_get_accessor_declaration
2381 : /* empty */ { $$ = null; }
2382 | get_accessor_declaration
2385 opt_set_accessor_declaration
2386 : /* empty */ { $$ = null; }
2387 | set_accessor_declaration
2390 get_accessor_declaration
2391 : opt_attributes GET logical_end_of_line
2393 if ((current_modifiers & Modifiers.WRITEONLY) != 0)
2394 Report.Error (30023, "'WriteOnly' properties cannot have a 'Get' accessor");
2396 current_local_parameters = get_parameters;
2398 lexer.PropertyParsing = false;
2403 ArrayList retval = new ArrayList ();
2404 retval.Add (new VariableDeclaration (get_implicit_value_parameter_name, get_implicit_value_parameter_type, lexer.Location));
2405 declare_local_variables (get_implicit_value_parameter_type, retval, lexer.Location);
2409 END GET logical_end_of_line
2411 $$ = new Accessor ((ToplevelBlock) $8, (int) current_modifiers,
2412 (Attributes) $1, lexer.Location);
2414 current_local_parameters = null;
2415 lexer.PropertyParsing = true;
2421 set_accessor_declaration
2422 : opt_attributes SET opt_set_parameter logical_end_of_line
2424 if ((current_modifiers & Modifiers.READONLY) != 0)
2425 Report.Error (30022, "'ReadOnly' properties cannot have a 'Set' accessor");
2427 Parameter implicit_value_parameter = new Parameter (
2428 set_implicit_value_parameter_type,
2429 set_implicit_value_parameter_name,
2430 Parameter.Modifier.NONE, null);
2432 set_parameters.AppendParameter (implicit_value_parameter);
2433 current_local_parameters = set_parameters;
2435 lexer.PropertyParsing = false;
2440 END SET logical_end_of_line
2442 $$ = new Accessor ((ToplevelBlock) $8, (int) current_modifiers,
2443 (Attributes) $1, lexer.Location);
2444 current_local_parameters = null;
2445 lexer.PropertyParsing = true;
2452 set_implicit_value_parameter_type = (Expression) get_implicit_value_parameter_type; // TypeManager.system_object_expr;
2453 set_implicit_value_parameter_name = "Value";
2455 |OPEN_PARENS CLOSE_PARENS
2457 set_implicit_value_parameter_type = (Expression) get_implicit_value_parameter_type;
2458 set_implicit_value_parameter_name = "Value";
2460 | OPEN_PARENS opt_parameter_modifier opt_identifier opt_type_with_ranks CLOSE_PARENS
2462 Parameter.Modifier pm = (Parameter.Modifier)$2;
2463 if ((pm | Parameter.Modifier.VAL) != 0)
2464 Report.Error (31065,
2466 "Set cannot have a paremeter modifier other than 'ByVal'");
2468 set_implicit_value_parameter_type = (Expression) $4;
2470 if (set_implicit_value_parameter_type.ToString () != get_implicit_value_parameter_type.ToString ())
2471 Report.Error (31064,
2473 "Set value parameter type can not be different from property type");
2476 set_implicit_value_parameter_name = (string) $3;
2478 set_implicit_value_parameter_name = "Value";
2484 variable_declarators logical_end_of_line
2486 int mod = (int) current_modifiers;
2488 VariableDeclaration.FixupTypes ((ArrayList) $2);
2489 VariableDeclaration.FixupArrayTypes ((ArrayList) $2);
2491 // if (current_container is Module)
2492 // mod = mod | Modifiers.STATIC;
2494 // Structure members are Public by default
2495 if ((current_container is Struct) && (mod == 0))
2496 mod = Modifiers.PUBLIC;
2498 if ((mod & Modifiers.Accessibility) == 0)
2499 mod |= Modifiers.PRIVATE;
2501 foreach (VariableDeclaration var in (ArrayList) $2){
2502 Location l = var.Location;
2503 Field field = new Field (current_class, var.type, mod,
2504 var.identifier, var.expression_or_array_initializer,
2505 (Attributes) null, l);
2507 current_container.AddField (field);
2513 // withevents_declaration
2514 // : opt_dim_stmt WITHEVENTS variable_declarators logical_end_of_line
2516 // // Module members are static by default, but delegates *can't* be declared static
2517 // // so we must fix it, if mbas was the one actually responsible for this
2518 // // instead of triggering an error.
2519 // if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
2520 // current_modifiers = (current_modifiers & ~Modifiers.STATIC);
2522 // /* WithEvents Fields must be resolved into properties
2523 // with a bit of magic behind the scenes */
2525 // VariableDeclaration.FixupTypes ((ArrayList) $3);
2527 // foreach (VariableDeclaration var in (ArrayList) $3) {
2528 // // 1 - We create a private field
2529 // Location l = var.Location;
2531 // if ((current_modifiers & Modifiers.STATIC) > 0)
2532 // Report.Error (30234, l, "'Static' is not valid on a WithEvents declaration.");
2534 // Field field = new Field (var.type, Modifiers.PRIVATE, "_" + var.identifier,
2535 // var.expression_or_array_initializer,
2536 // (Attributes) null, l);
2538 // CheckDef (current_container.AddField (field), field.Name, l);
2540 // // 2 - Public property
2542 // prop = BuildSimpleProperty (var.type, (string) var.identifier,
2543 // field, (int) current_modifiers,
2544 // (Attributes) current_attributes, l);
2546 // CheckDef (current_container.AddProperty (prop), prop.Name, l);
2556 delegate_declaration
2558 identifier OPEN_PARENS
2559 opt_formal_parameter_list
2563 Location l = lexer.Location;
2564 MemberName name = MakeName (new MemberName ((string) $3));
2566 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
2567 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
2569 Delegate del = new Delegate (current_namespace, current_container, TypeManager.system_void_expr,
2570 current_modifiers, name, (Parameters) $5, current_attributes, l);
2572 current_container.AddDelegate (del);
2573 RootContext.Tree.RecordDecl (name.GetName (true), del);
2577 identifier OPEN_PARENS
2578 opt_formal_parameter_list
2579 CLOSE_PARENS opt_type_with_ranks logical_end_of_line
2581 Location l = lexer.Location;
2582 MemberName name = MakeName (new MemberName ((string) $3));
2584 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
2585 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
2587 Expression rettype = ($7 == null) ? TypeManager.system_object_expr : (Expression) $7;
2588 Delegate del = new Delegate (current_namespace, current_container, rettype,
2589 current_modifiers, name, (Parameters) $5, current_attributes, l);
2591 current_container.AddDelegate (del);
2592 RootContext.Tree.RecordDecl (name.GetName (true), del);
2599 : /* empty */ { $$ = null; }
2600 // | HANDLES evt_handler { $$ = $2; }
2604 // : qualified_identifier
2606 // $$ = (Expression) DecomposeQI ((string)$1, lexer.Location);
2612 // | ME DOT qualified_identifier
2614 // $$ = (Expression) DecomposeQI ((string)$3, lexer.Location);
2616 // /*| MYBASE DOT qualified_identifier
2618 // // FIXME: this is blatantly wrong and crash-prone
2619 // $$ = (Expression) DecomposeQI ("MyBase." + (string)$4, lexer.Location);
2624 constructor_declaration
2625 : SUB NEW opt_params logical_end_of_line
2627 current_local_parameters = (Parameters) $3;
2628 $$ = new Constructor (current_class, current_container.Basename, 0, (Parameters) $3,
2629 (ConstructorInitializer) null, lexer.Location);
2635 Constructor c = (Constructor) $5;
2636 c.Block = (ToplevelBlock) $8;
2637 c.ModFlags = (int) current_modifiers;
2638 c.OptAttributes = current_attributes;
2640 // FIXME: Some more error checking from mcs needs to be merged here ???
2642 c.Initializer = CheckConstructorInitializer (ref c.Block.statements);
2644 current_container.AddConstructor(c);
2645 current_local_parameters = null;
2647 END SUB logical_end_of_line
2650 opt_formal_parameter_list
2653 $$ = Parameters.EmptyReadOnlyParameters;
2655 | formal_parameter_list
2661 formal_parameter_list
2664 ArrayList pars_list = (ArrayList) $1;
2665 Parameter [] pars = null;
2666 Parameter array_parameter = null;
2667 int non_array_count = pars_list.Count;
2668 if (pars_list.Count > 0 && (((Parameter) pars_list [pars_list.Count - 1]).ModFlags & Parameter.Modifier.PARAMS) != 0) {
2669 array_parameter = (Parameter) pars_list [pars_list.Count - 1];
2670 non_array_count = pars_list.Count - 1;
2672 foreach (Parameter par in pars_list)
2673 if (par != array_parameter && (par.ModFlags & Parameter.Modifier.PARAMS) != 0) {
2674 Report.Error (30192, lexer.Location, "ParamArray parameters must be last");
2675 non_array_count = 0;
2676 array_parameter = null;
2679 if (non_array_count > 0) {
2680 pars = new Parameter [non_array_count];
2681 pars_list.CopyTo (0, pars, 0, non_array_count);
2683 $$ = new Parameters (pars, array_parameter, lexer.Location);
2690 ArrayList pars = new ArrayList ();
2695 | parameters COMMA parameter
2697 ArrayList pars = (ArrayList) $1;
2706 opt_parameter_modifier
2707 identifier opt_type_character opt_rank_specifiers opt_type_with_ranks opt_variable_initializer
2709 Parameter.Modifier pm = (Parameter.Modifier)$2;
2710 bool opt_parm = ((pm & Parameter.Modifier.OPTIONAL) != 0);
2713 if (opt_parm && ($7 == null))
2714 Report.Error (30812, lexer.Location, "Optional parameters must have a default value");
2716 if (!opt_parm && ($7 != null))
2717 Report.Error (32024, lexer.Location, "Non-Optional parameters should not have a default value");
2719 if ((pm & Parameter.Modifier.PARAMS) != 0) {
2720 if ((pm & ~Parameter.Modifier.PARAMS) != 0)
2721 Report.Error (30667, lexer.Location, "ParamArray parameters must be ByVal");
2724 if ((pm & Parameter.Modifier.REF) !=0)
2725 pm |= Parameter.Modifier.ISBYREF;
2727 if ($4 != null && $6 != null && $4 != $6)
2728 Report.Error (30302, lexer.Location, "Type character conflicts with declared type."); // TODO: Correct error number and message text
2730 ptype = (Expression)(($6 == null) ? (($4 == null) ? TypeManager.system_object_expr : $4) : $6);
2732 string t = ptype.ToString ();
2733 if (t.IndexOf('[') >= 0)
2734 Report.Error (31087, lexer.Location, "Array types specified in too many places");
2736 ptype = DecomposeQI (t + VariableDeclaration.BuildRanks ((ArrayList) $5, true, lexer.Location), lexer.Location);
2738 if ((pm & Parameter.Modifier.PARAMS) != 0 && ptype.ToString ().IndexOf('[') < 0)
2739 Report.Error (30050, lexer.Location, "ParamArray parameters must be an array type");
2740 $$ = new Parameter (ptype, (string) $3, pm,
2741 (Attributes) $1, (Expression) $7, opt_parm);
2745 opt_parameter_modifier
2746 : /* empty */ { $$ = Parameter.Modifier.VAL; }
2747 | parameter_modifiers { $$ = $1; }
2751 : parameter_modifiers parameter_modifier { $$ = (Parameter.Modifier)$1 | (Parameter.Modifier)$2; }
2752 | parameter_modifier { $$ = $1; }
2756 : BYREF { $$ = Parameter.Modifier.REF | Parameter.Modifier.ISBYREF; }
2757 | BYVAL { $$ = Parameter.Modifier.VAL; }
2758 | OPTIONAL { $$ = Parameter.Modifier.OPTIONAL; }
2759 | PARAM_ARRAY { $$ = Parameter.Modifier.PARAMS; }
2764 | statement_list end_of_stmt
2769 | statement_list end_of_stmt statement
2775 end_block { $$ = $3; }
2781 if (current_block == null){
2782 current_block = new ToplevelBlock ((ToplevelBlock) top_current_block, current_local_parameters, lexer.Location);
2783 top_current_block = current_block;
2785 current_block = new Block (current_block, current_local_parameters,
2786 lexer.Location, Location.Null);
2795 while (current_block.Implicit)
2796 current_block = current_block.Parent;
2798 current_block.SetEndLocation (lexer.Location);
2799 current_block = current_block.Parent;
2800 if (current_block == null)
2801 top_current_block = null;
2806 : declaration_statement
2808 if ($1 != null && (Block) $1 != current_block){
2809 current_block.AddStatement ((Statement) $1);
2810 current_block = (Block) $1;
2813 | embedded_statement
2815 Statement s = (Statement) $1;
2817 current_block.AddStatement ((Statement) $1);
2819 // | labeled_statement
2820 | ADDHANDLER prefixed_unary_expression COMMA ADDRESSOF expression
2822 Location loc = lexer.Location;
2824 ExpressionStatement expr = new CompoundAssign (Binary.Operator.Addition,
2825 (Expression) $2, (Expression) $5, loc);
2827 Statement stmt = new StatementExpression (expr, loc);
2829 current_block.AddStatement (stmt);
2833 | REMOVEHANDLER prefixed_unary_expression COMMA ADDRESSOF expression
2835 Location loc = lexer.Location;
2837 ExpressionStatement expr = new CompoundAssign (Binary.Operator.Subtraction,
2838 (Expression) $2, (Expression) $5, loc);
2840 Statement stmt = new StatementExpression (expr, loc);
2842 current_block.AddStatement (stmt);
2845 | RAISEEVENT identifier opt_raise_event_args //OPEN_PARENS opt_argument_list CLOSE_PARENS
2847 Location loc = lexer.Location;
2848 MemberName mname = new MemberName ((string) $2);
2849 Expression expr = mname.GetTypeExpression (loc);
2851 Invocation inv_expr = new Invocation (expr, (ArrayList) $3, loc);
2852 Statement stmt = new StatementExpression (inv_expr, loc);
2853 current_block.AddStatement (stmt);
2855 // /* | array_handling_statement */
2856 // /* | empty_statement */
2859 // Statement s = (Statement) $1;
2861 // current_block.AddStatement ((Statement) $1);
2866 opt_raise_event_args
2867 : /* empty */ { $$ = null; }
2868 | OPEN_PARENS opt_argument_list CLOSE_PARENS
2876 // | LITERAL_INTEGER
2878 // $$ = $1.ToString();
2882 // labeled_statement
2883 // : label_name COLON
2885 // LabeledStatement labeled = new LabeledStatement ((string) $1, lexer.Location);
2887 // if (!current_block.AddLabel ((string) $1, labeled)){
2888 // Location l = lexer.Location;
2889 // Report.Error (140, l, "The label '" + ((string) $1) + "' is a duplicate");
2891 // current_block.AddStatement (labeled);
2893 // | label_name COLON
2895 // LabeledStatement labeled = new LabeledStatement ((string) $1, lexer.Location);
2897 // if (!current_block.AddLabel ((string) $1, labeled)){
2898 // Location l = lexer.Location;
2899 // Report.Error (140, l, "The label '" + ((string) $1) + "' is a duplicate");
2901 // current_block.AddStatement (labeled);
2907 : expression_statement
2908 | selection_statement
2909 // | iteration_statement
2911 | synclock_statement
2913 // | array_handling_statement
2920 // $$ = new EmptyStatement ();
2926 // : WITH expression end_of_stmt /* was : WITH qualified_identifier end_of_stmt */
2928 // // was : Expression e = DecomposeQI ((string) $2, lexer.Location);
2929 // Expression e = (Expression) $2;
2930 // with_stack.Push(e);
2933 // opt_statement_list
2936 // Block b = end_block();
2937 // with_stack.Pop();
2943 // array_handling_statement
2944 // : redim_statement
2945 // | erase_statement
2949 // : REDIM opt_preserve redim_clauses
2951 // ArrayList list = (ArrayList) $3;
2952 // ReDim r = new ReDim (list, (bool) $2, lexer.Location);
2959 // : /* empty */ { $$ = false; }
2960 // | PRESERVE { $$ = true; }
2966 // ArrayList clauses = new ArrayList ();
2968 // clauses.Add ($1);
2971 // | redim_clauses COMMA redim_clause
2973 // ArrayList clauses = (ArrayList) ($1);
2974 // clauses.Add ($2);
2981 // : invocation_expression
2983 // Invocation i = (Invocation) $1;
2984 // RedimClause rc = new RedimClause (i.expr, i.Arguments);
2990 // : ERASE erase_clauses
2992 // ArrayList list = (ArrayList) $2;
2993 // foreach(Expression e in list)
2995 // Erase r = new Erase (e, lexer.Location);
3004 // ArrayList clauses = new ArrayList ();
3006 // clauses.Add ($1);
3009 // | erase_clauses COMMA erase_clause
3011 // ArrayList clauses = (ArrayList) ($1);
3012 // clauses.Add ($2);
3019 // : primary_expression
3024 | continue_statement
3025 | */return_statement
3029 // | yield_statement
3035 $$ = new Goto (current_block, (string) $2, lexer.Location);
3040 : THROW opt_expression
3042 $$ = new Throw ((Expression) $2, lexer.Location);
3049 // $$ = new Exit ((ExitType)$2, lexer.Location);
3054 // : DO { $$ = ExitType.DO; }
3055 // | FOR { $$ = ExitType.FOR; }
3056 // | WHILE { $$ = ExitType.WHILE; }
3057 // | SELECT { $$ = ExitType.SELECT; }
3058 // | SUB { $$ = ExitType.SUB; }
3059 // | FUNCTION { $$ = ExitType.FUNCTION; }
3060 // | PROPERTY { $$ = ExitType.PROPERTY; }
3061 // | TRY { $$ = ExitType.TRY; }
3065 : RETURN opt_expression
3067 $$ = new Return ((Expression) $2, lexer.Location);
3071 // iteration_statement
3072 // : while_statement
3075 // | foreach_statement
3078 // foreach_statement
3079 // : FOR EACH identifier opt_type_spec IN
3081 // oob_stack.Push (lexer.Location);
3083 // expression end_of_stmt
3085 // Location l = lexer.Location;
3086 // LocalVariableReference v = null;
3092 // VariableDeclaration decl = new VariableDeclaration ((string) $3,
3093 // (Expression) $4, null, lexer.Location, null);
3095 // vi = current_block.AddVariable (
3096 // (Expression) $4, decl.identifier, current_local_parameters, decl.Location);
3099 // if (decl.expression_or_array_initializer is Expression)
3100 // expr = (Expression) decl.expression_or_array_initializer;
3101 // else if (decl.expression_or_array_initializer == null)
3105 // ArrayList init = (ArrayList) decl.expression_or_array_initializer;
3106 // expr = new ArrayCreation ((Expression) $4, "", init, decl.Location);
3109 // v = new LocalVariableReference (current_block, decl.identifier, l);
3111 // if (expr != null)
3113 // Assign a = new Assign (v, expr, decl.Location);
3114 // current_block.AddStatement (new StatementExpression (a, lexer.Location));
3119 // vi = current_block.GetVariableInfo ((string) $3);
3121 // if (vi != null) {
3122 // // Get a reference to this variable.
3123 // v = new LocalVariableReference (current_block, (string) $3, l, vi, false);
3126 // Report.Error (451, "Name '" + (string) $3 + "' is not declared.");
3129 // oob_stack.Push (v);
3132 // opt_statement_list
3133 // NEXT opt_identifier
3135 // LocalVariableReference v = (LocalVariableReference) oob_stack.Pop ();
3136 // Block foreach_block = end_block();
3137 // Location l = (Location) oob_stack.Pop ();
3139 // Foreach f = null;
3141 // f = new Foreach (null, v, (Expression) $7, foreach_block, l);
3145 // current_block.AddStatement (f);
3146 // $$ = end_block ();
3154 // : YIELD expression
3156 // if (!UseExtendedSyntax)
3158 // ReportError9998();
3162 // if (iterator_container == null){
3163 // Report.Error (204, lexer.Location, "yield statement can only be used within a method, operator or property");
3166 // iterator_container.SetYields ();
3167 // $$ = new Yield ((Expression) $2, lexer.Location);
3172 // if (!UseExtendedSyntax)
3174 // ReportError9998();
3178 // if (iterator_container == null){
3179 // Report.Error (204, lexer.Location, "yield statement can only be used within a method, operator or property");
3182 // iterator_container.SetYields ();
3183 // $$ = new YieldBreak (lexer.Location);
3189 : SYNCLOCK expression end_of_stmt
3193 $$ = new Lock ((Expression) $2, (Statement) $4, lexer.Location);
3204 : TRY end_of_stmt block opt_catch_clauses END TRY
3208 ArrayList c = (ArrayList)$4;
3209 for (int i = 0; i < c.Count; ++i) {
3210 Catch cc = (Catch) c [i];
3212 if (i != c.Count - 1)
3213 Report.Error (1017, cc.loc, "Empty catch block must be the last in a series of catch blocks");
3220 // Now s contains the list of specific catch clauses
3221 // and g contains the general one.
3223 $$ = new Try ((Block) $3, c, g, null, ((Block) $3).loc);
3236 ArrayList s = new ArrayList (4);
3237 ArrayList catch_list = (ArrayList) $4;
3239 if (catch_list != null){
3240 foreach (Catch cc in catch_list) {
3248 $$ = new Try ((Block) $3, s, g, (Block) $7, ((Block) $3).loc);
3253 : /* empty */ { $$ = null; }
3260 ArrayList l = new ArrayList (4);
3265 | catch_clauses catch_clause
3267 ArrayList l = (ArrayList) $1;
3275 : /* empty */ { $$ = null; }
3280 // : /* empty */ { $$ = null; }
3281 // | WHEN boolean_expression { $$ = $2; }
3286 // : CATCH opt_catch_args opt_when end_of_stmt
3287 : CATCH opt_catch_args end_of_stmt
3289 // FIXME: opt_when needs to be hnadled
3290 Expression type = null;
3294 DictionaryEntry cc = (DictionaryEntry) $2;
3295 type = (Expression) cc.Key;
3296 id = (string) cc.Value;
3299 ArrayList one = new ArrayList (4);
3300 Location loc = lexer.Location;
3302 one.Add (new VariableDeclaration (id, type, loc));
3305 current_block = new Block (current_block);
3306 Block b = declare_local_variables (type, one, loc);
3313 Expression type = null;
3317 DictionaryEntry cc = (DictionaryEntry) $2;
3318 type = (Expression) cc.Key;
3319 id = (string) cc.Value;
3323 // FIXME: I can change this for an assignment.
3325 while (current_block != (Block) $1)
3326 current_block = current_block.Parent;
3331 $$ = new Catch (type, id , (Block) $5, ((Block) $5).loc);
3336 : /* empty */ { $$ = null; }
3341 : identifier AS type
3343 $$ = new DictionaryEntry ($3, $1);
3349 // : DO opt_do_construct end_of_stmt
3352 // oob_stack.Push (lexer.Location);
3354 // opt_statement_list
3355 // LOOP opt_do_construct
3357 // Expression t_before = (Expression) $2;
3358 // Expression t_after = (Expression) $7;
3361 // if ((t_before != null) && (t_after != null))
3362 // Report.Error (30238, "'Loop' cannot have a condition if matching 'Do' has one.");
3364 // if ((t_before == null) && (t_after == null))
3365 // t = new BoolLiteral (true);
3367 // t = (t_before != null) ? t_before : t_after;
3369 // DoOptions test_type = (t_before != null) ? DoOptions.TEST_BEFORE : DoOptions.TEST_AFTER;
3371 // if (((do_type == DoOptions.WHILE) && (test_type == DoOptions.TEST_BEFORE)) ||
3372 // ((do_type == DoOptions.UNTIL) && (test_type == DoOptions.TEST_AFTER)))
3373 // t = new Unary (Unary.Operator.LogicalNot, (Expression) t, lexer.Location);
3375 // $$ = new Do ((Statement) end_block(), (Expression) t, test_type, lexer.Location);
3380 // : /* empty */ { $$ = null; }
3381 // | while_or_until boolean_expression
3383 // do_type = (DoOptions)$1;
3384 // $$ = (Expression) $2;
3389 // : WHILE { $$ = DoOptions.WHILE; }
3390 // | UNTIL { $$ = DoOptions.UNTIL; }
3396 oob_stack.Push (lexer.Location);
3398 boolean_expression end_of_stmt
3404 Location l = (Location) oob_stack.Pop ();
3405 $$ = new While ((Expression) $3, (Statement) $7, l);
3410 // : FOR identifier opt_type_spec ASSIGN expression TO expression opt_step end_of_stmt
3415 // ArrayList VarDeclaration = new ArrayList ();
3416 // VarDeclaration.Add (new VariableDeclaration ((string) $2,
3417 // (Expression) $3, null, lexer.Location, null));
3419 // DictionaryEntry de = new DictionaryEntry (DecomposeQI("_local_vars_", lexer.Location), VarDeclaration);
3420 // Block b = declare_local_variables ((Expression) de.Key, (ArrayList) de.Value, lexer.Location);
3421 // current_block = b;
3423 // oob_stack.Push (lexer.Location);
3426 // opt_statement_list
3427 // NEXT opt_identifier
3429 // Block inner_statement = end_block();
3430 // Location l = (Location) oob_stack.Pop ();
3431 // Expression for_var = (Expression) DecomposeQI ((string)$2, l);
3433 // Expression assign_expr = new Assign (for_var, (Expression) $5, l);
3434 // Expression test_expr = new Binary (Binary.Operator.LessThanOrEqual,
3435 // for_var, (Expression) $7, l);
3436 // Expression step_expr = new Assign (for_var, (Expression) new Binary (Binary.Operator.Addition,
3437 // for_var, (Expression) $8, l), l);
3439 // Statement assign_stmt = new StatementExpression ((ExpressionStatement) assign_expr, l);
3440 // Statement step_stmt = new StatementExpression ((ExpressionStatement) step_expr, l);
3442 // For f = new For (assign_stmt, test_expr, step_stmt, inner_statement, l);
3445 // current_block.AddStatement (f);
3446 // $$ = end_block();
3454 // : /* empty */ { $$ = new IntLiteral ((Int32) 1); }
3455 // | STEP expression { $$ = $2; }
3460 // | select_statement
3464 // : IF boolean_expression opt_then end_of_stmt
3465 // if_statement_rest
3466 // // | IF boolean_expression THEN block opt_else_pre_embedded_statement
3467 // // | IF boolean_expression else_pre_embedded_statement
3471 // FXIME: The rule for LineIfThenStatement needs to be still enabled
3472 // FIXME: The lexer.Location that is calculated may have to replaced with the most correct one
3475 : IF boolean_expression opt_then end_of_stmt
3479 oob_stack.Push (lexer.Location);
3480 Location l = (Location) oob_stack.Pop ();
3482 $$ = new If ((Expression) $2, (Statement) $5, l);
3484 if (RootContext.WarningLevel >= 3){
3485 if ($5 == EmptyStatement.Value)
3486 Report.Warning (642, lexer.Location, "Possible mistaken empty statement");
3491 | IF boolean_expression opt_then end_of_stmt
3497 oob_stack.Push (lexer.Location);
3498 Location l = (Location) oob_stack.Pop ();
3500 $$ = new If ((Expression) $2, (Statement) $5, (Statement) $8, l);
3503 | IF boolean_expression opt_then end_of_stmt
3505 else_if_statement_rest
3507 oob_stack.Push (lexer.Location);
3508 Location l = (Location) oob_stack.Pop ();
3510 $$ = new If ((Expression) $2, (Statement) $5, (Statement) $6, l);
3514 else_if_statement_rest
3515 : ELSEIF boolean_expression opt_then end_of_stmt
3519 oob_stack.Push (lexer.Location);
3520 Location l = (Location) oob_stack.Pop ();
3522 $$ = new If ((Expression) $2, (Statement) $5, l);
3524 if (RootContext.WarningLevel >= 3){
3525 if ($5 == EmptyStatement.Value)
3526 Report.Warning (642, lexer.Location, "Possible mistaken empty statement");
3531 | ELSEIF boolean_expression opt_then end_of_stmt
3537 oob_stack.Push (lexer.Location);
3538 Location l = (Location) oob_stack.Pop ();
3540 $$ = new If ((Expression) $2, (Statement) $5, (Statement) $8, l);
3543 | ELSEIF boolean_expression opt_then end_of_stmt
3545 else_if_statement_rest
3547 oob_stack.Push (lexer.Location);
3548 Location l = (Location) oob_stack.Pop ();
3550 $$ = new If ((Expression) $2, (Statement) $5, (Statement) $6, l);
3555 // opt_else_pre_embedded_statement
3557 // | else_pre_embedded_statement
3560 // else_pre_embedded_statement
3563 // Block bl = end_block();
3564 // tmp_blocks.Push(bl);
3568 // | ELSE embedded_statement
3570 // Block bl = end_block();
3571 // tmp_blocks.Push(bl);
3574 // Statement s = (Statement) $2;
3575 // current_block.AddStatement ((Statement) $2);
3587 // : SELECT opt_case expression end_of_stmt
3589 // oob_stack.Push (lexer.Location);
3590 // switch_stack.Push (current_block);
3592 // opt_case_sections
3595 // $$ = new Switch ((Expression) $3, (ArrayList) $6, (Location) oob_stack.Pop ());
3596 // current_block = (Block) switch_stack.Pop ();
3600 // opt_case_sections
3601 // : /* empty */ { $$ = null; }
3602 // | case_sections { $$ = $1; }
3606 // : case_sections case_section
3608 // ArrayList sections = (ArrayList) $1;
3610 // sections.Add ($2);
3615 // ArrayList sections = new ArrayList (4);
3617 // sections.Add ($1);
3624 // | ends end_of_stmt
3629 // : CASE case_clauses ends
3633 // opt_statement_list
3635 // //Block topmost = current_block;
3636 // Block topmost = end_block();
3638 // while (topmost.Implicit)
3639 // topmost = topmost.Parent;
3641 // // FIXME: This is a horrible hack which MUST go
3642 // topmost.statements.Add (new Break (lexer.Location));
3643 // $$ = new SwitchSection ((ArrayList) $2, topmost);
3646 // /* FIXME: we should somehow flag an error
3647 // (BC30321 'Case' cannot follow a 'Case Else'
3648 // in the same 'Select' statement.)
3649 // if Case Else is not the last of the Case clauses
3654 // opt_statement_list
3656 // //Block topmost = current_block;
3657 // Block topmost = end_block();
3659 // while (topmost.Implicit)
3660 // topmost = topmost.Parent;
3662 // // FIXME: This is a horrible hack which MUST go
3663 // topmost.statements.Add (new Break (lexer.Location));
3665 // ArrayList a = new ArrayList();
3666 // a.Add (new SwitchLabel (null, lexer.Location));
3667 // $$ = new SwitchSection ((ArrayList) a, topmost);
3675 ArrayList labels = new ArrayList ();
3680 | case_clauses COMMA case_clause
3682 ArrayList labels = (ArrayList) ($1);
3690 : opt_is comparison_operator expression
3693 $$ = new SwitchLabel ((Expression) $1, lexer.Location);
3715 expression_statement
3716 : statement_expression
3723 statement_expression
3724 : invocation_expression { $$ = new StatementExpression ((ExpressionStatement) $1, lexer.Location); }
3725 | object_creation_expression { $$ = new StatementExpression ((ExpressionStatement) $1, lexer.Location); }
3726 | assignment_expression { $$ = new StatementExpression ((ExpressionStatement) $1, lexer.Location); }
3729 object_creation_expression
3730 : NEW type OPEN_PARENS opt_argument_list CLOSE_PARENS
3732 $$ = new New ((Expression) $2, (ArrayList) $4, lexer.Location);
3736 $$ = new New ((Expression) $2, new ArrayList(), lexer.Location);
3741 // array_creation_expression
3742 // : object_creation_expression opt_rank_specifiers array_initializer
3744 // New n = (New) $1;
3745 // ArrayList dims = new ArrayList();
3747 // if (n.Arguments != null) {
3748 // foreach (Argument a in n.Arguments) {
3749 // dims.Add (a.Expr);
3753 // Expression atype = n.RequestedType;
3756 // atype = DecomposeQI (atype.ToString () + VariableDeclaration.BuildRanks ((ArrayList)$2, true, lexer.Location), lexer.Location);
3758 // ArrayList init = (ArrayList) $3;
3759 // if (init.Count == 0)
3762 // if (VariableDeclaration.IndexesSpecifiedInRank(dims)) {
3763 // VariableDeclaration.VBFixIndexList (ref dims);
3764 // $$ = new ArrayCreation (atype, dims, "", init, lexer.Location);
3768 // string rank = VariableDeclaration.BuildRank (dims);
3769 // $$ = new ArrayCreation (atype, rank, (ArrayList) $3, lexer.Location);
3771 // //Console.WriteLine ("Creating a new array of type " + (atype.ToString()) + " with rank '" + dims + "'");
3776 : object_creation_expression
3777 // | array_creation_expression
3780 declaration_statement
3781 : local_variable_declaration
3784 DictionaryEntry de = (DictionaryEntry) $1;
3786 $$ = declare_local_variables ((Expression) de.Key, (ArrayList) de.Value, lexer.Location);
3789 | local_constant_declaration
3792 DictionaryEntry de = (DictionaryEntry) $1;
3794 $$ = declare_local_constant ((Expression) de.Key, (ArrayList) de.Value);
3799 local_variable_declaration
3800 : DIM variable_declarators
3802 $$ = new DictionaryEntry (DecomposeQI("_local_vars_", lexer.Location), $2);
3807 local_constant_declaration
3808 : CONST constant_declarators
3811 $$ = new DictionaryEntry (DecomposeQI("_local_consts_", lexer.Location), $2);
3817 constant_declarators
3818 : constant_declarator
3820 ArrayList decl = new ArrayList ();
3826 | constant_declarators COMMA constant_declarator
3828 ArrayList decls = (ArrayList) $1;
3837 : variable_name opt_type_decl opt_variable_initializer
3839 VarName vname = (VarName) $1;
3840 string varname = (string) vname.Name;
3841 current_rank_specifiers = (ArrayList) vname.Rank;
3842 object varinit = $3;
3843 ArrayList a_dims = null;
3845 if (varinit == null)
3847 30438, lexer.Location, "Constant should have a value"
3850 if (vname.Type != null && $2 != null)
3852 30302, lexer.Location,
3853 "Type character cannot be used with explicit type declaration" );
3855 Expression vartype = ($2 == null) ? ((vname.Type == null) ? TypeManager.system_object_expr : (Expression) vname.Type ) : (Expression) $2;
3857 if (current_rank_specifiers != null)
3859 Report.Error (30424, lexer.Location, "Constant doesn't support array");
3863 $$ = new VariableDeclaration (varname, vartype, varinit, lexer.Location, null);
3867 variable_declarators
3868 : variable_declarator
3870 ArrayList decl = new ArrayList ();
3871 decl.AddRange ((ArrayList) $1);
3874 | variable_declarators COMMA variable_declarator
3876 ArrayList decls = (ArrayList) $1;
3877 decls.AddRange ((ArrayList) $3);
3883 : variable_names opt_type_decl opt_variable_initializer
3885 ArrayList names = (ArrayList) $1;
3886 object varinit = $3;
3887 ArrayList VarDeclarations = new ArrayList();
3889 ArrayList a_dims = null;
3891 if ((names.Count > 1) && (varinit != null))
3893 30671, lexer.Location,
3894 "Multiple variables with single type can not have " +
3895 "a explicit initialization" );
3898 foreach (VarName vname in names)
3900 string varname = (string) vname.Name;
3901 current_rank_specifiers = (ArrayList) vname.Rank;
3905 if(vname.Type != null && $2 != null)
3907 30302, lexer.Location,
3908 "Type character cannot be used with explicit type declaration" );
3910 // Some checking is required for particularly weird declarations
3911 // like Dim a As Integer(,)
3913 vartype = (Expression) ((Pair) $2).First;
3915 /*if ($3 != null && $3 is ArrayList)
3916 Report.Error (205, "End of statement expected.");*/
3918 ArrayList args = (ArrayList) ((Pair) $2).Second;
3919 if (current_rank_specifiers != null)
3920 Report.Error (31087, lexer.Location,
3921 "Array types specified in too many places");
3923 if (VariableDeclaration.IndexesSpecifiedInRank (args))
3924 Report.Error (30638, "Array bounds cannot appear in type specifiers.");
3926 current_rank_specifiers = new ArrayList ();
3927 current_rank_specifiers.Add (args);
3930 vartype = ($2 == null) ? ((vname.Type == null) ? TypeManager.system_object_expr : (Expression) vname.Type ) : (Expression) $2;
3932 // if the variable is an array with explicit bound
3933 // and having explicit initialization throw exception
3934 if (current_rank_specifiers != null && varinit != null)
3936 bool broken = false;
3937 foreach (ArrayList exprs in current_rank_specifiers)
3939 foreach (Expression expr in exprs)
3941 if (!((Expression)expr is EmptyExpression ))
3944 30672, lexer.Location,
3945 "Array declared with explicit bound " +
3946 " can not have explicit initialization");
3957 Check for a declaration like Dim a(2) or Dim a(2,3)
3958 If this is the case, we must generate an ArrayCreationExpression
3959 and, in case, add the initializer after the array has been created.
3961 // if (VariableDeclaration.IsArrayDecl (this)) {
3962 // if (VariableDeclaration.IndexesSpecified(current_rank_specifiers)) {
3963 // a_dims = (ArrayList) current_rank_specifiers;
3964 // VariableDeclaration.VBFixIndexLists (ref a_dims);
3965 // varinit = VariableDeclaration.BuildArrayCreator(vartype, a_dims, (ArrayList) varinit, lexer.Location);
3967 // vartype = DecomposeQI (vartype.ToString() + VariableDeclaration.BuildRanks (current_rank_specifiers, false, lexer.Location), lexer.Location);
3970 if (vartype is New) {
3971 if (varinit != null) {
3972 Report.Error (30205, lexer.Location, "End of statement expected");
3978 vartype = ((New)vartype).RequestedType;
3981 VarDeclarations.Add (new VariableDeclaration (varname, vartype, varinit, lexer.Location, null));
3983 $$ = VarDeclarations;
3990 ArrayList list = new ArrayList ();
3994 | variable_names COMMA variable_name
3996 ArrayList list = (ArrayList) $1;
4003 : identifier opt_type_character opt_array_name_modifier
4005 $$ = new VarName ($1, $2, $3);
4016 $$ = (Expression) $2;
4022 // | AS type rank_specifiers
4024 // // $$ = DecomposeQI ($2.ToString() + VariableDeclaration.BuildRanks ((ArrayList)$3, true, lexer.Location), lexer.Location);
4029 : opt_type_with_ranks
4035 New n = new New ((Expression)$3, null, lexer.Location);
4036 $$ = (Expression) n;
4038 | AS NEW type OPEN_PARENS opt_argument_list CLOSE_PARENS
4040 New n = new New ((Expression)$3, (ArrayList) $5, lexer.Location);
4041 $$ = (Expression) n;
4043 /*| AS NEW type OPEN_PARENS ADDRESSOF expression CLOSE_PARENS
4045 ArrayList args = new ArrayList();
4046 Argument arg = new Argument ((Expression) $6, Argument.AType.Expression);
4049 New n = new New ((Expression)$3, (ArrayList) args, lexer.Location);
4050 $$ = (Expression) n;
4054 opt_array_name_modifier
4055 : /* empty */ { $$ = null; }
4056 // | array_type_modifier { $$ = $1; }
4059 // array_type_modifier
4060 // : rank_specifiers { $$ = $1; }
4063 opt_variable_initializer
4064 : /* empty */ { $$ = null; }
4065 | ASSIGN variable_initializer { $$ = $2; }
4068 variable_initializer
4081 : OPEN_BRACE CLOSE_BRACE
4083 ArrayList list = new ArrayList ();
4086 | OPEN_BRACE variable_initializer_list CLOSE_BRACE
4088 $$ = (ArrayList) $2;
4092 variable_initializer_list
4093 : variable_initializer
4095 ArrayList list = new ArrayList ();
4099 | variable_initializer_list COMMA variable_initializer
4101 ArrayList list = (ArrayList) $1;
4122 ArrayList rs = new ArrayList();
4126 | rank_specifiers rank_specifier
4128 ArrayList rs = (ArrayList) $1;
4135 : OPEN_PARENS opt_dim_specifiers CLOSE_PARENS
4144 ArrayList ds = new ArrayList();
4145 ds.Add (new EmptyExpression());
4150 ArrayList ds = new ArrayList();
4151 ds.Add ((Expression) $1);
4154 | opt_dim_specifiers COMMA expression
4156 ArrayList ds = (ArrayList) $1;
4157 ds.Add ((Expression) $3);
4160 | opt_dim_specifiers COMMA
4162 ArrayList ds = (ArrayList) $1;
4163 ds.Add (new EmptyExpression());
4168 // primary_expression
4173 // | parenthesized_expression
4176 // | qualified_identifier
4178 // string name = (string) $1;
4179 // $$ = DecomposeQI (name, lexer.Location);
4181 // | get_type_expression
4183 // | invocation_expression
4184 // //| element_access
4186 // | cast_expression
4194 | parenthesized_expression
4197 | qualified_identifier
4199 $$ = ((MemberName) $1).GetTypeExpression (lexer.Location);
4201 | get_type_expression
4203 | invocation_expression
4215 | LITERAL_DATE { $$ = new DateLiteral ((DateTime)lexer.Value); }
4216 | LITERAL_CHARACTER { $$ = new CharLiteral ((char) lexer.Value); }
4217 | LITERAL_STRING { $$ = new StringLiteral ((string) lexer.Value); }
4218 | NOTHING { $$ = NullLiteral.Null; }
4222 : LITERAL_SINGLE { $$ = new FloatLiteral ((float) lexer.Value); }
4223 | LITERAL_DOUBLE { $$ = new DoubleLiteral ((double) lexer.Value); }
4224 | LITERAL_DECIMAL { $$ = new DecimalLiteral ((decimal) lexer.Value); }
4229 object v = lexer.Value;
4232 $$ = new IntLiteral ((Int32)v);
4233 // else if (v is short)
4234 // $$ = new ShortLiteral ((Int16)v);
4236 $$ = new LongLiteral ((Int64)v);
4238 Console.WriteLine ("OOPS. Unexpected result from scanner");
4244 : TRUE { $$ = new BoolLiteral (true); }
4245 | FALSE { $$ = new BoolLiteral (false); }
4248 parenthesized_expression
4249 : OPEN_PARENS expression CLOSE_PARENS
4254 : primary_expression DOT identifier
4257 string id_name = (string)$3;
4258 if (id_name.ToUpper() == "NEW")
4260 $$ = new MemberAccess ((Expression) $1, id_name, lexer.Location);
4264 // if (with_stack.Count > 0) {
4265 // Expression e = (Expression) with_stack.Peek();
4266 // $$ = new MemberAccess (e, (string) $3, lexer.Location);
4274 /* | primary_expression DOT NEW
4276 $$ = new MemberAccess ((Expression) $1, (string) ".ctor", lexer.Location);
4278 | predefined_type DOT identifier
4281 $$ = new MemberAccess ((Expression) $1, (string) $3, lexer.Location);
4284 // if (with_stack.Count > 0) {
4285 // Expression e = (Expression) with_stack.Peek();
4286 // $$ = new MemberAccess (e, (string) $3, lexer.Location);
4300 invocation_expression
4301 : primary_expression OPEN_PARENS opt_argument_list CLOSE_PARENS
4304 Location l = lexer.Location;
4305 Report.Error (1, l, "Parse error");
4307 $$ = new Invocation ((Expression) $1, (ArrayList) $3, lexer.Location);
4309 | CALL primary_expression OPEN_PARENS opt_argument_list CLOSE_PARENS
4312 Location l = lexer.Location;
4313 Report.Error (1, l, "THIS IS CRAZY");
4315 $$ = new Invocation ((Expression) $2, (ArrayList) $3, lexer.Location);
4316 // Console.WriteLine ("Invocation: {0} with {1} arguments", $2, ($3 != null) ? ((ArrayList) $3).Count : 0);
4321 : MYBASE DOT IDENTIFIER
4323 string id_name = (string) $3;
4324 if (id_name.ToUpper() == "NEW")
4326 $$ = new BaseAccess (id_name, lexer.Location);
4330 $$ = new BaseAccess ("New", lexer.Location);
4338 The 'argument' rule returns an 'empty' argument
4339 of type NoArg (used for default arguments in invocations)
4340 if no arguments are actually passed.
4342 If there is only one argument and it is o type NoArg,
4343 we return a null (empty) list
4345 ArrayList args = (ArrayList) $1;
4346 if (args.Count == 1 &&
4347 ((Argument)args[0]).ArgType == Argument.AType.NoArg)
4357 ArrayList list = new ArrayList ();
4361 | argument_list COMMA argument
4363 ArrayList list = (ArrayList) $1;
4372 $$ = new Argument ((Expression) $1, Argument.AType.Expression);
4374 | BYREF variable_reference
4376 $$ = new Argument ((Expression) $2, Argument.AType.Ref);
4380 $$ = new Argument (new EmptyExpression (), Argument.AType.NoArg);
4382 | ADDRESSOF expression
4384 $$ = new Argument ((Expression) $2, Argument.AType.AddressOf);
4389 : expression {/* note ("section 5.4"); */ $$ = $1; }
4394 : conditional_xor_expression { $$ = $1; }
4395 /*| assignment_expression*/
4406 $$ = new This (current_block, lexer.Location);
4410 // FIXME: This is actually somewhat different from Me
4411 // because it is for accessing static (classifier) methods/properties/fields
4412 $$ = new This (current_block, lexer.Location);
4417 : DIRECTCAST OPEN_PARENS expression COMMA type CLOSE_PARENS
4421 | CTYPE OPEN_PARENS expression COMMA type CLOSE_PARENS
4423 $$ = new Cast ((Expression) $5, (Expression) $3, lexer.Location);
4425 | cast_operator OPEN_PARENS expression CLOSE_PARENS
4427 $$ = new Cast ((Expression) $1, (Expression) $3, lexer.Location);
4432 : CBOOL { $$ = TypeManager.system_boolean_expr; }
4433 | CBYTE { $$ = TypeManager.system_byte_expr; }
4434 | CCHAR { $$ = TypeManager.system_char_expr; }
4435 | CDATE { $$ = TypeManager.system_date_expr; }
4436 | CDBL { $$ = TypeManager.system_double_expr; }
4437 | CDEC { $$ = TypeManager.system_decimal_expr; }
4438 | CINT { $$ = TypeManager.system_int32_expr; }
4439 | CLNG { $$ = TypeManager.system_int64_expr; }
4440 | COBJ { $$ = TypeManager.system_object_expr; }
4441 | CSHORT { $$ = TypeManager.system_int16_expr; }
4442 | CSNG { $$ = TypeManager.system_single_expr; }
4443 | CSTR { $$ = TypeManager.system_string_expr; }
4447 : GETTYPE OPEN_PARENS type CLOSE_PARENS
4449 $$ = new TypeOf ((Expression) $3, lexer.Location);
4453 exponentiation_expression
4454 : primary_expression
4455 | exponentiation_expression OP_EXP primary_expression
4457 $$ = new Binary (Binary.Operator.Exponentiation,
4458 (Expression) $1, (Expression) $3, lexer.Location);
4462 prefixed_unary_expression
4463 : exponentiation_expression
4464 | PLUS prefixed_unary_expression
4466 //FIXME: Is this rule correctly defined ?
4467 $$ = new Unary (Unary.Operator.UnaryPlus, (Expression) $2, lexer.Location);
4469 | MINUS prefixed_unary_expression
4471 //FIXME: Is this rule correctly defined ?
4472 $$ = new Unary (Unary.Operator.UnaryNegation, (Expression) $2, lexer.Location);
4476 multiplicative_expression
4477 : prefixed_unary_expression
4478 | multiplicative_expression STAR prefixed_unary_expression
4480 $$ = new Binary (Binary.Operator.Multiply,
4481 (Expression) $1, (Expression) $3, lexer.Location);
4483 | multiplicative_expression DIV prefixed_unary_expression
4485 $$ = new Binary (Binary.Operator.Division,
4486 (Expression) $1, (Expression) $3, lexer.Location);
4490 integer_division_expression
4491 : multiplicative_expression
4492 | integer_division_expression OP_IDIV multiplicative_expression
4494 $$ = new Binary (Binary.Operator.IntegerDivision,
4495 (Expression) $1, (Expression) $3, lexer.Location);
4500 : integer_division_expression
4501 | mod_expression MOD integer_division_expression
4503 $$ = new Binary (Binary.Operator.Modulus,
4504 (Expression) $1, (Expression) $3, lexer.Location);
4510 | additive_expression PLUS mod_expression
4512 $$ = new Binary (Binary.Operator.Addition,
4513 (Expression) $1, (Expression) $3, lexer.Location);
4515 | additive_expression MINUS mod_expression
4517 $$ = new Binary (Binary.Operator.Subtraction,
4518 (Expression) $1, (Expression) $3, lexer.Location);
4523 : additive_expression
4524 | concat_expression OP_CONCAT additive_expression
4526 $$ = new Binary (Binary.Operator.Concatenation,
4527 (Expression) $1, (Expression) $3, lexer.Location);
4533 | shift_expression OP_SHIFT_LEFT concat_expression
4535 $$ = new Binary (Binary.Operator.LeftShift,
4536 (Expression) $1, (Expression) $3, lexer.Location);
4538 | shift_expression OP_SHIFT_RIGHT concat_expression
4540 $$ = new Binary (Binary.Operator.RightShift,
4541 (Expression) $1, (Expression) $3, lexer.Location);
4545 relational_expression
4547 | relational_expression ASSIGN shift_expression
4549 $$ = new Binary (Binary.Operator.Equality,
4550 (Expression) $1, (Expression) $3, lexer.Location);
4552 | relational_expression OP_NE shift_expression
4554 $$ = new Binary (Binary.Operator.Inequality,
4555 (Expression) $1, (Expression) $3, lexer.Location);
4557 | relational_expression OP_LT shift_expression
4559 $$ = new Binary (Binary.Operator.LessThan,
4560 (Expression) $1, (Expression) $3, lexer.Location);
4562 | relational_expression OP_GT shift_expression
4564 $$ = new Binary (Binary.Operator.GreaterThan,
4565 (Expression) $1, (Expression) $3, lexer.Location);
4567 | relational_expression OP_LE shift_expression
4569 $$ = new Binary (Binary.Operator.LessThanOrEqual,
4570 (Expression) $1, (Expression) $3, lexer.Location);
4572 | relational_expression OP_GE shift_expression
4574 $$ = new Binary (Binary.Operator.GreaterThanOrEqual,
4575 (Expression) $1, (Expression) $3, lexer.Location);
4577 | relational_expression IS shift_expression
4579 $$ = new Binary (Binary.Operator.Is,
4580 (Expression) $1, (Expression) $3, lexer.Location);
4582 | relational_expression LIKE shift_expression
4584 $$ = new Binary (Binary.Operator.Like,
4585 (Expression) $1, (Expression) $3, lexer.Location);
4587 | TYPEOF shift_expression IS type
4589 $$ = new Is ((Expression) $2, (Expression) $4, lexer.Location);
4594 : relational_expression
4595 | NOT negation_expression
4597 $$ = new Unary (Unary.Operator.OnesComplement, (Expression) $2, lexer.Location);
4601 conditional_and_expression
4602 : negation_expression
4603 | conditional_and_expression AND negation_expression
4605 $$ = new Binary (Binary.Operator.BitwiseAnd,
4606 (Expression) $1, (Expression) $3, lexer.Location);
4608 | conditional_and_expression ANDALSO negation_expression
4610 $$ = new Binary (Binary.Operator.LogicalAndAlso,
4611 (Expression) $1, (Expression) $3, lexer.Location);
4615 conditional_or_expression
4616 : conditional_and_expression
4617 | conditional_or_expression OR conditional_and_expression
4619 $$ = new Binary (Binary.Operator.BitwiseOr,
4620 (Expression) $1, (Expression) $3, lexer.Location);
4622 | conditional_or_expression ORELSE conditional_and_expression
4624 $$ = new Binary (Binary.Operator.LogicalOrElse,
4625 (Expression) $1, (Expression) $3, lexer.Location);
4629 conditional_xor_expression
4630 : conditional_or_expression
4631 | conditional_xor_expression XOR conditional_or_expression
4633 $$ = new Binary (Binary.Operator.ExclusiveOr,
4634 (Expression) $1, (Expression) $3, lexer.Location);
4638 assignment_expression
4639 : prefixed_unary_expression ASSIGN expression
4641 $$ = new Assign ((Expression) $1, (Expression) $3, lexer.Location);
4643 | prefixed_unary_expression STAR ASSIGN expression
4645 Location l = lexer.Location;
4647 $$ = new CompoundAssign (
4648 Binary.Operator.Multiply, (Expression) $1, (Expression) $4, l);
4650 | prefixed_unary_expression DIV ASSIGN expression
4652 Location l = lexer.Location;
4654 $$ = new CompoundAssign (
4655 Binary.Operator.Division, (Expression) $1, (Expression) $4, l);
4657 | prefixed_unary_expression PLUS ASSIGN expression
4659 Location l = lexer.Location;
4661 $$ = new CompoundAssign (
4662 Binary.Operator.Addition, (Expression) $1, (Expression) $4, l);
4664 | prefixed_unary_expression MINUS ASSIGN expression
4666 Location l = lexer.Location;
4668 $$ = new CompoundAssign (
4669 Binary.Operator.Subtraction, (Expression) $1, (Expression) $4, l);
4671 | prefixed_unary_expression OP_SHIFT_LEFT ASSIGN expression
4673 Location l = lexer.Location;
4675 $$ = new CompoundAssign (
4676 Binary.Operator.LeftShift, (Expression) $1, (Expression) $4, l);
4678 | prefixed_unary_expression OP_SHIFT_RIGHT ASSIGN expression
4680 Location l = lexer.Location;
4682 $$ = new CompoundAssign (
4683 Binary.Operator.RightShift, (Expression) $1, (Expression) $4, l);
4685 | prefixed_unary_expression OP_CONCAT ASSIGN expression
4687 Location l = lexer.Location;
4689 // FIXME should be strings only
4690 $$ = new CompoundAssign (
4691 Binary.Operator.Addition, (Expression) $1, (Expression) $4, l);
4693 | prefixed_unary_expression OP_EXP ASSIGN expression
4695 Location l = lexer.Location;
4697 /* TODO: $$ = new CompoundAssign (
4698 Binary.Operator.ExclusiveOr, (Expression) $1, (Expression) $4, l); */
4700 | prefixed_unary_expression ASSIGN ADDRESSOF expression
4702 // ArrayList args = new ArrayList();
4703 // Argument arg = new Argument ((Expression) $4, Argument.AType.Expression);
4706 // New n = new New ((Expression) $1, (ArrayList) args, lexer.Location);
4707 // n.isDelegate = true;
4708 $$ = new Assign ((Expression) $1, (Expression) $4, lexer.Location);
4721 : namespace_or_type_name
4723 $$ = ((MemberName) $1).GetTypeExpression (lexer.Location);
4732 ArrayList types = new ArrayList ();
4737 | type_list COMMA type
4739 ArrayList types = (ArrayList) $1;
4746 namespace_or_type_name
4747 : qualified_identifier
4751 : OBJECT { $$ = TypeManager.system_object_expr; }
4757 | BOOLEAN { $$ = TypeManager.system_boolean_expr; }
4758 | DATE { $$ = TypeManager.system_date_expr; }
4759 | CHAR { $$ = TypeManager.system_char_expr; }
4760 | STRING { $$ = TypeManager.system_string_expr; }
4766 | floating_point_type
4767 | DECIMAL { $$ = TypeManager.system_decimal_expr; }
4772 | BYTE { $$ = TypeManager.system_byte_expr; }
4773 | SHORT { $$ = TypeManager.system_int16_expr; }
4774 | INTEGER { $$ = TypeManager.system_int32_expr; }
4775 | LONG { $$ = TypeManager.system_int64_expr; }
4779 : SINGLE { $$ = TypeManager.system_single_expr; }
4780 | DOUBLE { $$ = TypeManager.system_double_expr; }
4784 : HASH IDENTIFIER OPEN_PARENS LITERAL_STRING COMMA LITERAL_INTEGER CLOSE_PARENS EOL
4786 // if(tokenizerController.IsAcceptingTokens)
4788 // if(in_external_source)
4789 // Report.Error (30580, lexer.Location, "#ExternalSource directives may not be nested");
4791 // in_external_source = true;
4793 // lexer.EffectiveSource = (string) $4;
4794 // lexer.EffectiveLine = (int) $6;
4798 | HASH IDENTIFIER LITERAL_STRING EOL
4800 if(tokenizerController.IsAcceptingTokens)
4802 string id = ($2 as string);
4804 if(!($2 as string).ToLower().Equals("region"))
4805 Report.Error (30205, lexer.Location, "Invalid Pre-processor directive");
4812 | HASH END IDENTIFIER EOL
4814 if(tokenizerController.IsAcceptingTokens)
4816 // if( ($3 as string).ToLower().Equals("externalsource")) {
4817 // if(!in_external_source)
4818 // Report.Error (30578, lexer.Location, "'#End ExternalSource' must be preceded by a matching '#ExternalSource'");
4820 // in_external_source = false;
4821 // lexer.EffectiveSource = lexer.Source;
4822 // lexer.EffectiveLine = lexer.Line;
4825 /* else */if(($3 as string).ToLower().Equals("region")) {
4826 if(in_marked_region > 0)
4829 Report.Error (30205, lexer.Location, "'#End Region' must be preceded by a matching '#Region'");
4832 Report.Error (29999, lexer.Location, "Unrecognized Pre-Processor statement");
4836 | HASH CONST IDENTIFIER ASSIGN boolean_literal EOL
4838 if(tokenizerController.IsAcceptingTokens)
4845 IfElseStateMachine.Token tok = IfElseStateMachine.Token.IF;
4848 ifElseStateMachine.HandleToken(tok);
4850 catch(ApplicationException) {
4851 throw new MBASException(ifElseStateMachine.Error, lexer.Location, ifElseStateMachine.ErrString);
4854 boolean_literal opt_then EOL
4856 HandleConditionalDirective(IfElseStateMachine.Token.IF, (BoolLiteral)$4);
4860 IfElseStateMachine.Token tok = IfElseStateMachine.Token.ELSEIF;
4862 ifElseStateMachine.HandleToken(tok);
4864 catch(ApplicationException) {
4865 throw new MBASException(ifElseStateMachine.Error, lexer.Location, ifElseStateMachine.ErrString);
4868 boolean_literal opt_then EOL
4870 HandleConditionalDirective(IfElseStateMachine.Token.ELSEIF, (BoolLiteral)$4);
4874 IfElseStateMachine.Token tok = IfElseStateMachine.Token.ELSE;
4876 ifElseStateMachine.HandleToken(tok);
4878 catch(ApplicationException) {
4879 throw new MBASException(ifElseStateMachine.Error, lexer.Location, ifElseStateMachine.ErrString);
4884 HandleConditionalDirective(IfElseStateMachine.Token.ELSE, new BoolLiteral(true));
4888 IfElseStateMachine.Token tok = IfElseStateMachine.Token.ENDIF;
4890 ifElseStateMachine.HandleToken(tok);
4892 catch(ApplicationException) {
4893 throw new MBASException(ifElseStateMachine.Error, lexer.Location, ifElseStateMachine.ErrString);
4898 HandleConditionalDirective(IfElseStateMachine.Token.ENDIF, new BoolLiteral(false));
4902 if(tokenizerController.IsAcceptingTokens)
4903 Report.Error(2999, lexer.Location, "Unrecognized Pre-Processor statement");
4905 Report.Warning (9999, lexer.Location, "Unrecognized Pre-Processor statement");
4915 public Tokenizer Lexer {
4921 public static Expression DecomposeQI (string name, Location loc)
4925 if (name.IndexOf ('.') == -1){
4926 return new SimpleName (name, loc);
4928 int pos = name.LastIndexOf (".");
4929 string left = name.Substring (0, pos);
4930 string right = name.Substring (pos + 1);
4932 o = DecomposeQI (left, loc);
4934 return new MemberAccess (o, right, loc);
4938 Block declare_local_variables (Expression dummy_type, ArrayList variable_declarators, Location loc)
4940 Block implicit_block;
4941 ArrayList inits = null;
4944 // We use the `Used' property to check whether statements
4945 // have been added to the current block. If so, we need
4946 // to create another block to contain the new declaration
4947 // otherwise, as an optimization, we use the same block to
4948 // add the declaration.
4950 // FIXME: A further optimization is to check if the statements
4951 // that were added were added as part of the initialization
4952 // below. In which case, no other statements have been executed
4953 // and we might be able to reduce the number of blocks for
4954 // situations like this:
4956 // int j = 1; int k = j + 1;
4959 VariableDeclaration.FixupTypes (variable_declarators);
4960 // FIXME: Should VariableDeclaration.FixupArrayTypes be called here
4962 if (current_block.Used)
4963 implicit_block = new Block (current_block, Block.Flags.Implicit, loc, Location.Null);
4965 implicit_block = current_block;
4968 foreach (VariableDeclaration decl in variable_declarators){
4969 Expression type = decl.type;
4970 if (implicit_block.AddVariable (type, decl.identifier, current_local_parameters, decl.Location) != null) {
4971 if (decl.expression_or_array_initializer != null){
4973 inits = new ArrayList ();
4980 return implicit_block;
4982 foreach (VariableDeclaration decl in inits){
4985 Expression type = decl.type;
4987 if ((decl.expression_or_array_initializer is Expression) ||
4988 (decl.expression_or_array_initializer is New)) {
4989 expr = (Expression) decl.expression_or_array_initializer;
4991 ArrayList init = (ArrayList) decl.expression_or_array_initializer;
4993 expr = new ArrayCreation (type, "", init, decl.Location);
4996 LocalVariableReference var;
4997 var = new LocalVariableReference (implicit_block, decl.identifier, loc);
4999 assign = new Assign (var, expr, decl.Location);
5001 implicit_block.AddStatement (new StatementExpression (assign, lexer.Location));
5004 return implicit_block;
5007 Block declare_local_constant (Expression dummy_type, ArrayList variable_declarators)
5009 Block implicit_block;
5010 VariableDeclaration.FixupTypes (variable_declarators);
5012 if (current_block.Used)
5013 implicit_block = new Block (current_block, Block.Flags.Implicit);
5015 implicit_block = current_block;
5017 foreach (VariableDeclaration decl in variable_declarators){
5018 Expression type = decl.type;
5019 implicit_block.AddConstant (type, decl.identifier, (Expression) decl.expression_or_array_initializer,
5020 current_local_parameters, decl.Location);
5023 return implicit_block;
5033 public VarName (object n, object t, object r)
5043 // A class used to pass around variable declarations and constants
5045 public class VariableDeclaration {
5046 public string identifier;
5047 public object expression_or_array_initializer;
5048 public Location Location;
5049 public Attributes OptAttributes;
5050 public string DocComment;
5051 public Expression type;
5052 public ArrayList dims;
5054 public VariableDeclaration (string id, Expression t, object eoai, Location l, Attributes opt_attrs)
5056 this.identifier = id;
5057 this.expression_or_array_initializer = eoai;
5059 this.OptAttributes = opt_attrs;
5064 public VariableDeclaration (string id, object eoai, Location l) : this (id, eoai, l, null)
5068 public VariableDeclaration (string id, Expression t, Location l) : this (id, t, null, l, null)
5072 public VariableDeclaration (string id, object eoai, Location l, Attributes opt_attrs) : this
5073 (id, TypeManager.system_object_expr, eoai, l, opt_attrs)
5077 public static ArrayCreation BuildArrayCreator (Expression vartype, ArrayList a_dims, ArrayList varinit, Location l)
5079 // FIXME : This is broken: only the first rank is parsed
5080 return new ArrayCreation (vartype, (ArrayList) a_dims[0], "", varinit, l);
5083 public static void FixupTypes (ArrayList vars)
5085 int varcount = vars.Count;
5086 VariableDeclaration last_var = (VariableDeclaration) vars[varcount - 1];
5088 if (last_var.type == null)
5089 last_var.type = TypeManager.system_object_expr;
5091 Expression cur_type = last_var.type;
5092 int n = varcount - 1;
5095 VariableDeclaration var = (VariableDeclaration) vars[n--];
5096 if (var.type == null)
5097 var.type = cur_type;
5099 cur_type = var.type;
5103 public static bool IndexesSpecifiedInRank (ArrayList IndexList)
5107 if (IndexList != null) {
5108 foreach (Expression e in IndexList)
5109 if (!(e is EmptyExpression)) {
5118 public static bool IndexesSpecified (ArrayList ranks)
5122 if (ranks != null) {
5123 foreach (ArrayList IndexList in ranks) {
5124 if (IndexesSpecifiedInRank (IndexList)) {
5133 public static string StripDims (string varname, ref string d)
5135 string res = varname;
5138 if (varname.IndexOf("[") >= 0) {
5139 dres = varname.Substring(varname.IndexOf("["), (varname.LastIndexOf("]") - varname.IndexOf("["))+1);
5140 res = varname.Substring(0, varname.IndexOf("["));
5146 public static string StripDims (string varname)
5150 return (StripDims(varname, ref dres));
5153 public static string StripIndexesFromDims (string dims)
5155 StringBuilder sb = new StringBuilder();
5157 foreach (char c in dims)
5158 if (c == ',' || c == ']' || c == '[')
5161 return sb.ToString();
5164 public static string BuildRank (ArrayList rank)
5167 return BuildRank(rank, out allEmpty);
5170 public static string BuildRank (ArrayList rank, out bool allEmpty)
5177 foreach (object e in rank) {
5178 if (!(e is EmptyExpression))
5189 public static string BuildRanks (ArrayList rank_specifiers, bool mustBeEmpty, Location loc)
5193 bool allEmpty = true;
5194 foreach (ArrayList rank in rank_specifiers) {
5196 res = BuildRank (rank, out tmp) + res;
5200 if (!allEmpty && mustBeEmpty)
5201 Report.Error (30638, loc, "Array bounds cannot appear in type specifiers.");
5206 public static void VBFixIndexList (ref ArrayList IndexList)
5208 if (IndexList != null) {
5209 for (int x = 0; x < IndexList.Count; x++) {
5210 Expression e = (Expression) IndexList[x];
5211 if (!(e is EmptyExpression)) {
5212 IndexList[x] = new Binary (Binary.Operator.Addition, e, new IntLiteral(1), Location.Null);
5218 // public static bool IsArrayDecl (Parser t)
5220 // // return (varname.IndexOf("[") >= 0);
5221 // return (t.current_rank_specifiers != null);
5224 public static void VBFixIndexLists (ref ArrayList ranks)
5226 if (ranks != null) {
5227 for (int x = 0; x < ranks.Count; x++) {
5228 ArrayList IndexList = (ArrayList) ranks[x];
5229 VBFixIndexList (ref IndexList);
5234 public static void FixupArrayTypes (ArrayList vars)
5236 int varcount = vars.Count;
5239 foreach (VariableDeclaration var in vars) {
5240 if (var.identifier.EndsWith(",")) {
5241 dims = "[" + var.identifier.Substring(var.identifier.IndexOf (","),
5242 var.identifier.LastIndexOf(",")) + "]";
5243 var.identifier = var.identifier.Substring (0, var.identifier.IndexOf (","));
5244 var.type = new ComposedCast (var.type, (string) dims, var.Location);
5251 // public Property BuildSimpleProperty (Expression p_type, string name,
5252 // Field p_fld, int mod_flags,
5253 // Attributes attrs, Location loc)
5256 // Block get_block, set_block;
5257 // Accessor acc_set, acc_get;
5258 // StatementExpression a_set;
5260 // Parameter [] args;
5262 // // Build SET Block
5263 // Parameter implicit_value_parameter = new Parameter (p_type, "value", Parameter.Modifier.NONE, null);
5264 // args = new Parameter [1];
5265 // args [0] = implicit_value_parameter;
5267 // Parameters set_params = new Parameters (args, null, loc);
5268 // a_set = new StatementExpression ((ExpressionStatement) new Assign ((Expression) DecomposeQI(p_fld.Name, loc),
5269 // (Expression) new SimpleName("value", loc), loc), loc);
5271 // set_block = new Block (current_block, set_params, loc, Location.Null);
5272 // set_block.AddStatement ((Statement) a_set);
5273 // acc_set = new Accessor (set_block, attrs);
5275 // // Build GET Block
5276 // a_get = (Statement) new Return ((Expression) DecomposeQI(p_fld.Name, loc), loc);
5277 // get_block = new Block (current_block, null, loc, Location.Null);
5278 // get_block.AddStatement ((Statement) a_get);
5279 // acc_get = new Accessor (get_block, attrs);
5281 // p = new Property (p_type, name, mod_flags, (Accessor) acc_get, (Accessor) acc_set, attrs, loc);
5288 if (current_block == null){
5289 current_block = new ToplevelBlock ((ToplevelBlock) top_current_block,
5290 current_local_parameters, lexer.Location);
5291 top_current_block = current_block;
5293 current_block = new Block (current_block, current_local_parameters,
5294 lexer.Location, Location.Null);
5303 while (current_block.Implicit)
5304 current_block = current_block.Parent;
5305 res = current_block;
5306 current_block.SetEndLocation (lexer.Location);
5307 current_block = current_block.Parent;
5308 if (current_block == null)
5309 top_current_block = null;
5314 // private void AddHandler (Expression evt_definition, Expression handler_exp)
5316 // AddHandler (current_block, evt_definition, handler_exp);
5319 void CheckAttributeTarget (string a)
5323 case "assembly" : case "field" : case "method" : case "param" : case "property" : case "type" :
5327 Location l = lexer.Location;
5328 Report.Error (658, l, "`" + a + "' is an invalid attribute target");
5333 // private void AddHandler (Block b, Expression evt_id, Expression handles_exp)
5335 // Expression evt_target;
5336 // Location loc = lexer.Location;
5338 // Statement addhnd = (Statement) new AddHandler (evt_id,
5342 // b.AddStatement (addhnd);
5345 // private void RaiseEvent (string evt_name, ArrayList args)
5347 // Location loc = lexer.Location;
5349 // Invocation evt_call = new Invocation (DecomposeQI(evt_name, loc), args, lexer.Location);
5350 // Statement s = (Statement)(new StatementExpression ((ExpressionStatement) evt_call, loc));
5351 // current_block.AddStatement (s);
5354 // private void RemoveHandler (Block b, Expression evt_definition, Expression handler_exp)
5356 // Expression evt_target;
5357 // Location loc = lexer.Location;
5359 // Statement rmhnd = (Statement) new RemoveHandler (evt_definition,
5362 // b.AddStatement (rmhnd);
5366 // This method is used to get at the complete string representation of
5367 // a fully-qualified type name, hiding inside a MemberAccess ;-)
5368 // This is necessary because local_variable_type admits primary_expression
5369 // as the type of the variable. So we do some extra checking
5371 string GetQualifiedIdentifier (Expression expr)
5373 if (expr is SimpleName)
5374 return ((SimpleName)expr).Name;
5375 else if (expr is MemberAccess)
5376 return GetQualifiedIdentifier (((MemberAccess)expr).Expr) + "." + ((MemberAccess) expr).Identifier;
5378 throw new Exception ("Expr has to be either SimpleName or MemberAccess! (" + expr + ")");
5382 // private void RemoveHandler (Expression evt_definition, Expression handler_exp)
5384 // RemoveHandler (current_block, evt_definition, handler_exp);
5387 // FIXME: This needs to be fixed for This and Base access because the way the name of the
5388 // mbas' constructor is changed from "New" to current_container.Basename
5390 private ConstructorInitializer CheckConstructorInitializer (ref ArrayList s)
5392 ConstructorInitializer ci = null;
5395 if (s[0] is StatementExpression && ((StatementExpression) s[0]).expr is Invocation) {
5396 Invocation i = (Invocation) ((StatementExpression) s[0]).expr;
5398 if (i.expr is BaseAccess) {
5399 BaseAccess ba = (BaseAccess) i.expr;
5400 if (ba.member == "New" || ba.member == ".ctor") {
5401 ci = new ConstructorBaseInitializer (i.Arguments, current_local_parameters, lexer.Location);
5405 if (i.expr.ToString() == "Mono.MonoBASIC.This..ctor") {
5406 ci = new ConstructorThisInitializer (i.Arguments, current_local_parameters, lexer.Location);
5414 void Error_ExpectingTypeName (Location l, Expression expr)
5416 if (expr is Invocation){
5417 Report.Error (1002, l, "; expected");
5419 Report.Error (-1, l, "Invalid Type definition");
5423 static bool AlwaysAccept (MemberInfo m, object filterCriteria) {
5427 private void ReportError9998()
5429 Report.Error (29998, lexer.Location, "This construct is only available in MonoBASIC extended syntax.");
5432 public CSharpParser (SeekableStreamReader reader, SourceFile file, ArrayList defines)
5434 current_namespace = new NamespaceEntry (null, file, null, Location.Null);
5435 this.name = file.Name;
5437 current_container = RootContext.Tree.Types;
5438 current_container.NamespaceEntry = current_namespace;
5439 oob_stack = new Stack ();
5440 switch_stack = new Stack ();
5442 lexer = new Tokenizer (reader, file, defines);
5444 ifElseStateMachine = new IfElseStateMachine();
5445 tokenizerController = new TokenizerController(lexer);
5448 public void parse ()
5451 if (yacc_verbose_flag > 1)
5452 yyparse (lexer, new yydebug.yyDebugSimple ());
5455 Tokenizer tokenizer = lexer as Tokenizer;
5456 tokenizer.cleanup ();
5457 } catch (Exception e){
5459 // Removed for production use, use parser verbose to get the output.
5461 // Console.WriteLine (e);
5462 Report.Error (-25, lexer.Location, "Parsing error");
5463 if (yacc_verbose_flag > 0)
5464 Console.WriteLine (e);
5469 // protected override int parse ()
5471 // RootContext.InitializeImports(ImportsList);
5472 // current_namespace = new Namespace (null, RootContext.RootNamespace);
5473 // current_container = RootContext.Tree.Types;
5474 // current_container.Namespace = current_namespace;
5475 // oob_stack = new Stack ();
5476 // switch_stack = new Stack ();
5477 // expr_stack = new Stack ();
5478 // tmp_blocks = new Stack();
5479 // with_stack = new Stack();
5480 // statement_stack = new Stack();
5482 // allow_global_attribs = true;
5483 // expecting_global_attribs = false;
5484 // expecting_local_attribs = false;
5485 // local_attrib_section_added = false;
5487 // UseExtendedSyntax = name.EndsWith(".mbs");
5488 // OptionExplicit = InitialOptionExplicit || UseExtendedSyntax;
5489 // OptionStrict = InitialOptionStrict || UseExtendedSyntax;
5490 // OptionCompareBinary = InitialOptionCompareBinary;
5492 // lexer = new Tokenizer (input, name, defines);
5494 // ifElseStateMachine = new IfElseStateMachine();
5495 // tokenizerController = new TokenizerController(lexer);
5497 // StringBuilder value = new StringBuilder ();
5499 // if (yacc_verbose_flag > 0)
5500 // yyparse (lexer, new yydebug.yyDebugSimple ());
5506 // catch(MBASException e) {
5507 // Report.Error(e.code, e.loc, e.Message);
5509 // catch (Exception e) {
5510 // if (Report.Stacktrace)
5511 // Console.WriteLine(e);
5512 // Report.Error (29999, lexer.Location, "Parsing error");
5515 // RootContext.VerifyImports();
5517 // return Report.Errors;
5523 // ifElseStateMachine.HandleToken(IfElseStateMachine.Token.EOF);
5525 // catch(ApplicationException) {
5526 // throw new MBASException(ifElseStateMachine.Error, lexer.Location, ifElseStateMachine.ErrString);
5529 // if(in_external_source)
5530 // Report.Error (30579, lexer.Location, "'#ExternalSource' directives must end with matching '#End ExternalSource'");
5532 // if(in_marked_region > 0)
5533 // Report.Error (30205, lexer.Location, "'#Region' directive must be followed by a matching '#End Region'");
5536 void HandleConditionalDirective(IfElseStateMachine.Token tok, BoolLiteral expr)
5539 tokenizerController.PositionTokenizerCursor(tok, expr);
5541 catch(ApplicationException) {
5542 tok = IfElseStateMachine.Token.EOF;
5544 ifElseStateMachine.HandleToken(tok);
5546 catch(ApplicationException) {
5547 throw new MBASException(ifElseStateMachine.Error, lexer.Location, ifElseStateMachine.ErrString);
5554 // Given the @class_name name, it creates a fully qualified name
5555 // based on the containing declaration space
5558 MakeName (MemberName class_name)
5560 string ns = current_namespace.FullName;
5562 if (current_container.Name == ""){
5564 return new MemberName (new MemberName (ns), class_name);
5568 return new MemberName (current_container.MemberName, class_name);