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)
8 // Manjula GHM (mmanjula@novell.com)
9 // Sudharsan V (vsudharsan@novell.com)
11 // Licensed under the terms of the GNU GPL
13 // Copyright (C) 2001, 2002, 2003, 2004 A Rafael D Teixeira
14 // Copyright (C) 2003, 2004 Novell
17 namespace Mono.MonoBASIC
21 using System.Reflection;
22 using System.Collections;
26 public class MBASException : ApplicationException
31 public MBASException(int code, Location loc, string text) : base(text)
39 /// The MonoBASIC Parser
42 public class Parser : GenericParser
48 /// Current block is used to add statements as we find
54 /// Tmp block is used to store block endings in if/select's
59 /// Tmp block is used to store tmp copies of expressions
64 /// Tmp catch is used to store catch clauses in try..catch..finally
66 ArrayList tmp_catch_clauses;
69 /// Current interface is used by the various declaration
70 /// productions in the interface declaration to "add"
71 /// the interfaces as we find them.
73 Interface current_interface;
76 /// This is used by the unary_expression code to resolve
77 /// a name against a parameter.
79 Parameters current_local_parameters;
82 /// This are used when parsing parameters in property
85 Parameters set_parameters;
86 Parameters get_parameters;
89 /// This is used by the sub_header parser to store modifiers
90 /// to be passed to sub/constructor
92 int current_modifiers;
95 /// This is used by the sub_header parser to store attributes
96 /// to be passed to sub/constructor
98 Attributes current_attributes;
101 /// Using during property parsing to describe the implicit
102 /// value parameter that is passed to the "set" accessor
105 string get_implicit_value_parameter_name;
108 // Using during property parsing to describe the implicit
109 // value parameter that is passed to the "set" and "get"accesor
110 // methods (properties and indexers).
112 Expression get_implicit_value_parameter_type;
115 /// Using during property parsing to describe the implicit
116 /// value parameter that is passed to the "set" accessor
119 string set_implicit_value_parameter_name;
122 // Using during property parsing to describe the implicit
123 // value parameter that is passed to the "set" and "get"accesor
124 // methods (properties and indexers).
126 Expression set_implicit_value_parameter_type;
128 // An out-of-band stack.
132 ArrayList current_rank_specifiers;
134 //To handle the End of a block
135 // We use grammer, priority, strings, and an integer called Parenta
137 // FIX ME: Need to implement some better method than this and in
138 // some cases parser will come out without proceeding further
139 // if it comes acorss error.
142 // 1) The value for corresponding blocks with which it will be accessed...
143 // In case of any more addition to end of blocks... add it at the end
145 public enum Start_block {
171 // In case of any more addition to end of blocks... add it at the end
173 public string[,] end_blocks = {
174 { "empty" , "empty" },
178 { "Sub" , "End Sub" },
179 { "Module" , "End Module" },
180 { "NameSpace" , "End NameSpace" },
181 { "Class" , "End Class" },
182 { "Function" , "End Function" },
183 { "Structure" , "End Structure" },
184 { "Enum" , "End Enum" },
185 { "Interface" , "End Interface" },
186 { "Property" , "End Property" },
187 { "With" , "End With" },
188 { "SyncLock" , "End SyncLock" },
189 { "Try" , "End Try" },
190 { "While" , "End While" },
191 { "Select" , "End Select" },
192 { "Set" , "End Set" },
193 { "Get" , "End Get" }
198 // 1) Error number for End of block missing
199 // 2) Extra End of Block
200 // 3) Priority for the end 0f blocks
201 // In case of any more addition to end of blocks... add it at the end
203 public int[,] error_end_blocks = {
204 { 29999 , 29999 , 0 },
205 { 30084 , 30092 , 1 },
206 { 30083 , 30091 , 1 },
207 { 30081 , 30087 , 1 },
208 { 30289 , 30429 , 3 },
209 { 30625 , 30622 , 5 },
210 { 30626 , 30623 , 6 },
211 { 30481 , 30460 , 4 },
212 { 30027 , 30430 , 3 },
213 { 30624 , 30621 , 4 },
214 { 30185 , 30184 , 1 },
215 { 30253 , 30252 , 3 },
216 { 30025 , 30431 , 3 },
217 { 30085 , 30093 , 1 },
218 { 30675 , 30674 , 1 },
219 { 30384 , 30383 , 1 },
220 { 30082 , 30090 , 1 },
221 { 30095 , 30088 , 1 },
222 { 30633 , 30632 , 2 },
223 { 30631 , 30630 , 2 }
228 Stack loc_end_of_block;
229 Stack loc_temp_block;
239 // Expression stack for nested ifs
243 Stack statement_stack;
245 // A stack for With expressions.
250 // Hash table for const preprocessing directive
252 public static Hashtable constPreDir = new Hashtable();
254 static public bool InitialOptionExplicit = false;
255 static public bool InitialOptionStrict = false;
256 static public bool InitialOptionCompareBinary = true;
257 static public ArrayList ImportsList = null;
261 bool OptionCompareBinary;
263 static public bool UseExtendedSyntax; // for ".mbs" files
265 bool implicit_modifiers;
267 public override string[] extensions()
269 string [] list = { ".vb", ".mbs" };
273 bool in_external_source = false;
274 int in_marked_region = 0;
276 TokenizerController tokenizerController;
277 IfElseStateMachine ifElseStateMachine;
280 public class IfElseStateMachine {
304 public static Hashtable errStrings = new Hashtable();
307 static int[,] errTable = new int[(int)State.MAX, (int)Token.MAX];
309 static IfElseStateMachine()
311 // FIXME: Fix both the error nos and the error strings.
312 // Currently the error numbers and the error strings are
313 // just placeholders for getting the state-machine going.
315 errStrings.Add(0, "");
316 errStrings.Add(30012, "#If must end with a matching #End If");
317 errStrings.Add(30013, "#ElseIf, #Else or #End If must be preceded by a matching #If");
318 errStrings.Add(30014, "#ElseIf must be preceded by a matching #If or #ElseIf");
319 errStrings.Add(30028, "#Else must be preceded by a matching #If or #ElseIf");
320 errStrings.Add(32030, "#ElseIf cannot follow #Else as part of #If block");
322 errTable[(int)State.START, (int)Token.IF] = 0;
323 errTable[(int)State.START, (int)Token.ELSEIF] = 30014;
324 errTable[(int)State.START, (int)Token.ELSE] = 30028;
325 errTable[(int)State.START, (int)Token.ENDIF] = 30013;
326 errTable[(int)State.START, (int)Token.EOF] = 0;
328 errTable[(int)State.IF_SEEN, (int)Token.IF] = 0;
329 errTable[(int)State.IF_SEEN, (int)Token.ELSEIF] = 0;
330 errTable[(int)State.IF_SEEN, (int)Token.ELSE] = 0;
331 errTable[(int)State.IF_SEEN, (int)Token.ENDIF] = 0;
332 errTable[(int)State.IF_SEEN, (int)Token.EOF] = 30012;
334 errTable[(int)State.ELSEIF_SEEN, (int)Token.IF] = 0;
335 errTable[(int)State.ELSEIF_SEEN, (int)Token.ELSEIF] = 0;
336 errTable[(int)State.ELSEIF_SEEN, (int)Token.ELSE] = 0;
337 errTable[(int)State.ELSEIF_SEEN, (int)Token.ENDIF] = 0;
338 errTable[(int)State.ELSEIF_SEEN, (int)Token.EOF] = 30012;
340 errTable[(int)State.ELSE_SEEN, (int)Token.IF] = 0;
341 errTable[(int)State.ELSE_SEEN, (int)Token.ELSEIF] = 32030;
342 errTable[(int)State.ELSE_SEEN, (int)Token.ELSE] = 32030;
343 errTable[(int)State.ELSE_SEEN, (int)Token.ENDIF] = 0;
344 errTable[(int)State.ELSE_SEEN, (int)Token.EOF] = 30012;
346 errTable[(int)State.ENDIF_SEEN, (int)Token.IF] = 0;
347 errTable[(int)State.ENDIF_SEEN, (int)Token.ELSEIF] = 30014;
348 errTable[(int)State.ENDIF_SEEN, (int)Token.ELSE] = 30028;
349 errTable[(int)State.ENDIF_SEEN, (int)Token.ENDIF] = 30013;
350 errTable[(int)State.ENDIF_SEEN, (int)Token.EOF] = 0;
353 public IfElseStateMachine()
357 stateStack = new Stack();
358 stateStack.Push(state);
361 // The parameter here need not be qualified with IfElseStateMachine
362 // But it hits a bug in mcs. So temporarily scoping it so that builds
365 public void HandleToken(IfElseStateMachine.Token tok)
367 err = (int) errTable[(int)state, (int)tok];
370 throw new ApplicationException("Unexpected pre-processor directive #"+tok);
372 if(tok == Token.IF) {
373 stateStack.Push(state);
376 else if(tok == Token.ENDIF) {
377 state = (State)stateStack.Pop();
389 public string ErrString {
391 return (string) errStrings[err];
397 public class TokenizerController {
401 public bool CanAcceptTokens;
402 public bool CanSelectBlock;
409 public TokenizerController(Tokenizer lexer)
412 stateStack = new Stack();
414 currentState.CanAcceptTokens = true;
415 currentState.CanSelectBlock = true;
417 stateStack.Push(currentState);
422 return (State)stateStack.Peek();
426 public bool IsAcceptingTokens {
428 return currentState.CanAcceptTokens;
432 public void PositionCursorAtNextPreProcessorDirective()
434 lexer.PositionCursorAtNextPreProcessorDirective();
437 public void PositionTokenizerCursor(IfElseStateMachine.Token tok, BoolLiteral expr)
439 if(tok == IfElseStateMachine.Token.ENDIF) {
440 currentState = (State)stateStack.Pop();
442 if(currentState.CanAcceptTokens)
445 PositionCursorAtNextPreProcessorDirective();
450 if(tok == IfElseStateMachine.Token.IF) {
451 stateStack.Push(currentState);
453 currentState.CanAcceptTokens = parentState.CanAcceptTokens;
454 currentState.CanSelectBlock = true;
457 if(parentState.CanAcceptTokens &&
458 currentState.CanSelectBlock && (bool)(expr.GetValue()) ) {
460 currentState.CanAcceptTokens = true;
461 currentState.CanSelectBlock = false;
465 currentState.CanAcceptTokens = false;
466 PositionCursorAtNextPreProcessorDirective();
472 bool allow_global_attribs = true;
474 bool expecting_global_attribs = false;
475 bool expecting_local_attribs = false;
477 bool local_attrib_section_added = false;
481 %token NONE /* This token is never returned by our lexer */
482 %token ERROR // This is used not by the parser, but by the tokenizer.
486 *These are the MonoBASIC keywords
579 %token NOTINHERITABLE
580 %token NOTOVERRIDABLE
636 %token YIELD // MonoBASIC extension
640 /* MonoBASIC single character operators/punctuation. */
642 %token OPEN_BRACKET "["
643 %token CLOSE_BRACKET "]"
644 %token OPEN_PARENS "("
645 %token OPEN_BRACE "{"
646 %token CLOSE_BRACE "}"
647 %token CLOSE_PARENS ")"
661 %token OP_IDIV "\\" //FIXME: This should be "\"
663 %token EXCLAMATION "!"
666 %token LONGTYPECHAR "&"
668 %token SINGLETYPECHAR "!"
669 %token NUMBER_SIGN "#"
670 %token DOLAR_SIGN "$"
672 %token ATTR_ASSIGN ":="
674 /* MonoBASIC multi-character operators. */
679 //%token OP_MODULUS //"mod"
681 /* VB.NET 2003 new bit-shift operators */
682 %token OP_SHIFT_LEFT "<<"
683 %token OP_SHIFT_RIGHT ">>"
686 %token LITERAL_INTEGER "int literal"
687 %token LITERAL_SINGLE "float literal"
688 %token LITERAL_DOUBLE "double literal"
689 %token LITERAL_DECIMAL "decimal literal"
690 %token LITERAL_CHARACTER "character literal"
691 %token LITERAL_STRING "string literal"
692 %token LITERAL_DATE "datetime literal"
696 /* Add precedence rules to solve dangling else s/r conflict */
705 %left OP_SHIFT_LEFT OP_SHIFT_RIGHT
707 %left STAR DIV PERCENT
708 %right BITWISE_NOT CARRET UMINUS
709 %nonassoc OP_INC OP_DEC
711 %left OPEN_BRACKET OPEN_BRACE
716 %start compilation_unit
720 : logical_end_of_line
727 | logical_end_of_line pp_directive
731 : logical_end_of_line _mark_
732 opt_option_directives
733 opt_imports_directives
739 | logical_end_of_line _mark_
740 opt_option_directives
741 opt_imports_directives
749 opt_option_directives
756 | option_directives option_directive
760 : option_explicit_directive
761 | option_strict_directive
762 | option_compare_directive
763 | OPTION _mark_ logical_end_of_line
765 Report.Error(30206 ,(Location)$2, "Option must be followed by 'Compare' or 'Explicit' or 'Strict'");
767 | OPTION _mark_ IDENTIFIER logical_end_of_line
769 Report.Error(30206 ,(Location)$2, "Option must be followed by 'Compare' or 'Explicit' or 'Strict'");
799 option_explicit_directive
800 : OPTION EXPLICIT _mark_ on_off logical_end_of_line
802 if (!UseExtendedSyntax)
803 OptionExplicit = (bool)$4;
807 "In MonoBASIC extended syntax explicit declaration is always required. So OPTION EXPLICIT is deprecated");
812 option_strict_directive
813 : OPTION STRICT _mark_ on_off logical_end_of_line
815 if (!UseExtendedSyntax)
816 OptionStrict = (bool)$4;
820 "In MonoBASIC extended syntax strict assignability is always required. So OPTION STRICT is deprecated");
824 option_compare_directive
825 : OPTION COMPARE text_or_binary logical_end_of_line
827 OptionCompareBinary = (bool)$3;
838 | declarations declaration
842 : declaration_qualifiers
844 // FIXME: Need to check declaration qualifiers for multi-file compilation
845 // FIXME: Qualifiers cannot be applied to namespaces
846 allow_global_attribs = false;
848 namespace_declaration
849 |declaration_qualifiers _mark_
851 // FIXME: Need to check declaration qualifiers for multi-file compilation
852 allow_global_attribs = false;
854 type_spec_declaration
859 if ($4 is Class || $4 is Struct || $4 is Module ){
860 TypeContainer c = (TypeContainer) $4;
861 mod_flags = c.ModFlags;
866 if ((mod_flags & (Modifiers.PRIVATE)) != 0){
869 "Namespace elements cannot be explicitly " +
870 "declared private in '" + name + "'");
872 else if ((mod_flags & (Modifiers.PROTECTED)) != 0){
875 "Namespace elements cannot be explicitly " +
876 "declared protected in '" + name + "'");
891 : PERCENT { $$ = TypeManager.system_int32_expr; }
892 | LONGTYPECHAR { $$ = TypeManager.system_int64_expr; }
893 | AT_SIGN { $$ = TypeManager.system_decimal_expr; }
894 | SINGLETYPECHAR { $$ = TypeManager.system_single_expr; }
895 | NUMBER_SIGN { $$ = TypeManager.system_double_expr; }
896 | DOLAR_SIGN { $$ = TypeManager.system_string_expr; }
900 : /* empty */ { $$ = null; }
901 | type_character { $$ = $1; }
907 | qualified_identifier DOT identifier // FIXME: It should be qualified_identifier DOT identifier-or-keyword
909 $$ = (($1).ToString ()) + "." + ($3.ToString ());
913 opt_imports_directives
920 | imports_directives imports_directive
924 : IMPORTS imports_terms logical_end_of_line
929 | imports_terms COMMA imports_term
933 : namespace_or_type_name
935 RootContext.SourceBeingCompiled.Imports ((string) $1, lexer.Location);
937 | identifier _mark_ ASSIGN namespace_or_type_name
939 RootContext.SourceBeingCompiled.ImportsWithAlias ((string) $1, (string) $4, (Location)$2);
941 | identifier _mark_ ASSIGN
943 Report.Error(30203, (Location)$2, "Alias Statement no complete: Expression Expected");
947 Report.Error(30203, (Location)$1, "No namespace imported: Expression Expected");
952 : /* empty */ { $$ = Parameters.EmptyReadOnlyParameters; }
953 | OPEN_PARENS CLOSE_PARENS { $$ = Parameters.EmptyReadOnlyParameters; }
954 | OPEN_PARENS _mark_ opt_formal_parameter_list CLOSE_PARENS { $$ = $3; }
957 Report.Error(30203,(Location)$2, "Identifier Expected");
958 $$ = Parameters.EmptyReadOnlyParameters;
960 | OPEN_PARENS _mark_ opt_formal_parameter_list error
962 Report.Error(30198,(Location)$2, "'(' is not having a matching ')'");
965 | error _mark_ opt_formal_parameter_list CLOSE_PARENS
967 Report.Error(30205,(Location)$2, "')' is not having a matching '('");
977 local_attrib_section_added = false;
986 expecting_local_attribs = false;
987 expecting_global_attribs = false;
991 if (expecting_local_attribs) {
992 local_attrib_section_added = true;
993 allow_global_attribs = false;
995 $$ = new Attributes ((ArrayList) $1);
998 if (expecting_global_attribs) {
1000 CodeGen.AddGlobalAttributes ((ArrayList) $1);
1003 expecting_local_attribs = false;
1004 expecting_global_attribs = false;
1006 | attribute_sections
1008 $$ = lexer.Location;
1014 ArrayList attrs = (ArrayList) $3;
1016 if (expecting_local_attribs) {
1017 if (local_attrib_section_added) {
1018 expecting_local_attribs = false;
1019 expecting_global_attribs = false;
1020 Report.Error (30205, (Location) $2, "Multiple attribute sections may not be used; Coalesce multiple attribute sections in to a single attribute section");
1025 $$ = new Attributes (attrs);
1027 ((Attributes) $1).Add (attrs);
1029 local_attrib_section_added = true;
1030 allow_global_attribs = false;
1033 if (expecting_global_attribs) {
1035 CodeGen.AddGlobalAttributes ((ArrayList) $3);
1039 expecting_local_attribs = false;
1040 expecting_global_attribs = false;
1045 : OP_LT _mark_ attribute_list OP_GT opt_end_of_stmt
1049 if (expecting_global_attribs && !(bool) $5) {
1050 Report.Error (30205, (Location)$2, "End of statement expected");
1054 if (expecting_local_attribs) {
1056 Report.Error (32035, (Location)$2, "Use a line continuation after the attribute specifier to apply it to the following statement.");
1067 : /* empty */ { $$ = false; }
1068 | end_of_stmt { $$ = true; }
1074 ArrayList attrs = null;
1076 attrs = new ArrayList ();
1081 | attribute_list COMMA attribute
1083 ArrayList attrs = null;
1086 attrs = ($1 == null) ? new ArrayList () : (ArrayList) $1;
1095 : namespace_or_type_name
1097 $$ = lexer.Location;
1099 opt_attribute_arguments
1103 if (expecting_global_attribs)
1104 Report.Error (32015, (Location) $2, "Expecting Assembly or Module attribute specifiers");
1106 expecting_local_attribs = true;
1107 $$ = new Attribute ((string) $1, (ArrayList) $3, (Location) $2);
1110 | attribute_target_specifier
1112 $$ = lexer.Location;
1115 namespace_or_type_name
1117 $$ = lexer.Location;
1119 opt_attribute_arguments
1123 string attribute_target = (string) $1;
1124 if (attribute_target != "assembly" && attribute_target != "module") {
1125 Report.Error (29999, lexer.Location, "`" + (string)$1 + "' is an invalid attribute modifier");
1128 if (!allow_global_attribs) {
1129 Report.Error (30637, (Location) $2, "Global attribute statements must precede any declarations in a file");
1133 if (expecting_local_attribs) {
1134 Report.Error (30183, (Location) $2, "Global attributes cannot be combined with local attributes");
1138 expecting_global_attribs = true;
1139 $$ = new Attribute (attribute_target, (string) $4, (ArrayList) $6, (Location) $5);
1143 attribute_target_specifier
1144 : ASSEMBLY { $$ = "assembly"; }
1145 | MODULE { $$ = "module"; }
1146 | namespace_or_type_name
1150 opt_attribute_arguments
1151 : /* empty */ { $$ = null; }
1152 | OPEN_PARENS opt_attribute_arguments_list CLOSE_PARENS
1158 opt_attribute_arguments_list
1160 | attribute_arguments_list
1163 attribute_arguments_list
1164 : positional_argument_list
1166 ArrayList args = new ArrayList ();
1171 | positional_argument_list COMMA named_argument_list
1173 ArrayList args = new ArrayList ();
1179 | named_argument_list
1181 ArrayList args = new ArrayList ();
1189 positional_argument_list
1190 : constant_expression
1192 ArrayList args = new ArrayList ();
1193 args.Add (new Argument ((Expression) $1, Argument.AType.Expression));
1197 | positional_argument_list COMMA constant_expression
1199 ArrayList args = (ArrayList) $1;
1200 args.Add (new Argument ((Expression) $3, Argument.AType.Expression));
1209 ArrayList args = new ArrayList ();
1214 | named_argument_list COMMA named_argument
1216 ArrayList args = (ArrayList) $1;
1224 : identifier ATTR_ASSIGN constant_expression //FIXME: It should be identifier_or_keyword ATTR_ASSIGN constant_expression
1226 $$ = new DictionaryEntry (
1228 new Argument ((Expression) $3, Argument.AType.Expression));
1232 namespace_declaration
1233 : NAMESPACE _mark_ qualified_identifier logical_end_of_line
1235 push_into_stack((int)Start_block.NAMESPACE, (Location)$2);
1236 current_namespace = RootContext.Tree.RecordNamespace(current_namespace, name, (string)$3);
1242 pop_out_of_stack((int)$7, lexer.Location);
1246 current_namespace = current_namespace.Parent;
1250 declaration_qualifiers
1254 current_attributes = (Attributes) $1;
1255 current_modifiers = (int) $2;
1259 type_spec_declaration
1261 | module_declaration
1262 | interface_declaration
1263 | delegate_declaration
1264 | struct_declaration
1269 : CLASS identifier _mark_ end_of_stmt opt_inherits opt_implements
1271 // Module members are static by default, but Class *can't* be declared static
1272 // so we must fix it, if mbas was the one actually responsible for this
1273 // instead of triggering an error.
1274 push_into_stack((int)Start_block.CLASS, (Location)$3);
1276 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
1277 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
1282 name = MakeName ((string) $2);
1283 new_class = new Class (current_container, name, current_modifiers,
1284 (Attributes) current_attributes, (Location)$3);
1286 current_container = new_class;
1287 current_container.Namespace = current_namespace;
1288 RootContext.Tree.RecordDecl (name, new_class);
1290 opt_class_member_declarations
1293 pop_out_of_stack((int)$9, lexer.Location);
1297 Class new_class = (Class) current_container;
1299 ArrayList bases = (ArrayList) $5;
1301 ArrayList ifaces = (ArrayList) $6;
1302 if (ifaces != null){
1304 bases.AddRange(ifaces);
1308 new_class.Bases = bases;
1310 current_container = current_container.Parent;
1311 CheckDef (current_container.AddClass (new_class), new_class.Name, new_class.Location);
1318 : /* empty */ { $$ = null; }
1319 | INHERITS type_list end_of_stmt { $$ = $2; }
1323 : /* empty */ { $$ = null; }
1324 | IMPLEMENTS type_list end_of_stmt { $$ = $2; }
1328 : /* empty */ { $$ = (int) 0; current_modifiers = 0; }
1329 | modifiers { $$ = $1; current_modifiers = (int) $1; }
1334 | modifiers modifier
1339 if ((m1 & m2) != 0) {
1340 Location l = lexer.Location;
1341 Report.Error (1004, l, "Duplicate modifier: `" + Modifiers.Name (m2) + "'");
1343 $$ = (int) (m1 | m2);
1348 : PUBLIC { $$ = Modifiers.PUBLIC; }
1349 | PROTECTED { $$ = Modifiers.PROTECTED; }
1350 | PRIVATE { $$ = Modifiers.PRIVATE; }
1351 | SHARED { $$ = Modifiers.STATIC; }
1352 | FRIEND { $$ = Modifiers.INTERNAL; }
1353 | NOTINHERITABLE { $$ = Modifiers.SEALED; }
1354 | OVERRIDABLE { $$ = Modifiers.VIRTUAL; }
1355 | NOTOVERRIDABLE { $$ = Modifiers.NONVIRTUAL; }
1356 | OVERRIDES { $$ = Modifiers.OVERRIDE; }
1357 | OVERLOADS { $$ = Modifiers.NEW; }
1358 | SHADOWS { $$ = Modifiers.SHADOWS; }
1359 | MUSTINHERIT { $$ = Modifiers.ABSTRACT; }
1360 | READONLY { $$ = Modifiers.READONLY; }
1361 | DEFAULT { $$ = Modifiers.DEFAULT; }
1362 | WRITEONLY { $$ = Modifiers.WRITEONLY; }
1366 : MODULE _mark_ identifier logical_end_of_line
1368 push_into_stack((int)Start_block.MODULE, (Location)$2);
1371 name = MakeName((string) $3);
1372 new_module = new Module(current_container,
1374 current_modifiers, // already checks then
1375 (Attributes) current_attributes,
1377 current_container = new_module;
1378 current_container.Namespace = current_namespace;
1379 RootContext.Tree.RecordDecl(name, new_module);
1381 opt_module_member_declarations
1384 pop_out_of_stack((int)$7, lexer.Location);
1388 Module new_module = (Module)current_container;
1390 current_container = current_container.Parent;
1391 CheckDef (current_container.AddClass(new_module), new_module.Name, new_module.Location);
1393 TypeManager.AddStandardModule(new_module);
1399 opt_module_member_declarations
1401 | module_member_declarations
1404 module_member_declarations
1405 : module_member_declaration
1406 | module_member_declarations module_member_declaration
1409 module_member_declaration
1413 current_attributes = (Attributes) $1;
1414 current_modifiers = ((int)$2) | Modifiers.STATIC;
1415 bool explicit_static = (((int) $2 & Modifiers.STATIC) > 0);
1416 implicit_modifiers = (!explicit_static);
1418 module_member_declarator
1420 implicit_modifiers = false;
1425 module_member_declarator
1426 : constructor_declaration
1427 | method_declaration
1429 Method method = (Method) $1;
1430 CheckDef (current_container.AddMethod (method), method.Name, method.Location);
1433 | withevents_declaration /* This is a field but must be treated specially, see below */
1434 | constant_declaration
1435 | property_declaration
1437 | type_spec_declaration
1440 constant_declaration
1441 : CONST constant_declarators end_of_stmt
1443 // Module members are static by default, but constants *can't* be declared static
1444 // so we must fix it, if mbas was the one actually responsible for this
1445 // instead of triggering an error.
1446 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
1447 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
1449 int mod = (int) current_modifiers;
1451 // Structure members are Public by default
1452 if ((current_container is Struct) && (mod == 0))
1453 mod = Modifiers.PUBLIC;
1455 ArrayList consts = (ArrayList) $2;
1456 if(consts.Count > 0)
1458 VariableDeclaration.FixupTypes ((ArrayList) $2);
1459 VariableDeclaration.FixupArrayTypes ((ArrayList) $2);
1461 foreach (VariableDeclaration var in (ArrayList) $2){
1462 Location l = var.Location;
1463 Const vconstant = new Const ((Expression)var.type, (String)var.identifier,
1464 (Expression)var.expression_or_array_initializer,
1465 mod, (Attributes) null, l);
1467 CheckDef (current_container.AddConstant (vconstant), vconstant.Name, l);
1473 opt_class_member_declarations
1475 | class_member_declarations
1478 class_member_declarations
1479 : class_member_declaration
1480 | class_member_declarations class_member_declaration
1483 class_member_declaration
1487 current_attributes = (Attributes) $1;
1488 current_modifiers = (int) $2;
1490 class_member_declarator
1496 class_member_declarator
1497 : constructor_declaration
1498 | method_declaration
1500 Method method = (Method) $1;
1501 CheckDef (current_container.AddMethod (method), method.Name, method.Location);
1504 | constant_declaration
1505 | property_declaration
1507 | withevents_declaration /* This is a field but must be treated specially, see below */
1508 | type_spec_declaration
1515 | must_override_declaration
1518 must_override_declaration
1519 : must_override_sub_declaration
1520 | must_override_func_declaration
1523 must_override_sub_declaration
1524 : MUSTOVERRIDE SUB identifier opt_params opt_implement_clause _mark_ logical_end_of_line
1526 if (current_container is Module)
1527 Report.Error (30433, (Location)$6, "Methods in a Module cannot be declared 'MustOverride'.");
1529 if (current_container is Struct)
1530 Report.Error (435, (Location)$6, "Methods in a Structure cannot be declared 'MustOverride'.");
1532 current_modifiers |= Modifiers.ABSTRACT;
1534 Method method = new Method (TypeManager.system_void_expr, (int) current_modifiers, (string) $3,
1535 (Parameters) $4, null, (ArrayList) $5, (Location)$6);
1537 if (!(current_container is Class))
1538 Report.Error (9999, (Location)$6, "THIS SHOULD NEVER HAPPEN!");
1545 must_override_func_declaration
1546 : MUSTOVERRIDE FUNCTION identifier opt_type_character opt_params _mark_ opt_type_with_ranks opt_implement_clause logical_end_of_line
1548 Expression ftype = ($7 == null) ? (($4 == null) ? TypeManager.
1549 system_object_expr : (Expression) $4 ) : (Expression) $7;
1551 if (current_container is Module)
1552 Report.Error (30433, (Location)$6,"Methods in a Module cannot be declared 'MustOverride'.");
1554 if (current_container is Struct)
1555 Report.Error (435, (Location)$6,"Methods in a Structure cannot be declared 'MustOverride'.");
1557 current_modifiers |= Modifiers.ABSTRACT;
1559 Method method = new Method ((Expression) ftype, (int) current_modifiers,
1560 (string) $3,(Parameters) $5, null, (ArrayList) $8,
1563 if (!(current_container is Class))
1564 Report.Error (9999, (Location)$6,"THIS SHOULD NEVER HAPPEN!");
1571 : SUB identifier _mark_ opt_params opt_evt_handler opt_implement_clause logical_end_of_line
1573 push_into_stack((int)Start_block.SUB, (Location)$3);
1574 current_local_parameters = (Parameters) $4;
1577 // Structure members are Public by default
1578 if ((current_container is Struct) && (current_modifiers == 0))
1579 current_modifiers = Modifiers.PUBLIC;
1585 pop_out_of_stack((int)$10, lexer.Location);
1589 Method method = new Method (TypeManager.system_void_expr, (int) current_modifiers, (string) $2,
1590 (Parameters) current_local_parameters, (Attributes) current_attributes,
1591 (ArrayList) $6, (Location)$3);
1593 method.Block = (Block) end_block();
1597 // we have an event handler to take care of
1599 Expression handles_exp = (Expression) $5;
1600 Location loc = (Location)$3;
1602 if (handles_exp is MemberAccess) {
1603 string evt_def = ((MemberAccess)$5).ToString();
1604 int pos = evt_def.LastIndexOf (".");
1605 string evt_target = evt_def.Substring (0, pos);
1608 if (current_container.Properties != null) {
1609 foreach (Property p in current_container.Properties) {
1610 if (p.Name == evt_target) {
1613 Statement addhnd = (Statement) new AddHandler ((Expression) $5,
1614 DecomposeQI((string) $2, loc),
1617 current_container.AddEventHandler (addhnd);
1625 Report.Error(30506, (Location)$3,
1626 evt_target + " is not declared with WithEvents");
1628 } else if (handles_exp is BaseAccess) {
1629 Statement addhnd = (Statement) new AddHandler ((Expression) $5,
1630 DecomposeQI((string) $2, loc),
1633 current_container.AddEventHandler (addhnd);
1641 : FUNCTION identifier opt_type_character
1642 opt_params _mark_ opt_type_with_ranks opt_implement_clause logical_end_of_line
1644 push_into_stack((int)Start_block.FUNCTION, (Location)$5);
1645 current_local_parameters = (Parameters) $4;
1648 Expression ftype = ($6 == null) ? (($3 == null) ? TypeManager.system_object_expr : (Expression) $3 ) : (Expression) $6;
1650 // Structure members are Public by default
1651 if ((current_container is Struct) && (current_modifiers == 0))
1652 current_modifiers = Modifiers.PUBLIC;
1653 // Add local var declaration
1655 ArrayList retval = new ArrayList ();
1656 retval.Add (new VariableDeclaration ((string) $2, (Expression) ftype, (Location)$5));
1657 declare_local_variables ((Expression) ftype, retval, (Location)$5);
1662 pop_out_of_stack((int)$11, lexer.Location);
1666 Expression ftype = ($6 == null) ? (($3 == null) ? TypeManager.system_object_expr : (Expression) $3 ) : (Expression) $6;
1668 Method method = new Method ((Expression) ftype, (int) current_modifiers, (string) $2,
1669 (Parameters) current_local_parameters, (Attributes) current_attributes,/* (Attributes) currx ent_attributes, */
1670 (ArrayList) $7, (Location)$5);
1671 method.Block = end_block();
1677 : STRUCTURE _mark_ identifier end_of_stmt
1678 opt_implement_clause
1680 push_into_stack((int)Start_block.STRUCTURE, (Location)$2);
1682 string full_struct_name = MakeName ((string) $3);
1684 // Module members are static by default, but structures *can't* be declared static
1685 // so we must fix it, if mbas was the one actually responsible for this
1686 // instead of triggering an error.
1687 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
1688 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
1690 new_struct = new Struct (current_container, full_struct_name,
1691 (int) current_modifiers,
1692 (Attributes) current_attributes, (Location)$2);
1693 current_container = new_struct;
1694 current_container.Namespace = current_namespace;
1695 RootContext.Tree.RecordDecl (full_struct_name, new_struct);
1697 opt_struct_member_declarations
1699 Struct new_struct = (Struct) current_container;
1702 new_struct.Bases = (ArrayList) $5;
1704 current_container = current_container.Parent;
1705 CheckDef (current_container.AddStruct (new_struct), new_struct.Name, new_struct.Location);
1710 pop_out_of_stack((int)$9, lexer.Location);
1715 opt_struct_member_declarations
1717 | struct_member_declarations
1720 struct_member_declarations
1721 : struct_member_declaration
1722 | struct_member_declarations struct_member_declaration
1725 struct_member_declaration
1727 struct_member_declarator
1730 struct_member_declarator
1732 | constant_declaration
1733 | constructor_declaration
1734 | method_declaration
1736 Method method = (Method) $1;
1737 CheckDef (current_container.AddMethod (method), method.Name, method.Location);
1739 | property_declaration
1741 | type_spec_declaration
1744 * This is only included so we can flag error 575:
1745 * destructors only allowed on class types
1747 //| destructor_declaration
1751 : EVENT identifier _mark_ AS type opt_implement_clause logical_end_of_line
1753 VariableDeclaration var = new VariableDeclaration ((string) $2, (Expression) $5, (Location)$3);
1755 Event e = new Event ((Expression) $5, var.identifier,
1756 null, current_modifiers,
1757 current_attributes, (ArrayList) $6,
1760 CheckDef (current_container.AddEvent (e), e.Name, e.Location);
1762 | EVENT identifier _mark_ opt_params opt_implement_clause logical_end_of_line
1764 string delName = null;
1767 delName = (string) $2;
1768 delName = delName + "EventHandler";
1769 Mono.MonoBASIC.Delegate del = new Mono.MonoBASIC.Delegate
1770 (current_container, TypeManager.system_void_expr,
1771 (int) current_modifiers, MakeName(delName), (Parameters) $4,
1772 (Attributes) current_attributes, (Location)$3);
1774 del.Namespace = current_namespace;
1775 CheckDef (current_container.AddDelegate (del), del.Name, (Location)$3);
1777 ArrayList impls = (ArrayList) $5;
1778 if (impls.Count > 1) {
1779 string expstr = "Event '" + ((Expression) impls[1]).ToString () +
1780 "' can not be implemented with Event '" +
1781 (string) $2 + "', since it's delegate type does not match " +
1782 "with the delegate type of '" + ((Expression) impls[0]).ToString () + "'";
1783 Report.Error (31407, (Location)$3, expstr);
1785 Expression impl = (Expression) impls[0];
1786 delName = impl.ToString();
1787 delName = delName.Substring (delName.LastIndexOf(".") + 1);
1788 delName = delName + "EventHandler";
1791 Event e = new Event (DecomposeQI (delName, (Location)$3),
1793 null, current_modifiers,
1794 current_attributes, (ArrayList) $5,
1797 CheckDef (current_container.AddEvent (e), e.Name, e.Location);
1802 : ENUM _mark_ identifier opt_type_spec logical_end_of_line
1803 opt_enum_member_declarations
1805 push_into_stack((int)Start_block.ENUM, (Location)$2);
1806 Location enum_location = (Location)$2;
1807 string full_name = MakeName ((string) $3);
1808 Expression enum_type = ($4 == null) ? TypeManager.system_int32_expr : (Expression) $4;
1809 ArrayList enum_members = (ArrayList) $6;
1811 if (enum_members.Count == 0)
1812 Report.Error (30280, enum_location,
1813 "Enum can not have empty member list");
1815 // Module members are static by default, but enums *can't* be declared static
1816 // so we must fix it if mbas was the one actually responsible for this
1817 // instead of triggering an error.
1818 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
1819 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
1821 Mono.MonoBASIC.Enum e = new Mono.MonoBASIC.Enum (current_container, enum_type,
1822 (int) current_modifiers, full_name,
1823 (Attributes) current_attributes, enum_location);
1825 foreach (VariableDeclaration ev in enum_members) {
1826 Location loc = (Location) ev.Location;
1828 CheckDef (e.AddEnumMember (ev.identifier,
1829 (Expression) ev.expression_or_array_initializer,
1830 loc, ev.OptAttributes), ev.identifier, loc);
1833 e.Namespace = current_namespace;
1835 CheckDef (current_container.AddEnum (e), full_name, enum_location);
1836 RootContext.Tree.RecordDecl (full_name, e);
1841 pop_out_of_stack((int)$8,lexer.Location);
1846 opt_enum_member_declarations
1847 : /* empty */ { $$ = new ArrayList (); }
1848 | enum_member_declarations { $$ = $1; }
1851 enum_member_declarations
1852 : enum_member_declaration
1854 ArrayList l = new ArrayList ();
1859 | enum_member_declarations enum_member_declaration
1861 ArrayList l = (ArrayList) $1;
1869 enum_member_declaration
1870 : opt_attributes identifier _mark_ logical_end_of_line
1872 $$ = new VariableDeclaration ((string) $2, null, (Location)$3, (Attributes) $1);
1874 | opt_attributes identifier
1876 $$ = lexer.Location;
1878 ASSIGN expression logical_end_of_line
1880 $$ = new VariableDeclaration ((string) $2, (Expression)$5, (Location)$3, (Attributes) $1);
1884 interface_declaration
1885 : INTERFACE _mark_ identifier logical_end_of_line
1887 push_into_stack((int)Start_block.INTERFACE, (Location)$2);
1888 Interface new_interface;
1889 string full_interface_name = MakeName ((string) $3);
1891 new_interface = new Interface (current_container, full_interface_name, (int) current_modifiers,
1892 (Attributes) current_attributes, (Location)$2);
1893 if (current_interface != null) {
1894 Report.Error (-2, (Location)$2, "Internal compiler error: interface inside interface");
1896 current_interface = new_interface;
1897 new_interface.Namespace = current_namespace;
1898 RootContext.Tree.RecordDecl (full_interface_name, new_interface);
1903 Interface new_interface = (Interface) current_interface;
1906 new_interface.Bases = (ArrayList) $6;
1908 current_interface = null;
1909 CheckDef (current_container.AddInterface (new_interface),
1910 new_interface.Name, new_interface.Location);
1915 pop_out_of_stack((int)$9, lexer.Location);
1921 : /* empty */ { $$ = null; }
1927 | interface_bases interface_base
1929 ArrayList bases = (ArrayList) $1;
1930 bases.AddRange ((ArrayList) $2);
1936 : INHERITS type_list logical_end_of_line { $$ = $2; }
1940 : opt_interface_member_declarations
1943 opt_interface_member_declarations
1945 | interface_member_declarations
1948 interface_member_declarations
1949 : interface_member_declaration
1950 | interface_member_declarations interface_member_declaration
1953 interface_member_declaration
1957 current_attributes = (Attributes) $1;
1958 current_modifiers = ((int)$2) | Modifiers.ABSTRACT;
1960 interface_member_declarator
1966 interface_member_declarator
1967 : interface_method_declaration
1969 Method m = (Method) $1;
1970 CheckDef (current_interface.AddMethod (m), m.Name, m.Location);
1972 | interface_property_declaration
1973 | interface_event_declaration
1976 interface_method_declaration
1977 : SUB identifier opt_params _mark_ logical_end_of_line
1979 Method method = new Method (TypeManager.system_void_expr, (int) current_modifiers, (string) $2,
1980 (Parameters) $3, current_attributes, null, (Location)$4);
1984 | FUNCTION identifier opt_type_character opt_params _mark_ opt_type_with_ranks logical_end_of_line
1986 Expression ftype = ($6 == null) ? (($3 == null) ? TypeManager.
1987 system_object_expr : (Expression) $3 ) : (Expression) $6;
1989 Method method = new Method ((Expression) ftype, (int) current_modifiers,
1990 (string) $2,(Parameters) $4, current_attributes, null,
1997 interface_property_declaration
1998 : PROPERTY identifier _mark_ opt_type_character opt_property_parameters opt_type_with_ranks logical_end_of_line
2000 Expression ftype = ($6 == null) ? (($4 == null) ?
2001 TypeManager.system_object_expr : (Expression) $4 ) : (Expression) $6;
2003 current_local_parameters = (Parameters) $5;
2004 if (current_local_parameters != Parameters.EmptyReadOnlyParameters) {
2005 get_parameters = current_local_parameters.Copy ((Location)$3);
2006 set_parameters = current_local_parameters.Copy ((Location)$3);
2008 Parameter implicit_value_parameter = new Parameter (
2009 ftype, "Value", Parameter.Modifier.NONE, null);
2011 set_parameters.AppendParameter (implicit_value_parameter);
2015 get_parameters = Parameters.EmptyReadOnlyParameters;
2016 set_parameters = new Parameters (null, null ,(Location)$3);
2018 Parameter implicit_value_parameter = new Parameter (
2019 ftype, "Value", Parameter.Modifier.NONE, null);
2021 set_parameters.AppendParameter (implicit_value_parameter);
2023 lexer.PropertyParsing = true;
2025 Accessor get_block = new Accessor (null, null);
2026 Accessor set_block = new Accessor (null, null);
2028 Property prop = new Property ((Expression) ftype, (string) $2, current_modifiers,
2029 get_block, set_block, current_attributes, (Location)$3,
2030 null, get_parameters, set_parameters, null);
2032 CheckDef (current_interface.AddProperty (prop), prop.Name, (Location)$3);
2034 get_implicit_value_parameter_type = null;
2035 set_implicit_value_parameter_type = null;
2036 get_parameters = null;
2037 set_parameters = null;
2038 current_local_parameters = null;
2042 interface_event_declaration
2043 : EVENT identifier AS _mark_ type logical_end_of_line
2045 VariableDeclaration var = new VariableDeclaration ((string) $2, (Expression) $5, (Location)$4);
2047 Event e = new Event ((Expression) $5, var.identifier,
2048 null, current_modifiers,
2049 current_attributes, (Location)$4);
2051 CheckDef (current_interface.AddEvent (e), e.Name, e.Location);
2054 | EVENT identifier opt_params _mark_ logical_end_of_line
2056 string delName = (string) $2;
2057 delName = delName + "EventHandler";
2058 int delModifiers = (current_modifiers & ~Modifiers.ABSTRACT);
2059 Mono.MonoBASIC.Delegate del = new Mono.MonoBASIC.Delegate
2060 (current_container, TypeManager.system_void_expr,
2061 (int) delModifiers, MakeName(delName), (Parameters) $3,
2062 (Attributes) current_attributes, (Location)$4);
2064 del.Namespace = current_namespace;
2065 CheckDef (current_interface.AddDelegate (del), del.Name, (Location)$4);
2067 Event e = new Event (DecomposeQI (delName, (Location)$4),
2069 null, current_modifiers,
2070 current_attributes, (Location)$4);
2072 CheckDef (current_interface.AddEvent (e), e.Name, e.Location);
2076 property_declaration
2077 : abstract_propery_declaration
2078 | non_abstract_propery_declaration
2081 abstract_propery_declaration
2082 : MUSTOVERRIDE PROPERTY identifier opt_type_character opt_property_parameters _mark_ opt_type_with_ranks logical_end_of_line
2084 Expression ftype = ($7 == null) ? (($4 == null) ?
2085 TypeManager.system_object_expr : (Expression) $4 ) : (Expression) $7;
2087 if (current_container is Module)
2088 Report.Error (30503, (Location) $6 , "Properties in a Module cannot be declared 'MustOverride'.");
2090 if (current_container is Struct)
2091 Report.Error (435, (Location) $6 ,"Methods in a Structure cannot be declared 'MustOverride'.");
2093 current_modifiers |= Modifiers.ABSTRACT;
2095 current_local_parameters = (Parameters) $5;
2096 if (current_local_parameters != Parameters.EmptyReadOnlyParameters) {
2097 get_parameters = current_local_parameters.Copy (lexer.Location);
2098 set_parameters = current_local_parameters.Copy (lexer.Location);
2100 Parameter implicit_value_parameter = new Parameter (
2101 ftype, "Value", Parameter.Modifier.NONE, null);
2103 set_parameters.AppendParameter (implicit_value_parameter);
2107 get_parameters = Parameters.EmptyReadOnlyParameters;
2108 set_parameters = new Parameters (null, null ,lexer.Location);
2110 Parameter implicit_value_parameter = new Parameter (
2111 ftype, "Value", Parameter.Modifier.NONE, null);
2113 set_parameters.AppendParameter (implicit_value_parameter);
2115 lexer.PropertyParsing = true;
2117 Accessor get_block = new Accessor (null, null);
2118 Accessor set_block = new Accessor (null, null);
2120 Property prop = new Property ((Expression) ftype, (string) $3, current_modifiers,
2121 get_block, set_block, current_attributes, lexer.Location,
2122 null, get_parameters, set_parameters, null);
2124 if (!(current_container is Class))
2125 Report.Error (9999, (Location) $6, "THIS SHOULD NEVER HAPPEN!");
2127 CheckDef (current_container.AddProperty (prop), prop.Name, lexer.Location);
2129 get_implicit_value_parameter_type = null;
2130 set_implicit_value_parameter_type = null;
2131 get_parameters = null;
2132 set_parameters = null;
2133 current_local_parameters = null;
2138 non_abstract_propery_declaration
2139 : PROPERTY identifier
2141 opt_property_parameters
2144 opt_implement_clause
2146 push_into_stack((int)Start_block.PROPERTY, (Location)$5);
2147 if ((current_modifiers & Modifiers.DEFAULT) > 0) {
2148 if (current_container.DefaultPropName != null
2149 && current_container.DefaultPropName != (string) $2)
2150 Report.Error (30359,
2152 "Type '" + current_container.Name +
2153 "' cannot have more than one 'Default Property' ");
2155 current_container.DefaultPropName = (string) $2;
2158 get_implicit_value_parameter_type =
2159 ($6 == null) ? (($3 == null) ?
2160 TypeManager.system_object_expr : (Expression) $3 ) : (Expression) $6;
2161 get_implicit_value_parameter_name = (string) $2;
2163 current_local_parameters = (Parameters) $4;
2164 if (current_local_parameters != Parameters.EmptyReadOnlyParameters) {
2165 get_parameters = current_local_parameters.Copy ((Location)$5);
2166 set_parameters = current_local_parameters.Copy ((Location)$5);
2170 get_parameters = Parameters.EmptyReadOnlyParameters;
2171 set_parameters = new Parameters (null, null ,(Location)$5);
2173 lexer.PropertyParsing = true;
2178 accessor_declarations
2181 pop_out_of_stack((int)$11,lexer.Location);
2185 lexer.PropertyParsing = false;
2188 Pair pair = (Pair) $10;
2190 Accessor get_block = null;
2191 Accessor set_block = null;
2193 if (pair.First != null){
2194 get_block = (Accessor) pair.First;
2197 if (pair.Second != null) {
2198 set_block = (Accessor) pair.Second;
2201 Location loc = (Location) $5 ;
2203 // Structure members are Public by default
2204 if ((current_container is Struct) && (current_modifiers == 0))
2205 current_modifiers = Modifiers.PUBLIC;
2207 prop = new Property ((Expression) get_implicit_value_parameter_type,
2208 (string) $2, current_modifiers, get_block, set_block,
2209 current_attributes, loc, set_implicit_value_parameter_name,
2210 get_parameters, set_parameters, (ArrayList) $7);
2212 CheckDef (current_container.AddProperty (prop), prop.Name, loc);
2213 get_implicit_value_parameter_type = null;
2214 set_implicit_value_parameter_type = null;
2215 get_parameters = null;
2216 set_parameters = null;
2217 current_local_parameters = null;
2221 opt_property_parameters
2224 $$ = Parameters.EmptyReadOnlyParameters;
2226 | OPEN_PARENS opt_formal_parameter_list CLOSE_PARENS
2232 opt_implement_clause
2237 | IMPLEMENTS implement_clause_list
2243 implement_clause_list
2244 : qualified_identifier
2246 ArrayList impl_list = new ArrayList ();
2247 impl_list.Add (DecomposeQI ((string)$1, lexer.Location));
2250 | implement_clause_list COMMA qualified_identifier
2252 ArrayList impl_list = (ArrayList) $1;
2253 impl_list.Add (DecomposeQI ((string)$3, lexer.Location));
2259 accessor_declarations
2260 : get_accessor_declaration opt_set_accessor_declaration
2262 $$ = new Pair ($1, $2);
2264 | set_accessor_declaration opt_get_accessor_declaration
2266 $$ = new Pair ($2, $1);
2270 opt_get_accessor_declaration
2271 : /* empty */ { $$ = null; }
2272 | get_accessor_declaration
2275 opt_set_accessor_declaration
2276 : /* empty */ { $$ = null; }
2277 | set_accessor_declaration
2280 get_accessor_declaration
2281 : opt_attributes GET _mark_ logical_end_of_line
2283 push_into_stack((int)Start_block.GET, (Location)$3);
2284 if ((current_modifiers & Modifiers.WRITEONLY) != 0)
2285 Report.Error (30023, (Location)$3, "'WriteOnly' properties cannot have a 'Get' accessor");
2287 current_local_parameters = get_parameters;
2289 lexer.PropertyParsing = false;
2292 // Add local var declaration
2294 ArrayList retval = new ArrayList ();
2295 retval.Add (new VariableDeclaration (get_implicit_value_parameter_name, get_implicit_value_parameter_type, (Location)$3));
2296 declare_local_variables (get_implicit_value_parameter_type, retval, lexer.Location);
2301 pop_out_of_stack((int)$7,lexer.Location);
2305 $$ = new Accessor ((Block) end_block(), (Attributes) $1);
2306 current_local_parameters = null;
2307 lexer.PropertyParsing = true;
2311 set_accessor_declaration
2312 : opt_attributes SET opt_set_parameter _mark_ logical_end_of_line
2314 push_into_stack((int)Start_block.SET, (Location)$4);
2315 if ((current_modifiers & Modifiers.READONLY) != 0)
2316 Report.Error (30022,
2318 "'ReadOnly' properties cannot have a 'Set' accessor");
2320 Parameter implicit_value_parameter = new Parameter (
2321 set_implicit_value_parameter_type,
2322 set_implicit_value_parameter_name,
2323 Parameter.Modifier.NONE, null);
2325 current_local_parameters = set_parameters;
2326 current_local_parameters.AppendParameter (implicit_value_parameter);
2329 lexer.PropertyParsing = false;
2334 pop_out_of_stack((int)$8,lexer.Location);
2339 $$ = new Accessor ((Block) end_block(), (Attributes) $1);
2340 current_local_parameters = null;
2341 lexer.PropertyParsing = true;
2348 set_implicit_value_parameter_type = (Expression) get_implicit_value_parameter_type; // TypeManager.system_object_expr;
2349 set_implicit_value_parameter_name = "Value";
2351 |OPEN_PARENS CLOSE_PARENS
2353 set_implicit_value_parameter_type = (Expression) get_implicit_value_parameter_type;
2354 set_implicit_value_parameter_name = "Value";
2356 | OPEN_PARENS opt_parameter_modifier opt_identifier opt_type_with_ranks CLOSE_PARENS
2358 Parameter.Modifier pm = (Parameter.Modifier)$2;
2359 if ((pm | Parameter.Modifier.VAL) != 0)
2360 Report.Error (31065,
2362 "Set cannot have a paremeter modifier other than 'ByVal'");
2364 set_implicit_value_parameter_type = (Expression) $4;
2366 if (set_implicit_value_parameter_type.ToString () != get_implicit_value_parameter_type.ToString ())
2367 Report.Error (31064,
2369 "Set value parameter type can not be different from property type");
2372 set_implicit_value_parameter_name = (string) $3;
2374 set_implicit_value_parameter_name = "Value";
2380 variable_declarators end_of_stmt
2382 int mod = (int) current_modifiers;
2384 VariableDeclaration.FixupTypes ((ArrayList) $2);
2385 VariableDeclaration.FixupArrayTypes ((ArrayList) $2);
2387 if (current_container is Module)
2388 mod = mod | Modifiers.STATIC;
2390 // Structure members are Public by default
2391 if ((current_container is Struct) && (mod == 0))
2392 mod = Modifiers.PUBLIC;
2394 if ((mod & Modifiers.Accessibility) == 0)
2395 mod |= Modifiers.PRIVATE;
2397 foreach (VariableDeclaration var in (ArrayList) $2){
2398 Location l = var.Location;
2399 Field field = new Field (var.type, mod, var.identifier,
2400 var.expression_or_array_initializer,
2401 (Attributes) null, l);
2403 CheckDef (current_container.AddField (field), field.Name, l);
2408 withevents_declaration
2409 : opt_dim_stmt WITHEVENTS variable_declarators logical_end_of_line
2411 // Module members are static by default, but delegates *can't* be declared static
2412 // so we must fix it, if mbas was the one actually responsible for this
2413 // instead of triggering an error.
2414 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
2415 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
2417 /* WithEvents Fields must be resolved into properties
2418 with a bit of magic behind the scenes */
2420 VariableDeclaration.FixupTypes ((ArrayList) $3);
2422 foreach (VariableDeclaration var in (ArrayList) $3) {
2423 // 1 - We create a private field
2424 Location l = var.Location;
2426 if ((current_modifiers & Modifiers.STATIC) > 0)
2427 Report.Error (30234, l, "'Static' is not valid on a WithEvents declaration.");
2429 Field field = new Field (var.type, Modifiers.PRIVATE, "_" + var.identifier,
2430 var.expression_or_array_initializer,
2431 (Attributes) null, l);
2433 CheckDef (current_container.AddField (field), field.Name, l);
2435 // 2 - Public property
2437 prop = BuildSimpleProperty (var.type, (string) var.identifier,
2438 field, (int) current_modifiers,
2439 (Attributes) current_attributes, l);
2441 CheckDef (current_container.AddProperty (prop), prop.Name, l);
2451 delegate_declaration
2452 : DELEGATE SUB _mark_
2453 identifier OPEN_PARENS
2454 opt_formal_parameter_list
2458 Location l = (Location)$3;
2459 // Module members are static by default, but delegates *can't* be declared static
2460 // so we must fix it, if mbas was the one actually responsible for this
2461 // instead of triggering an error.
2462 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
2463 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
2465 Mono.MonoBASIC.Delegate del = new Mono.MonoBASIC.Delegate (current_container,
2466 TypeManager.system_void_expr,
2467 (int) current_modifiers,
2468 MakeName ((string) $4), (Parameters) $6,
2469 (Attributes) current_attributes, l);
2471 del.Namespace = current_namespace;
2472 CheckDef (current_container.AddDelegate (del), del.Name, l);
2474 | DELEGATE FUNCTION _mark_
2475 identifier OPEN_PARENS
2476 opt_formal_parameter_list
2477 CLOSE_PARENS opt_type_with_ranks logical_end_of_line
2479 Location l = (Location)$3;
2481 // Module members are static by default, but delegates *can't* be declared static
2482 // so we must fix it, if mbas was the one actually responsible for this
2483 // instead of triggering an error.
2484 if (implicit_modifiers && ((current_modifiers & Modifiers.STATIC) != 0))
2485 current_modifiers = (current_modifiers & ~Modifiers.STATIC);
2487 Expression ftype = ($8 == null) ? TypeManager.system_object_expr : (Expression) $8;
2489 Mono.MonoBASIC.Delegate del = new Mono.MonoBASIC.Delegate (
2491 ftype, (int) current_modifiers, MakeName ((string) $4),
2492 (Parameters) $6, (Attributes) current_attributes, l);
2494 del.Namespace = current_namespace;
2495 CheckDef (current_container.AddDelegate (del), del.Name, l);
2500 : /* empty */ { $$ = null; }
2501 | HANDLES evt_handler { $$ = $2; }
2505 : qualified_identifier _mark_
2507 $$ = (Expression) DecomposeQI ((string)$1, (Location)$2);
2513 | ME DOT qualified_identifier _mark_
2515 $$ = (Expression) DecomposeQI ((string)$3, (Location)$4);
2517 /*| MYBASE DOT qualified_identifier
2519 // FIXME: this is blatantly wrong and crash-prone
2520 $$ = (Expression) DecomposeQI ("MyBase." + (string)$4, lexer.Location);
2524 constructor_declaration
2525 : SUB _mark_ NEW opt_params logical_end_of_line
2527 push_into_stack((int)Start_block.SUB, (Location)$2);
2528 current_local_parameters = (Parameters) $4;
2530 $$ = new Constructor ((string) "New", (Parameters) $4, (ConstructorInitializer) null, (Location)$2);
2535 Constructor c = (Constructor) $1;
2536 c.Block = (Block) end_block();
2537 c.ModFlags = (int) current_modifiers;
2538 c.OptAttributes = current_attributes;
2540 c.Initializer = CheckConstructorInitializer (ref c.Block.statements);
2542 CheckDef (current_container.AddConstructor(c), c.Name, c.Location);
2543 current_local_parameters = null;
2547 pop_out_of_stack((int)$9, lexer.Location);
2552 opt_formal_parameter_list
2555 $$ = Parameters.EmptyReadOnlyParameters;
2557 | formal_parameter_list
2560 //Parameter p = ((Parameters) $1).FixedParameters[0];
2564 formal_parameter_list
2567 ArrayList pars_list = (ArrayList) $1;
2568 Parameter [] pars = null;
2569 Parameter array_parameter = null;
2570 int non_array_count = pars_list.Count;
2571 if (pars_list.Count > 0 && (((Parameter) pars_list [pars_list.Count - 1]).ModFlags & Parameter.Modifier.PARAMS) != 0) {
2572 array_parameter = (Parameter) pars_list [pars_list.Count - 1];
2573 non_array_count = pars_list.Count - 1;
2575 foreach (Parameter par in pars_list)
2576 if (par != array_parameter && (par.ModFlags & Parameter.Modifier.PARAMS) != 0) {
2577 Report.Error (30192, lexer.Location, "ParamArray parameters must be last");
2578 non_array_count = 0;
2579 array_parameter = null;
2582 if (non_array_count > 0) {
2583 pars = new Parameter [non_array_count];
2584 pars_list.CopyTo (0, pars, 0, non_array_count);
2586 $$ = new Parameters (pars, array_parameter, lexer.Location);
2593 ArrayList pars = new ArrayList ();
2598 | parameters COMMA parameter
2600 ArrayList pars = (ArrayList) $1;
2609 opt_parameter_modifier
2610 identifier _mark_ opt_type_character opt_rank_specifiers opt_type_with_ranks opt_variable_initializer
2612 Parameter.Modifier pm = (Parameter.Modifier)$2;
2613 bool opt_parm = ((pm & Parameter.Modifier.OPTIONAL) != 0);
2616 if (opt_parm && ($8 == null))
2617 Report.Error (30812, (Location)$4, "Optional parameters must have a default value");
2619 if (!opt_parm && ($8 != null))
2620 Report.Error (32024, (Location)$4, "Non-Optional parameters should not have a default value");
2622 if ((pm & Parameter.Modifier.PARAMS) != 0) {
2623 if ((pm & ~Parameter.Modifier.PARAMS) != 0)
2624 Report.Error (30667, (Location)$4, "ParamArray parameters must be ByVal");
2627 if ((pm & Parameter.Modifier.REF) !=0)
2628 pm |= Parameter.Modifier.ISBYREF;
2630 if ($5 != null && $7 != null && $5 != $7)
2631 Report.Error (30302, (Location)$4, "Type character conflicts with declared type."); // TODO: Correct error number and message text
2633 ptype = (Expression)(($7 == null) ? (($5 == null) ? TypeManager.system_object_expr : $5) : $7);
2635 string t = ptype.ToString ();
2636 if (t.IndexOf('[') >= 0)
2637 Report.Error (31087, (Location)$4, "Array types specified in too many places");
2639 ptype = DecomposeQI (t + VariableDeclaration.BuildRanks ((ArrayList) $6, true, (Location)$4), (Location)$4);
2641 if ((pm & Parameter.Modifier.PARAMS) != 0 && ptype.ToString ().IndexOf('[') < 0)
2642 Report.Error (30050, (Location)$4, "ParamArray parameters must be an array type");
2643 $$ = new Parameter (ptype, (string) $3, pm,
2644 (Attributes) $1, (Expression) $8, opt_parm);
2648 opt_parameter_modifier
2649 : /* empty */ { $$ = Parameter.Modifier.VAL; }
2650 | parameter_modifiers { $$ = $1; }
2654 : parameter_modifiers parameter_modifier { $$ = (Parameter.Modifier)$1 | (Parameter.Modifier)$2; }
2655 | parameter_modifier { $$ = $1; }
2659 : BYREF { $$ = Parameter.Modifier.REF | Parameter.Modifier.ISBYREF; }
2660 | BYVAL { $$ = Parameter.Modifier.VAL; }
2661 | OPTIONAL { $$ = Parameter.Modifier.OPTIONAL; }
2662 | PARAM_ARRAY { $$ = Parameter.Modifier.PARAMS; }
2667 | statement_list end_of_stmt
2672 | statement_list end_of_stmt
2677 : declaration_statement
2679 if ($1 != null && (Block) $1 != current_block){
2680 current_block.AddStatement ((Statement) $1);
2681 current_block = (Block) $1;
2684 | embedded_statement
2686 current_block.AddStatement ((Statement) $1);
2689 | ADDHANDLER prefixed_unary_expression COMMA ADDRESSOF evt_handler
2691 AddHandler ((Expression) $2, (Expression) $5);
2693 | REMOVEHANDLER prefixed_unary_expression COMMA ADDRESSOF evt_handler
2695 RemoveHandler ((Expression) $2, (Expression) $5);
2697 | RAISEEVENT identifier opt_raise_event_args //OPEN_PARENS opt_argument_list CLOSE_PARENS
2699 RaiseEvent ((string) $2, (ArrayList) $3);
2701 /* | array_handling_statement */
2702 /* | empty_statement */
2705 current_block.AddStatement ((Statement) $1);
2710 : END_EOL {$$ = new End (lexer.Location);}
2714 opt_raise_event_args
2715 : /* empty */ { $$ = null; }
2716 | OPEN_PARENS opt_argument_list CLOSE_PARENS
2733 LabeledStatement labeled = new LabeledStatement ((string) $1, lexer.Location);
2735 if (!current_block.AddLabel ((string) $1, labeled)){
2736 Location l = lexer.Location;
2737 Report.Error (140, l, "The label '" + ((string) $1) + "' is a duplicate");
2739 current_block.AddStatement (labeled);
2743 LabeledStatement labeled = new LabeledStatement ((string) $1, lexer.Location);
2745 if (!current_block.AddLabel ((string) $1, labeled)){
2746 Location l = lexer.Location;
2747 Report.Error (140, l, "The label '" + ((string) $1) + "' is a duplicate");
2749 current_block.AddStatement (labeled);
2755 : expression_statement
2756 | selection_statement
2757 | iteration_statement
2759 | synclock_statement
2761 | array_handling_statement
2767 $$ = new EmptyStatement ();
2773 : WITH _mark_ expression end_of_stmt /* was : WITH qualified_identifier end_of_stmt */
2775 // was : Expression e = DecomposeQI ((string) $3, (Location)$2);
2776 push_into_stack((int)Start_block.WITH, (Location)$2);
2777 Expression e = (Expression) $3;
2784 pop_out_of_stack((int)$7,lexer.Location);
2785 Block b = end_block();
2792 array_handling_statement
2798 : REDIM opt_preserve redim_clauses
2800 ArrayList list = (ArrayList) $3;
2801 ReDim r = new ReDim (list, (bool) $2, lexer.Location);
2808 : /* empty */ { $$ = false; }
2809 | PRESERVE { $$ = true; }
2815 ArrayList clauses = new ArrayList ();
2820 | redim_clauses COMMA redim_clause
2822 ArrayList clauses = (ArrayList) ($1);
2830 : invocation_expression
2832 Invocation i = (Invocation) $1;
2833 RedimClause rc = new RedimClause (i.expr, i.Arguments);
2839 : ERASE erase_clauses
2841 ArrayList list = (ArrayList) $2;
2842 foreach(Expression e in list)
2844 Erase r = new Erase (e, lexer.Location);
2853 ArrayList clauses = new ArrayList ();
2858 | erase_clauses COMMA erase_clause
2860 ArrayList clauses = (ArrayList) ($1);
2868 : primary_expression
2873 | continue_statement
2874 | */return_statement
2885 $$ = new Goto (current_block, (string) $2, lexer.Location);
2890 : THROW _mark_ opt_expression
2892 $$ = new Throw ((Expression) $3, (Location)$2);
2899 $$ = new Exit ((ExitType)$2, lexer.Location);
2904 : DO { $$ = ExitType.DO; }
2905 | FOR { $$ = ExitType.FOR; }
2906 | WHILE { $$ = ExitType.WHILE; }
2907 | SELECT { $$ = ExitType.SELECT; }
2908 | SUB { $$ = ExitType.SUB; }
2909 | FUNCTION { $$ = ExitType.FUNCTION; }
2910 | PROPERTY { $$ = ExitType.PROPERTY; }
2911 | TRY { $$ = ExitType.TRY; }
2914 : RETURN opt_expression
2916 $$ = new Return ((Expression) $2, lexer.Location);
2928 : FOR EACH identifier _mark_ opt_type_spec IN
2929 expression end_of_stmt
2931 Location l = (Location)$4;
2932 push_into_stack((int)Start_block.FOR, l);
2933 LocalVariableReference v = null;
2939 VariableDeclaration decl = new VariableDeclaration ((string) $3,
2940 (Expression) $5, null, (Location)$4, null);
2942 vi = current_block.AddVariable (
2943 (Expression) $5, decl.identifier, current_local_parameters, decl.Location);
2946 if (decl.expression_or_array_initializer is Expression)
2947 expr = (Expression) decl.expression_or_array_initializer;
2948 else if (decl.expression_or_array_initializer == null)
2952 ArrayList init = (ArrayList) decl.expression_or_array_initializer;
2953 expr = new ArrayCreation ((Expression) $5, "", init, decl.Location);
2956 v = new LocalVariableReference (current_block, decl.identifier, l);
2960 Assign a = new Assign (v, expr, decl.Location);
2961 current_block.AddStatement (new StatementExpression (a, (Location)$4));
2966 vi = current_block.GetVariableInfo ((string) $3);
2969 // Get a reference to this variable.
2970 v = new LocalVariableReference (current_block, (string) $3, l, vi, false);
2973 Report.Error (451, (Location)$4,"Name '" + (string) $3 + "' is not declared.");
2982 pop_out_of_stack((int)$11,lexer.Location);
2984 _mark_ opt_identifier
2986 string s = $3.ToString();
2989 s1 = $14.ToString();
2990 if (s1 != "" && s != s1)
2992 Report.Error(30070, (Location)$13, "Next Control Variable '"+s1+"' does not match with For Loop control variable '"+s+"'");
2994 LocalVariableReference v = (LocalVariableReference) oob_stack.Pop ();
2995 Block foreach_block = end_block();
2999 f = new Foreach (null, v, (Expression) $7, foreach_block, (Location)$4);
3003 current_block.AddStatement (f);
3012 : YIELD expression _mark_
3014 if (!UseExtendedSyntax)
3020 if (iterator_container == null){
3021 Report.Error (204, (Location)$3, "yield statement can only be used within a method, operator or property");
3024 iterator_container.SetYields ();
3025 $$ = new Yield ((Expression) $2, (Location)$3);
3030 if (!UseExtendedSyntax)
3036 if (iterator_container == null){
3037 Report.Error (204, (Location)$3, "yield statement can only be used within a method, operator or property");
3040 iterator_container.SetYields ();
3041 $$ = new YieldBreak ((Location)$3);
3047 : SYNCLOCK _mark_ expression end_of_stmt
3049 push_into_stack((int)Start_block.SYNCLOCK, (Location)$2);
3055 pop_out_of_stack((int)$7,lexer.Location);
3056 $$ = new Lock ((Expression) $3, (Statement) (Block) end_block(), (Location)$2);
3066 : TRY _mark_ end_of_stmt
3068 push_into_stack((int)Start_block.TRY, (Location)$2);
3069 try_top=(Location)$2;
3075 tmp_catch_clauses = (ArrayList) $6;
3080 /*FIXME: Try block without a end try is throwing error at a wrong place*/
3083 _mark_ opt_end_block
3085 pop_out_of_stack((int)$3,lexer.Location);
3087 ArrayList s = new ArrayList ();
3089 foreach (Catch cc in (ArrayList) tmp_catch_clauses) {
3096 // Now s contains the list of specific catch clauses
3097 // and g contains the general one.
3098 Block b = end_block();
3100 $$ = new Try ((Block) b, s, g, null, try_top);
3107 tmp_block = end_block();
3114 _mark_ opt_end_block
3116 pop_out_of_stack((int)$8,lexer.Location);
3118 ArrayList s = new ArrayList ();
3119 ArrayList catch_list = (ArrayList) tmp_catch_clauses;
3121 if (catch_list != null){
3122 foreach (Catch cc in catch_list) {
3130 $$ = new Try ((Block) tmp_block, s, g, (Block) end_block(), try_top);
3136 : /* empty */ { $$ = null; }
3143 ArrayList l = new ArrayList ();
3148 | catch_clauses catch_clause
3150 ArrayList l = (ArrayList) $1;
3158 : /* empty */ { $$ = null; }
3163 : /* empty */ { $$ = null; }
3164 | WHEN boolean_expression
3171 : CATCH opt_catch_args opt_when _mark_ end_of_stmt
3173 Expression type = null;
3177 DictionaryEntry cc = (DictionaryEntry) $2;
3178 type = (Expression) cc.Key;
3179 id = (string) cc.Value;
3182 ArrayList one = new ArrayList ();
3183 Location loc = (Location)$4;
3185 one.Add (new VariableDeclaration (id, type, loc));
3188 current_block = new Block (current_block);
3189 Block b = declare_local_variables (type, one, loc);
3194 opt_statement_list {
3195 Expression type = null;
3197 Block b_catch = current_block;
3200 DictionaryEntry cc = (DictionaryEntry) $2;
3201 type = (Expression) cc.Key;
3202 id = (string) cc.Value;
3206 // FIXME: I can change this for an assignment.
3208 while (current_block != (Block) $1)
3209 current_block = current_block.Parent;
3212 $$ = new Catch (type, id , (Block) b_catch, (Expression) $3, (Location)$4);
3217 : /* empty */ { $$ = null; }
3222 : identifier AS _mark_ type
3224 $$ = new DictionaryEntry ($4, $1);
3226 | error _mark_ AS type
3228 Report.Error(30203, (Location)$2, "Identifier Expected");
3231 | identifier AS _mark_ error
3233 Report.Error(30182, (Location)$3, "Type Expected");
3240 : DO _mark_ opt_do_construct end_of_stmt
3242 push_into_stack((int)Start_block.DO, (Location)$2);
3248 pop_out_of_stack((int)$7,lexer.Location);
3250 _mark_ opt_do_construct
3252 Expression t_before = (Expression) $3;
3253 Expression t_after = (Expression) $10;
3256 if ((t_before != null) && (t_after != null))
3257 Report.Error (30238, (Location)$9, "'Loop' cannot have a condition if matching 'Do' has one.");
3259 if ((t_before == null) && (t_after == null))
3260 t = new BoolLiteral (true);
3262 t = (t_before != null) ? t_before : t_after;
3264 DoOptions test_type = (t_before != null) ? DoOptions.TEST_BEFORE : DoOptions.TEST_AFTER;
3266 if (((do_type == DoOptions.WHILE) && (test_type == DoOptions.TEST_BEFORE)) ||
3267 ((do_type == DoOptions.UNTIL) && (test_type == DoOptions.TEST_AFTER)))
3268 t = new Unary (Unary.Operator.LogicalNot, (Expression) t, (Location)$2);
3270 $$ = new Do ((Statement) end_block(), (Expression) t, test_type, (Location)$2);
3275 : /* empty */ { $$ = null; }
3276 | while_or_until boolean_expression
3278 do_type = (DoOptions)$1;
3279 $$ = (Expression) $2;
3284 : WHILE { $$ = DoOptions.WHILE; }
3285 | UNTIL { $$ = DoOptions.UNTIL; }
3291 push_into_stack((int)Start_block.WHILE, lexer.Location);
3293 oob_stack.Push (lexer.Location);
3295 boolean_expression end_of_stmt
3299 Location l = (Location) oob_stack.Pop ();
3300 pop_out_of_stack((int)$6,lexer.Location);
3301 Block b = end_block();
3302 Expression e = (Expression) $3;
3303 $$ = new While ((Expression) e, (Statement) b, l);
3308 : FOR _mark_ identifier opt_type_spec ASSIGN expression TO expression opt_step end_of_stmt
3310 push_into_stack((int)Start_block.FOR, (Location)$2);
3314 ArrayList VarDeclaration = new ArrayList ();
3315 VarDeclaration.Add (new VariableDeclaration ((string) $3,
3316 (Expression) $4, null, (Location)$2, null));
3318 DictionaryEntry de = new DictionaryEntry (DecomposeQI("_local_vars_", (Location)$2), VarDeclaration);
3319 Block b = declare_local_variables ((Expression) de.Key, (ArrayList) de.Value, (Location)$2);
3327 pop_out_of_stack((int)$13,lexer.Location);
3329 _mark_ opt_identifier
3331 string s = $3.ToString();
3334 s1 = $16.ToString();
3335 if (s1 != "" && s != s1) {
3336 Report.Error(30070, (Location)$15, "Next Control Variable '"+s1+"' does not match with For Loop control variable '"+s+"'");
3339 Block inner_statement = end_block();
3340 Location l = (Location)$2;
3341 Expression for_var = (Expression) DecomposeQI ((string)$3, l);
3343 For f = new For (for_var, (Expression) $6, (Expression) $8, (Expression) $9, inner_statement, l);
3346 current_block.AddStatement (f);
3355 : /* empty */ { $$ = new IntLiteral ((Int32) 1); }
3356 | STEP expression { $$ = $2; }
3365 : if_statement_open opt_then end_of_stmt opt_statement_list
3367 push_into_stack((int)Start_block.IF, (Location)$1);
3373 | if_statement_open THEN pre_embedded_statement opt_else_pre_embedded_statement
3377 Location l = (Location) oob_stack.Pop ();
3378 tmp_expr = (Expression)expr_stack.Pop();
3379 $$ = new If ((Expression) tmp_expr, end_block(), l);
3383 Location l = (Location) oob_stack.Pop ();
3384 tmp_expr = (Expression)expr_stack.Pop();
3385 tmp_block = (Block) tmp_blocks.Pop ();
3386 $$ = new If ((Expression) tmp_expr, (Statement) tmp_block, end_block(), l);
3389 | if_statement_open THEN else_pre_embedded_statement
3391 Location l = (Location) oob_stack.Pop ();
3392 tmp_expr = (Expression)expr_stack.Pop();
3393 tmp_block = (Block) tmp_blocks.Pop ();
3394 $$ = new If ((Expression) tmp_expr, (Statement) tmp_block, end_block(), l);
3398 pre_embedded_statement
3399 : embedded_statement
3401 current_block.AddStatement ((Statement) $1);
3405 opt_else_pre_embedded_statement
3407 | else_pre_embedded_statement
3410 else_pre_embedded_statement
3413 Block bl = end_block();
3414 tmp_blocks.Push(bl);
3418 | ELSE embedded_statement
3420 Block bl = end_block();
3421 tmp_blocks.Push(bl);
3424 current_block.AddStatement ((Statement) $2);
3428 /*FIXME:if without end if not working. Error line shown is nor correct*/
3432 oob_stack.Push (lexer.Location);
3437 tmp_expr = (Expression) $4;
3438 expr_stack.Push(tmp_expr);
3452 Location l = (Location) oob_stack.Pop ();
3453 pop_out_of_stack((int)$1,lexer.Location);
3454 Expression expr = (Expression)expr_stack.Pop();
3455 $$ = new If ((Expression) expr, (Statement) end_block(), l);
3460 Block bl = end_block();
3461 tmp_blocks.Push(bl);
3467 Location l = (Location) oob_stack.Pop ();
3468 pop_out_of_stack((int)$5,lexer.Location);
3469 tmp_expr = (Expression)expr_stack.Pop();
3470 tmp_block = (Block) tmp_blocks.Pop();
3471 $$ = new If ((Expression) tmp_expr, (Statement) tmp_block, (Statement) end_block(), l);
3474 opt_elseif boolean_expression opt_then
3476 tmp_expr = (Expression) $2;
3477 expr_stack.Push(tmp_expr);
3478 tmp_block = end_block();
3479 tmp_blocks.Push(tmp_block);
3482 end_of_stmt opt_statement_list
3483 else_if_statement_rest
3485 Statement stmt = (Statement) statement_stack.Pop();
3486 Block bl = (Block) tmp_blocks.Pop();
3487 Expression expr = (Expression)expr_stack.Pop();
3488 Location l = (Location) oob_stack.Pop ();
3489 $$ = (Statement) new If ((Expression) expr, (Statement) bl , stmt , l);
3494 else_if_statement_rest
3498 Block bl = end_block();
3499 tmp_blocks.Push(bl);
3505 Location l = (Location) oob_stack.Pop ();
3506 pop_out_of_stack((int)$5,lexer.Location);
3508 Expression expr = (Expression)expr_stack.Pop();
3509 Block bl = (Block)tmp_blocks.Pop();
3510 Statement stmt = (Statement) new If ((Expression) expr, (Statement) bl , (Statement) end_block(), l);
3511 statement_stack.Push(stmt);
3514 opt_elseif boolean_expression opt_then
3516 expr_stack.Push((Expression) $2);
3517 Block bl = end_block();
3518 tmp_blocks.Push(bl);
3521 end_of_stmt opt_statement_list
3522 else_if_statement_rest
3524 Location l = (Location) oob_stack.Pop ();
3526 Statement tmp_stmt = (Statement)statement_stack.Pop();
3527 Block bl = (Block) tmp_blocks.Pop();
3528 Expression expr = (Expression)expr_stack.Pop();
3529 Statement stmt = (Statement) new If ((Expression) expr, (Statement) bl, tmp_stmt , l);
3530 statement_stack.Push(stmt);
3535 Location l = (Location) oob_stack.Pop ();
3536 pop_out_of_stack((int)$1,lexer.Location);
3538 Expression expr = (Expression)expr_stack.Pop();
3539 Statement stmt = (Statement) new If ((Expression) expr, (Statement) end_block(), l);
3540 statement_stack.Push(stmt);
3544 /*FIXME:Select without an expression is showing a parser error instead of a expression missing error*/
3547 _mark_ opt_case expression end_of_stmt
3549 push_into_stack((int)Start_block.SELECT, (Location)$2);
3550 oob_stack.Push (lexer.Location);
3551 switch_stack.Push (current_block);
3556 pop_out_of_stack((int)$8,lexer.Location);
3557 current_block = (Block) switch_stack.Pop ();
3558 $$ = new Switch ((Expression) $4, (ArrayList) $7, (Location) oob_stack.Pop ());
3563 : /* empty */ { $$ = null; }
3564 | case_sections { $$ = $1; }
3568 : case_sections case_section
3570 ArrayList sections = (ArrayList) $1;
3577 ArrayList sections = new ArrayList ();
3591 : CASE case_clauses ends
3597 //Block topmost = current_block;
3598 Block topmost = end_block();
3600 while (topmost.Implicit)
3601 topmost = topmost.Parent;
3603 // FIXME: This is a horrible hack which MUST go
3604 topmost.statements.Add (new Break (lexer.Location));
3605 $$ = new SwitchSection ((ArrayList) $2, topmost);
3608 /* FIXME: we should somehow flag an error
3609 (BC30321 'Case' cannot follow a 'Case Else'
3610 in the same 'Select' statement.)
3611 if Case Else is not the last of the Case clauses
3618 //Block topmost = current_block;
3619 Block topmost = end_block();
3621 while (topmost.Implicit)
3622 topmost = topmost.Parent;
3624 // FIXME: This is a horrible hack which MUST go
3625 topmost.statements.Add (new Break (lexer.Location));
3627 ArrayList a = new ArrayList();
3628 a.Add (new SwitchLabel (null, lexer.Location));
3629 $$ = new SwitchSection ((ArrayList) a, topmost);
3636 if ($1 is ArrayList) //From expression TO expression
3640 ArrayList labels = new ArrayList ();
3646 | case_clauses COMMA case_clause
3648 ArrayList labels = (ArrayList) ($1);
3656 : opt_is comparison_operator expression
3659 $$ = new SwitchLabel ((Expression) $1, lexer.Location);
3661 | expression TO expression
3663 //FIXME: need to handle when expressions are character strings.
3664 Constant start = (Constant) $1;
3665 Constant end = (Constant) $3;
3666 int i = 0, s = 0, e = 0;
3667 Location l = lexer.Location ;
3668 ArrayList labels = new ArrayList ();
3671 s = (int) start.GetValue ();
3673 e = (int) end.GetValue ();
3674 for(i = s; i <= e; i++) {
3675 labels.Add(new SwitchLabel ((Expression)new IntLiteral(i), l));
3700 expression_statement
3701 : statement_expression
3708 statement_expression
3709 : invocation_expression { $$ = new StatementExpression ((ExpressionStatement) $1, lexer.Location); }
3710 | object_creation_expression { $$ = new StatementExpression ((ExpressionStatement) $1, lexer.Location); }
3711 | assignment_expression { $$ = new StatementExpression ((ExpressionStatement) $1, lexer.Location); }
3714 object_creation_expression
3715 : NEW type OPEN_PARENS _mark_ opt_argument_list CLOSE_PARENS
3717 $$ = new New ((Expression) $2, (ArrayList) $5, (Location)$4);
3721 $$ = new New ((Expression) $2, new ArrayList(), (Location)$3);
3725 array_creation_expression
3726 : object_creation_expression opt_rank_specifiers _mark_ array_initializer
3729 ArrayList dims = new ArrayList();
3731 if (n.Arguments != null) {
3732 foreach (Argument a in n.Arguments) {
3737 Expression atype = n.RequestedType;
3740 atype = DecomposeQI (atype.ToString () + VariableDeclaration.BuildRanks ((ArrayList)$2, true, (Location)$3), (Location)$3);
3742 ArrayList init = (ArrayList) $4;
3743 if (init.Count == 0)
3746 if (VariableDeclaration.IndexesSpecifiedInRank(dims)) {
3747 VariableDeclaration.VBFixIndexList (ref dims);
3748 $$ = new ArrayCreation (atype, dims, "", init, (Location)$3);
3752 string rank = VariableDeclaration.BuildRank (dims);
3753 $$ = new ArrayCreation (atype, rank, (ArrayList) $4, (Location)$3);
3755 //Console.WriteLine ("Creating a new array of type " + (atype.ToString()) + " with rank '" + dims + "'");
3760 : object_creation_expression
3761 | array_creation_expression
3764 declaration_statement
3765 : _mark_ local_variable_declaration
3768 DictionaryEntry de = (DictionaryEntry) $2;
3770 $$ = declare_local_variables ((Expression) de.Key, (ArrayList) de.Value, (Location)$1);
3773 | local_constant_declaration
3776 DictionaryEntry de = (DictionaryEntry) $1;
3778 $$ = declare_local_constant ((Expression) de.Key, (ArrayList) de.Value);
3783 local_variable_declaration
3784 : DIM _mark_ variable_declarators
3786 $$ = new DictionaryEntry (DecomposeQI("_local_vars_", (Location)$2), $3);
3791 local_constant_declaration
3792 : CONST constant_declarators
3795 $$ = new DictionaryEntry (DecomposeQI("_local_consts_", lexer.Location), $2);
3801 constant_declarators
3802 : constant_declarator
3804 ArrayList decl = new ArrayList ();
3810 | constant_declarators COMMA constant_declarator
3812 ArrayList decls = (ArrayList) $1;
3821 : _mark_ variable_name opt_type_decl opt_variable_initializer
3823 VarName vname = (VarName) $2;
3824 string varname = (string) vname.Name;
3825 current_rank_specifiers = (ArrayList) vname.Rank;
3826 object varinit = $4;
3828 if (varinit == null)
3830 30438, (Location)$1, "Constant should have a value"
3833 if (vname.Type != null && $3 != null)
3835 30302, (Location)$1,
3836 "Type character cannot be used with explicit type declaration" );
3838 Expression vartype = ($3 == null) ? ((vname.Type == null) ? TypeManager.system_object_expr : (Expression) vname.Type ) : (Expression) $3;
3840 if (current_rank_specifiers != null)
3842 Report.Error (30424, (Location)$1, "Constant doesn't support array");
3846 $$ = new VariableDeclaration (varname, vartype, varinit, (Location)$1, null);
3850 variable_declarators
3851 : variable_declarator
3853 ArrayList decl = new ArrayList ();
3854 decl.AddRange ((ArrayList) $1);
3857 | variable_declarators COMMA variable_declarator
3859 ArrayList decls = (ArrayList) $1;
3860 decls.AddRange ((ArrayList) $3);
3866 : _mark_ variable_names opt_type_decl opt_variable_initializer
3868 ArrayList names = (ArrayList) $2;
3869 object varinit = $4;
3870 ArrayList VarDeclarations = new ArrayList();
3872 ArrayList a_dims = null;
3874 if ((names.Count > 1) && (varinit != null))
3876 30671, (Location)$1,
3877 "Multiple variables with single type can not have " +
3878 "a explicit initialization" );
3881 foreach (VarName vname in names)
3883 string varname = (string) vname.Name;
3884 current_rank_specifiers = (ArrayList) vname.Rank;
3888 if(vname.Type != null && $3 != null)
3890 30302, (Location)$1,
3891 "Type character cannot be used with explicit type declaration" );
3893 // Some checking is required for particularly weird declarations
3894 // like Dim a As Integer(,)
3896 vartype = (Expression) ((Pair) $3).First;
3898 /*if ($4 != null && $4 is ArrayList)
3899 Report.Error (205, "End of statement expected.");*/
3901 ArrayList args = (ArrayList) ((Pair) $3).Second;
3902 if (current_rank_specifiers != null)
3903 Report.Error (31087, (Location)$1,
3904 "Array types specified in too many places");
3906 if (VariableDeclaration.IndexesSpecifiedInRank (args))
3907 Report.Error (30638, (Location)$1,"Array bounds cannot appear in type specifiers.");
3909 current_rank_specifiers = new ArrayList ();
3910 current_rank_specifiers.Add (args);
3913 vartype = ($3 == null) ? ((vname.Type == null) ? TypeManager.system_object_expr : (Expression) vname.Type ) : (Expression) $3;
3915 // if the variable is an array with explicit bound
3916 // and having explicit initialization throw exception
3917 if (current_rank_specifiers != null && varinit != null)
3919 bool broken = false;
3920 foreach (ArrayList exprs in current_rank_specifiers)
3922 foreach (Expression expr in exprs)
3924 if (!((Expression)expr is EmptyExpression ))
3927 30672, (Location)$1,
3928 "Array declared with explicit bound " +
3929 " can not have explicit initialization");
3940 Check for a declaration like Dim a(2) or Dim a(2,3)
3941 If this is the case, we must generate an ArrayCreationExpression
3942 and, in case, add the initializer after the array has been created.
3944 if (VariableDeclaration.IsArrayDecl (this)) {
3945 if (VariableDeclaration.IndexesSpecified(current_rank_specifiers)) {
3946 a_dims = (ArrayList) current_rank_specifiers;
3947 VariableDeclaration.VBFixIndexLists (ref a_dims);
3948 varinit = VariableDeclaration.BuildArrayCreator(vartype, a_dims, (ArrayList) varinit, (Location)$1);
3950 vartype = DecomposeQI (vartype.ToString() + VariableDeclaration.BuildRanks (current_rank_specifiers, false, (Location)$1), (Location)$1);
3953 if (vartype is New) {
3954 if (varinit != null) {
3955 Report.Error (30205, (Location)$1, "End of statement expected");
3961 vartype = ((New)vartype).RequestedType;
3964 VarDeclarations.Add (new VariableDeclaration (varname, vartype, varinit, (Location)$1, null));
3966 $$ = VarDeclarations;
3973 ArrayList list = new ArrayList ();
3977 | variable_names COMMA variable_name
3979 ArrayList list = (ArrayList) $1;
3986 : identifier opt_type_character opt_array_name_modifier
3988 $$ = new VarName ($1, $2, $3);
3999 $$ = (Expression) $2;
4005 | AS type _mark_ rank_specifiers
4007 $$ = DecomposeQI ($2.ToString() + VariableDeclaration.BuildRanks ((ArrayList)$4, true, (Location)$3), (Location)$3);
4012 : opt_type_with_ranks
4018 New n = new New ((Expression)$3, null, lexer.Location);
4019 $$ = (Expression) n;
4021 | AS NEW type OPEN_PARENS opt_argument_list CLOSE_PARENS
4023 New n = new New ((Expression)$3, (ArrayList) $5, lexer.Location);
4024 $$ = (Expression) n;
4026 /*| AS NEW type OPEN_PARENS ADDRESSOF expression CLOSE_PARENS
4028 ArrayList args = new ArrayList();
4029 Argument arg = new Argument ((Expression) $6, Argument.AType.Expression);
4032 New n = new New ((Expression)$3, (ArrayList) args, lexer.Location);
4033 $$ = (Expression) n;
4037 opt_array_name_modifier
4038 : /* empty */ { $$ = null; }
4039 | array_type_modifier { $$ = $1; }
4043 : rank_specifiers { $$ = $1; }
4046 opt_variable_initializer
4047 : /* empty */ { $$ = null; }
4048 | ASSIGN variable_initializer { $$ = $2; }
4051 variable_initializer
4054 Expression etmp = (Expression) $1;
4055 etmp = SetValueRequiredFlag (etmp);
4066 : OPEN_BRACE CLOSE_BRACE
4068 ArrayList list = new ArrayList ();
4071 | OPEN_BRACE variable_initializer_list CLOSE_BRACE
4073 $$ = (ArrayList) $2;
4077 variable_initializer_list
4078 : variable_initializer
4080 ArrayList list = new ArrayList ();
4084 | variable_initializer_list COMMA variable_initializer
4086 ArrayList list = (ArrayList) $1;
4107 ArrayList rs = new ArrayList();
4111 | rank_specifiers rank_specifier
4113 ArrayList rs = (ArrayList) $1;
4120 : OPEN_PARENS opt_dim_specifiers CLOSE_PARENS
4129 ArrayList ds = new ArrayList();
4130 ds.Add (new EmptyExpression());
4135 ArrayList ds = new ArrayList();
4136 ds.Add ((Expression) $1);
4139 | opt_dim_specifiers COMMA expression
4141 ArrayList ds = (ArrayList) $1;
4142 ds.Add ((Expression) $3);
4145 | opt_dim_specifiers COMMA
4147 ArrayList ds = (ArrayList) $1;
4148 ds.Add (new EmptyExpression());
4158 | parenthesized_expression
4161 | qualified_identifier opt_type_character _mark_
4163 string name = (string) $1;
4164 $$ = DecomposeQI (name, (Location)$3);
4166 | get_type_expression
4168 | invocation_expression
4173 { Report.Error(30201,(Location)$2,"Expression expected"); $$ = (Expression)null;}
4180 | LITERAL_DATE { $$ = new DateLiteral ((DateTime)lexer.Value); }
4181 | LITERAL_CHARACTER { $$ = new CharLiteral ((char) lexer.Value); }
4182 | LITERAL_STRING { $$ = new StringLiteral ((string) lexer.Value); }
4183 | NOTHING { $$ = NullLiteral.Null; }
4187 : LITERAL_SINGLE { $$ = new FloatLiteral ((float) lexer.Value); }
4188 | LITERAL_DOUBLE { $$ = new DoubleLiteral ((double) lexer.Value); }
4189 | LITERAL_DECIMAL { $$ = new DecimalLiteral ((decimal) lexer.Value); }
4194 object v = lexer.Value;
4197 $$ = new IntLiteral ((Int32)v);
4198 else if (v is short)
4199 $$ = new ShortLiteral ((Int16)v);
4201 $$ = new LongLiteral ((Int64)v);
4203 Console.WriteLine ("Unexpected result from scanner");
4209 : TRUE { $$ = new BoolLiteral (true); }
4210 | FALSE { $$ = new BoolLiteral (false); }
4213 parenthesized_expression
4214 : OPEN_PARENS expression CLOSE_PARENS
4219 : primary_expression DOT _mark_ identifier
4222 string id_name = (string)$4;
4223 if (id_name.ToUpper() == "NEW")
4225 $$ = new MemberAccess ((Expression) $1, id_name, (Location)$3);
4229 if (with_stack.Count > 0) {
4230 Expression e = (Expression) with_stack.Peek();
4231 $$ = new MemberAccess (e, (string) $4, (Location)$3);
4239 /* | primary_expression DOT _mark_ NEW
4241 $$ = new MemberAccess ((Expression) $1, (string) ".ctor", (Location)$3);
4243 | predefined_type DOT _mark_ identifier
4246 $$ = new MemberAccess ((Expression) $1, (string) $4, (Location)$3);
4249 if (with_stack.Count > 0) {
4250 Expression e = (Expression) with_stack.Peek();
4251 $$ = new MemberAccess (e, (string) $4, (Location)$3);
4265 invocation_expression
4266 // To support Mid$()
4267 : primary_expression opt_dolar_sign OPEN_PARENS opt_argument_list _mark_ CLOSE_PARENS
4270 Location l = (Location)$5;
4271 Report.Error (1, l, "THIS IS CRAZY");
4273 $$ = new Invocation ((Expression) $1, (ArrayList) $4, (Location)$5);
4274 // Console.WriteLine ("Invocation: {0} with {1} arguments", $1, ($4 != null) ? ((ArrayList) $4).Count : 0);
4276 | CALL primary_expression OPEN_PARENS opt_argument_list _mark_ CLOSE_PARENS
4279 Location l = (Location)$5;
4280 Report.Error (1, l, "THIS IS CRAZY");
4282 $$ = new Invocation ((Expression) $2, (ArrayList) $3, (Location)$5);
4283 // Console.WriteLine ("Invocation: {0} with {1} arguments", $2, ($3 != null) ? ((ArrayList) $3).Count : 0);
4285 | primary_expression EXCLAMATION _mark_ identifier // FIXME : This should be identifier-or-keyword
4288 Location l = (Location)$3;
4289 Report.Error (1, l, "THIS IS CRAZY");
4292 ArrayList args = new ArrayList ();
4293 Expression etmp = new StringLiteral ((string)$4);
4295 args.Add (new Argument (etmp, Argument.AType.Expression));
4296 $$ = new Invocation ((Expression) $1, args, (Location)$3);
4306 : MYBASE DOT IDENTIFIER
4308 string id_name = (string) $3;
4309 if (id_name.ToUpper() == "NEW")
4311 $$ = new BaseAccess (id_name, lexer.Location);
4315 $$ = new BaseAccess ("New", lexer.Location);
4323 The 'argument' rule returns an 'empty' argument
4324 of type NoArg (used for default arguments in invocations)
4325 if no arguments are actually passed.
4327 If there is only one argument and it is o type NoArg,
4328 we return a null (empty) list
4330 ArrayList args = (ArrayList) $1;
4331 if (args.Count == 1 &&
4332 ((Argument)args[0]).ArgType == Argument.AType.NoArg)
4342 ArrayList list = new ArrayList ();
4346 | argument_list COMMA argument
4348 ArrayList list = (ArrayList) $1;
4357 $$ = new Argument ((Expression) $1, Argument.AType.Expression);
4359 | BYREF variable_reference
4361 $$ = new Argument ((Expression) $2, Argument.AType.Ref);
4365 $$ = new Argument (new EmptyExpression (), Argument.AType.NoArg);
4367 | ADDRESSOF expression
4369 $$ = new Argument ((Expression) $2, Argument.AType.AddressOf);
4371 | identifier ATTR_ASSIGN expression
4373 $$ = new Argument ((string) $1, (Expression) $3, Argument.AType.Expression);
4378 : expression {/* note ("section 5.4"); */ $$ = $1; }
4383 : conditional_xor_expression { $$ = $1; }
4384 /*| assignment_expression*/
4395 $$ = new This (current_block, lexer.Location);
4399 $$ = new This (This.TypeOfAccess.MyClass, current_block, lexer.Location);
4404 : DIRECTCAST OPEN_PARENS expression COMMA type CLOSE_PARENS
4408 | CTYPE OPEN_PARENS expression COMMA type CLOSE_PARENS
4410 $$ = new Cast ((Expression) $5, (Expression) $3, lexer.Location);
4412 | cast_operator OPEN_PARENS expression CLOSE_PARENS
4414 $$ = new Cast ((Expression) $1, (Expression) $3, lexer.Location);
4419 : CBOOL { $$ = TypeManager.system_boolean_expr; }
4420 | CBYTE { $$ = TypeManager.system_byte_expr; }
4421 | CCHAR { $$ = TypeManager.system_char_expr; }
4422 | CDATE { $$ = TypeManager.system_date_expr; }
4423 | CDBL { $$ = TypeManager.system_double_expr; }
4424 | CDEC { $$ = TypeManager.system_decimal_expr; }
4425 | CINT { $$ = TypeManager.system_int32_expr; }
4426 | CLNG { $$ = TypeManager.system_int64_expr; }
4427 | COBJ { $$ = TypeManager.system_object_expr; }
4428 | CSHORT { $$ = TypeManager.system_int16_expr; }
4429 | CSNG { $$ = TypeManager.system_single_expr; }
4430 | CSTR { $$ = TypeManager.system_string_expr; }
4434 : GETTYPE OPEN_PARENS _mark_ type CLOSE_PARENS
4436 $$ = new TypeOf ((Expression) $4, (Location)$3);
4440 exponentiation_expression
4441 : prefixed_unary_expression
4442 | exponentiation_expression OP_EXP _mark_ primary_expression
4444 $$ = new Binary (Binary.Operator.Exponentiation,
4445 (Expression) $1, (Expression) $4, (Location)$3);
4449 prefixed_unary_expression
4450 : primary_expression
4451 | PLUS _mark_ prefixed_unary_expression
4453 //FIXME: Is this rule correctly defined ?
4454 $$ = new Unary (Unary.Operator.UnaryPlus, (Expression) $3, (Location)$2);
4456 | MINUS _mark_ prefixed_unary_expression
4458 //FIXME: Is this rule correctly defined ?
4459 $$ = new Unary (Unary.Operator.UnaryNegation, (Expression) $3, (Location)$2);
4463 multiplicative_expression
4464 : exponentiation_expression
4465 | multiplicative_expression STAR _mark_ prefixed_unary_expression
4467 $$ = new Binary (Binary.Operator.Multiply,
4468 (Expression) $1, (Expression) $4, (Location)$3);
4470 | multiplicative_expression DIV _mark_ prefixed_unary_expression
4472 $$ = new Binary (Binary.Operator.Division,
4473 (Expression) $1, (Expression) $4, (Location)$3);
4477 integer_division_expression
4478 : multiplicative_expression
4479 | integer_division_expression OP_IDIV _mark_ multiplicative_expression
4481 //FIXME: Is this right ?
4482 $$ = new Binary (Binary.Operator.IntDivision,
4483 (Expression) $1, (Expression) $4, (Location)$3);
4488 : integer_division_expression
4489 | mod_expression MOD _mark_ integer_division_expression
4491 $$ = new Binary (Binary.Operator.Modulus,
4492 (Expression) $1, (Expression) $4, (Location)$3);
4498 | additive_expression PLUS _mark_ mod_expression
4500 $$ = new Binary (Binary.Operator.Addition,
4501 (Expression) $1, (Expression) $4, (Location)$3);
4503 | additive_expression MINUS _mark_ mod_expression
4505 $$ = new Binary (Binary.Operator.Subtraction,
4506 (Expression) $1, (Expression) $4, (Location)$3);
4511 : additive_expression
4512 | concat_expression OP_CONCAT _mark_ additive_expression
4514 // FIXME: This should only work for String expressions
4515 // We probably need to use something from the runtime
4516 $$ = new StringConcat((Location)$3,
4517 (Expression) $1, (Expression) $4);
4524 | shift_expression OP_SHIFT_LEFT _mark_ concat_expression
4526 $$ = new Binary(Binary.Operator.LeftShift, (Expression) $1, (Expression) $4, (Location)$3);
4528 | shift_expression OP_SHIFT_RIGHT _mark_ concat_expression
4530 $$ = new Binary(Binary.Operator.RightShift, (Expression) $1, (Expression) $4, (Location)$3);
4534 relational_expression
4536 | relational_expression LIKE _mark_ shift_expression
4538 $$ = new Binary (Binary.Operator.Like,
4539 (Expression) $1, (Expression) $4, (Location)$3);
4541 | relational_expression ASSIGN _mark_ shift_expression
4543 $$ = new Binary (Binary.Operator.Equality,
4544 (Expression) $1, (Expression) $4, (Location)$3);
4546 | relational_expression OP_NE _mark_ shift_expression
4548 $$ = new Binary (Binary.Operator.Inequality,
4549 (Expression) $1, (Expression) $4, (Location)$3);
4551 | relational_expression OP_LT _mark_ shift_expression
4553 $$ = new Binary (Binary.Operator.LessThan,
4554 (Expression) $1, (Expression) $4, (Location)$3);
4556 | relational_expression OP_GT _mark_ shift_expression
4558 $$ = new Binary (Binary.Operator.GreaterThan,
4559 (Expression) $1, (Expression) $4, (Location)$3);
4561 | relational_expression OP_LE _mark_ shift_expression
4563 $$ = new Binary (Binary.Operator.LessThanOrEqual,
4564 (Expression) $1, (Expression) $4, (Location)$3);
4566 | relational_expression OP_GE _mark_ shift_expression
4568 $$ = new Binary (Binary.Operator.GreaterThanOrEqual,
4569 (Expression) $1, (Expression) $4, (Location)$3);
4571 | relational_expression IS _mark_ shift_expression
4573 $$ = new Binary (Binary.Operator.Is,
4574 (Expression) $1, (Expression) $4, (Location)$3);
4576 | TYPEOF shift_expression _mark_ IS type
4578 //FIXME: Is this rule correctly defined ?
4579 $$ = new Is ((Expression) $2, (Expression) $5, (Location)$3);
4584 : relational_expression
4585 | NOT _mark_ negation_expression
4587 //FIXME: Is this rule correctly defined ?
4588 $$ = new Unary (Unary.Operator.LogicalNot, (Expression) $3, (Location)$2);
4592 conditional_and_expression
4593 : negation_expression
4594 | conditional_and_expression AND _mark_ negation_expression
4596 $$ = new Binary (Binary.Operator.BitwiseAnd,
4597 (Expression) $1, (Expression) $4, (Location)$3);
4599 | conditional_and_expression ANDALSO _mark_ negation_expression
4600 { // FIXME: this is likely to be broken
4601 $$ = new Binary (Binary.Operator.LogicalAnd,
4602 (Expression) $1, (Expression) $4, (Location)$3);
4606 conditional_or_expression
4607 : conditional_and_expression
4608 | conditional_or_expression OR _mark_ conditional_and_expression
4610 $$ = new Binary (Binary.Operator.BitwiseOr,
4611 (Expression) $1, (Expression) $4, (Location)$3);
4613 | conditional_or_expression ORELSE _mark_ conditional_and_expression
4614 { // FIXME: this is likely to be broken
4615 $$ = new Binary (Binary.Operator.LogicalOr,
4616 (Expression) $1, (Expression) $4, (Location)$3);
4620 conditional_xor_expression
4621 : conditional_or_expression
4622 | conditional_xor_expression XOR _mark_ conditional_or_expression
4624 $$ = new Binary (Binary.Operator.ExclusiveOr,
4625 (Expression) $1, (Expression) $4, (Location)$3);
4629 assignment_expression
4630 : prefixed_unary_expression ASSIGN _mark_ expression
4632 $$ = new Assign ((Expression) $1, (Expression) $4, (Location)$3);
4634 | prefixed_unary_expression OP_EXP ASSIGN _mark_ expression
4636 Location l = (Location)$4;
4637 $$ = new CompoundAssign (
4638 Binary.Operator.Exponentiation, (Expression) $1, (Expression) $5, l);
4640 | prefixed_unary_expression STAR ASSIGN _mark_ expression
4642 Location l = (Location)$4;
4643 $$ = new CompoundAssign (
4644 Binary.Operator.Multiply, (Expression) $1, (Expression) $5, l);
4646 | prefixed_unary_expression DIV ASSIGN _mark_ expression
4648 Location l = (Location)$4;
4649 $$ = new CompoundAssign (
4650 Binary.Operator.Division, (Expression) $1, (Expression) $5, l);
4652 | prefixed_unary_expression PLUS ASSIGN _mark_ expression
4654 Location l = (Location)$4;
4655 $$ = new CompoundAssign (
4656 Binary.Operator.Addition, (Expression) $1, (Expression) $5, l);
4658 | prefixed_unary_expression MINUS ASSIGN _mark_ expression
4660 Location l = (Location)$4;
4661 $$ = new CompoundAssign (
4662 Binary.Operator.Subtraction, (Expression) $1, (Expression) $5, l);
4664 | prefixed_unary_expression OP_SHIFT_LEFT ASSIGN _mark_ expression
4666 Location l = (Location)$4;
4667 $$ = new CompoundAssign (
4668 Binary.Operator.LeftShift, (Expression) $1, (Expression) $5, l);
4670 | prefixed_unary_expression OP_SHIFT_RIGHT ASSIGN _mark_ expression
4672 Location l = (Location)$4;
4673 $$ = new CompoundAssign (
4674 Binary.Operator.RightShift, (Expression) $1, (Expression) $5, l);
4676 | prefixed_unary_expression OP_CONCAT ASSIGN _mark_ expression
4678 Location l = (Location)$4;
4680 // FIXME should be strings only
4681 $$ = new CompoundAssign (
4682 Binary.Operator.Addition, (Expression) $1, (Expression) $5, l);
4684 | prefixed_unary_expression ASSIGN ADDRESSOF _mark_ expression
4686 ArrayList args = new ArrayList();
4687 Argument arg = new Argument ((Expression) $5, Argument.AType.Expression);
4690 New n = new New ((Expression) $1, (ArrayList) args, (Location)$4);
4691 n.isDelegate = true;
4692 $$ = new Assign ((Expression) $1, (Expression) n, (Location)$4);
4703 Expression expr = (Expression) $1;
4704 expr = SetValueRequiredFlag (expr);
4710 : namespace_or_type_name
4712 $$ = DecomposeQI ((string) $1, lexer.Location);
4721 ArrayList types = new ArrayList ();
4726 | type_list COMMA type
4728 ArrayList types = (ArrayList) $1;
4735 namespace_or_type_name
4736 : qualified_identifier
4740 : OBJECT { $$ = TypeManager.system_object_expr; }
4746 | BOOLEAN { $$ = TypeManager.system_boolean_expr; }
4747 | DATE { $$ = TypeManager.system_date_expr; }
4748 | CHAR { $$ = TypeManager.system_char_expr; }
4749 | STRING { $$ = TypeManager.system_string_expr; }
4755 | floating_point_type
4756 | DECIMAL { $$ = TypeManager.system_decimal_expr; }
4761 | BYTE { $$ = TypeManager.system_byte_expr; }
4762 | SHORT { $$ = TypeManager.system_int16_expr; }
4763 | INTEGER { $$ = TypeManager.system_int32_expr; }
4764 | LONG { $$ = TypeManager.system_int64_expr; }
4768 : SINGLE { $$ = TypeManager.system_single_expr; }
4769 | DOUBLE { $$ = TypeManager.system_double_expr; }
4774 | constant_expression _mark_ //FIXME: Fix for binary expression
4776 Expression exp = (Expression) $1;
4777 if(exp is SimpleName) {
4778 string key = ((SimpleName)exp).Name;
4779 if(constPreDir.Contains(key)) {
4780 $$ = new BoolLiteral ((bool)constPreDir [key]);
4784 object o = ((Constant) exp).GetValue ();
4785 bool temp = Convert.ToBoolean(o);
4786 $$ = new BoolLiteral ((bool)temp);
4787 // Report.Error (30580, (Location)$2, "value of Const used is not set");
4793 : HASH IDENTIFIER OPEN_PARENS LITERAL_STRING COMMA LITERAL_INTEGER CLOSE_PARENS _mark_ EOL
4795 if(tokenizerController.IsAcceptingTokens)
4797 if(in_external_source)
4798 Report.Error (30580, (Location)$8, "#ExternalSource directives may not be nested");
4800 in_external_source = true;
4802 lexer.EffectiveSource = (string) $4;
4803 lexer.EffectiveLine = (int) $6;
4807 | HASH IDENTIFIER LITERAL_STRING _mark_ EOL
4809 if(tokenizerController.IsAcceptingTokens)
4811 if(!($2 as string).ToLower().Equals("region"))
4812 Report.Error (30205, (Location)$4, "Invalid Pre-processor directive");
4819 | HASH END IDENTIFIER _mark_ EOL
4821 if(tokenizerController.IsAcceptingTokens)
4823 if( ($3 as string).ToLower().Equals("externalsource")) {
4824 if(!in_external_source)
4825 Report.Error (30578, (Location)$4, "'#End ExternalSource' must be preceded by a matching '#ExternalSource'");
4827 in_external_source = false;
4828 lexer.EffectiveSource = lexer.Source;
4829 lexer.EffectiveLine = lexer.Line;
4832 else if(($3 as string).ToLower().Equals("region")) {
4833 if(in_marked_region > 0)
4836 Report.Error (30205, (Location)$4, "'#End Region' must be preceded by a matching '#Region'");
4839 Report.Error (29999, (Location)$4, "Unrecognized Pre-Processor statement");
4843 | HASH CONST IDENTIFIER ASSIGN constant_expression _mark_ EOL
4846 Expression express = (Expression) $5;
4847 if (express is Binary) {
4851 object o = ((Constant) express).GetValue ();
4852 bool temp = Convert.ToBoolean(o);
4853 constPreDir.Add($3,temp);
4858 IfElseStateMachine.Token tok = IfElseStateMachine.Token.IF;
4861 ifElseStateMachine.HandleToken(tok);
4863 catch(ApplicationException) {
4864 throw new MBASException(ifElseStateMachine.Error, (Location)$3, ifElseStateMachine.ErrString);
4867 directive_exp opt_then EOL
4869 //FIXME: Fix for constant expression
4871 HandleConditionalDirective(IfElseStateMachine.Token.IF, (BoolLiteral)$5);
4873 | HASH opt_elseif _mark_
4875 IfElseStateMachine.Token tok = IfElseStateMachine.Token.ELSEIF;
4877 ifElseStateMachine.HandleToken(tok);
4879 catch(ApplicationException) {
4880 throw new MBASException(ifElseStateMachine.Error, (Location)$3, ifElseStateMachine.ErrString);
4883 directive_exp opt_then EOL
4885 //FIXME: Fix for constant expression
4887 HandleConditionalDirective(IfElseStateMachine.Token.ELSEIF, (BoolLiteral)$5);
4891 IfElseStateMachine.Token tok = IfElseStateMachine.Token.ELSE;
4893 ifElseStateMachine.HandleToken(tok);
4895 catch(ApplicationException) {
4896 throw new MBASException(ifElseStateMachine.Error, (Location)$3, ifElseStateMachine.ErrString);
4901 HandleConditionalDirective(IfElseStateMachine.Token.ELSE, new BoolLiteral(true));
4903 | HASH END IF _mark_
4905 /*FIXME: IF without ENDIF not working properly. Error line is not diplayed properly*/
4907 IfElseStateMachine.Token tok = IfElseStateMachine.Token.ENDIF;
4909 ifElseStateMachine.HandleToken(tok);
4911 catch(ApplicationException) {
4912 throw new MBASException(ifElseStateMachine.Error, (Location)$4, ifElseStateMachine.ErrString);
4917 HandleConditionalDirective(IfElseStateMachine.Token.ENDIF, new BoolLiteral(false));
4919 | HASH error _mark_ EOL
4921 if(tokenizerController.IsAcceptingTokens)
4922 Report.Error(29999, (Location)$3, "Unrecognized Pre-Processor statement");
4924 Report.Warning (29999, (Location)$3,"Unrecognized Pre-Processor statement");
4929 // Utility rule to save location information
4932 { $$ = lexer.Location; if (yyToken == Token.EOL) { $$ = new Location (lexer.Location.Row - 1, lexer.Location.Col); } }
4935 // Changed to accept "Else If" also along with "ElseIf"
4941 // Changed so as to check if every block is closed or not...
4990 /*In case of any new end block please add it here.. after END_GET as single token... and please continue the numbering from 17...*/
4998 public Tokenizer Lexer {
5004 public static Expression DecomposeQI (string name, Location loc)
5008 if (name.IndexOf ('.') == -1){
5009 return new SimpleName (name, loc);
5011 int pos = name.LastIndexOf (".");
5012 string left = name.Substring (0, pos);
5013 string right = name.Substring (pos + 1);
5015 o = DecomposeQI (left, loc);
5017 return new MemberAccess (o, right, loc);
5021 Block declare_local_variables (Expression dummy_type, ArrayList variable_declarators, Location loc)
5023 Block implicit_block;
5024 ArrayList inits = null;
5027 // We use the `Used' property to check whether statements
5028 // have been added to the current block. If so, we need
5029 // to create another block to contain the new declaration
5030 // otherwise, as an optimization, we use the same block to
5031 // add the declaration.
5033 // FIXME: A further optimization is to check if the statements
5034 // that were added were added as part of the initialization
5035 // below. In which case, no other statements have been executed
5036 // and we might be able to reduce the number of blocks for
5037 // situations like this:
5039 // int j = 1; int k = j + 1;
5042 VariableDeclaration.FixupTypes (variable_declarators);
5044 if (current_block.Used) {
5045 implicit_block = new Block (current_block, true, loc, Location.Null);
5046 implicit_block.AddChildVariableNames (current_block);
5048 implicit_block = current_block;
5050 foreach (VariableDeclaration decl in variable_declarators){
5051 Expression type = decl.type;
5052 if (implicit_block.AddVariable (type, decl.identifier, current_local_parameters, loc) != null) {
5053 if (decl.expression_or_array_initializer != null){
5055 inits = new ArrayList ();
5062 return implicit_block;
5064 foreach (VariableDeclaration decl in inits){
5067 Expression type = decl.type;
5069 if ((decl.expression_or_array_initializer is Expression) ||
5070 (decl.expression_or_array_initializer is New)) {
5071 expr = (Expression) decl.expression_or_array_initializer;
5073 ArrayList init = (ArrayList) decl.expression_or_array_initializer;
5075 expr = new ArrayCreation (type, "", init, decl.Location);
5078 LocalVariableReference var;
5079 var = new LocalVariableReference (implicit_block, decl.identifier, loc);
5081 assign = new Assign (var, expr, decl.Location);
5083 implicit_block.AddStatement (new StatementExpression (assign, lexer.Location));
5086 return implicit_block;
5089 Block declare_local_constant (Expression dummy_type, ArrayList variable_declarators)
5091 Block implicit_block;
5092 VariableDeclaration.FixupTypes (variable_declarators);
5094 if (current_block.Used)
5095 implicit_block = new Block (current_block, true);
5097 implicit_block = current_block;
5099 foreach (VariableDeclaration decl in variable_declarators){
5100 Expression type = decl.type;
5101 implicit_block.AddConstant (type, decl.identifier, (Expression) decl.expression_or_array_initializer,
5102 current_local_parameters, decl.Location);
5105 return implicit_block;
5113 public VarName (object n, object t, object r)
5123 // A class used to pass around variable declarations and constants
5125 public class VariableDeclaration {
5126 public string identifier;
5127 public object expression_or_array_initializer;
5128 public Location Location;
5129 public Attributes OptAttributes;
5130 public Expression type;
5131 public ArrayList dims;
5133 public VariableDeclaration (string id, Expression t, object eoai, Location l, Attributes opt_attrs)
5135 this.identifier = id;
5136 this.expression_or_array_initializer = eoai;
5138 this.OptAttributes = opt_attrs;
5143 public VariableDeclaration (string id, object eoai, Location l) : this (id, eoai, l, null)
5147 public VariableDeclaration (string id, Expression t, Location l) : this (id, t, null, l, null)
5151 public VariableDeclaration (string id, object eoai, Location l, Attributes opt_attrs) : this
5152 (id, TypeManager.system_object_expr, eoai, l, opt_attrs)
5156 public static ArrayCreation BuildArrayCreator (Expression vartype, ArrayList a_dims, ArrayList varinit, Location l)
5158 // FIXME : This is broken: only the first rank is parsed
5159 return new ArrayCreation (vartype, (ArrayList) a_dims[0], "", varinit, l);
5162 public static void FixupTypes (ArrayList vars)
5164 int varcount = vars.Count;
5165 VariableDeclaration last_var = (VariableDeclaration) vars[varcount - 1];
5167 if (last_var.type == null)
5168 last_var.type = TypeManager.system_object_expr;
5170 Expression cur_type = last_var.type;
5171 int n = varcount - 1;
5174 VariableDeclaration var = (VariableDeclaration) vars[n--];
5175 if (var.type == null)
5176 var.type = cur_type;
5178 cur_type = var.type;
5182 public static bool IndexesSpecifiedInRank (ArrayList IndexList)
5186 if (IndexList != null) {
5187 foreach (Expression e in IndexList)
5188 if (!(e is EmptyExpression)) {
5197 public static bool IndexesSpecified (ArrayList ranks)
5201 if (ranks != null) {
5202 foreach (ArrayList IndexList in ranks) {
5203 if (IndexesSpecifiedInRank (IndexList)) {
5212 public static string StripDims (string varname, ref string d)
5214 string res = varname;
5217 if (varname.IndexOf("[") >= 0) {
5218 dres = varname.Substring(varname.IndexOf("["), (varname.LastIndexOf("]") - varname.IndexOf("["))+1);
5219 res = varname.Substring(0, varname.IndexOf("["));
5225 public static string StripDims (string varname)
5229 return (StripDims(varname, ref dres));
5232 public static string StripIndexesFromDims (string dims)
5234 StringBuilder sb = new StringBuilder();
5236 foreach (char c in dims)
5237 if (c == ',' || c == ']' || c == '[')
5240 return sb.ToString();
5243 public static string BuildRank (ArrayList rank)
5246 return BuildRank(rank, out allEmpty);
5249 public static string BuildRank (ArrayList rank, out bool allEmpty)
5256 foreach (object e in rank) {
5257 if (!(e is EmptyExpression))
5268 public static string BuildRanks (ArrayList rank_specifiers, bool mustBeEmpty, Location loc)
5272 bool allEmpty = true;
5273 foreach (ArrayList rank in rank_specifiers) {
5275 res = BuildRank (rank, out tmp) + res;
5279 if (!allEmpty && mustBeEmpty)
5280 Report.Error (30638, loc, "Array bounds cannot appear in type specifiers.");
5285 public static void VBFixIndexList (ref ArrayList IndexList)
5287 if (IndexList != null) {
5288 for (int x = 0; x < IndexList.Count; x++) {
5289 Expression e = (Expression) IndexList[x];
5290 if (!(e is EmptyExpression)) {
5291 IndexList[x] = new Binary (Binary.Operator.Addition, e, new IntLiteral(1), Location.Null);
5297 public static bool IsArrayDecl (Parser t)
5299 // return (varname.IndexOf("[") >= 0);
5300 return (t.current_rank_specifiers != null);
5303 public static void VBFixIndexLists (ref ArrayList ranks)
5305 if (ranks != null) {
5306 for (int x = 0; x < ranks.Count; x++) {
5307 ArrayList IndexList = (ArrayList) ranks[x];
5308 VBFixIndexList (ref IndexList);
5313 public static void FixupArrayTypes (ArrayList vars)
5317 foreach (VariableDeclaration var in vars) {
5318 if (var.identifier.EndsWith(",")) {
5319 dims = "[" + var.identifier.Substring(var.identifier.IndexOf (","),
5320 var.identifier.LastIndexOf(",")) + "]";
5321 var.identifier = var.identifier.Substring (0, var.identifier.IndexOf (","));
5322 var.type = new ComposedCast (var.type, (string) dims, var.Location);
5329 public Property BuildSimpleProperty (Expression p_type, string name,
5330 Field p_fld, int mod_flags,
5331 Attributes attrs, Location loc)
5334 Block get_block, set_block;
5335 Accessor acc_set, acc_get;
5336 StatementExpression a_set;
5341 Parameter implicit_value_parameter = new Parameter (p_type, "value", Parameter.Modifier.NONE, null);
5342 args = new Parameter [1];
5343 args [0] = implicit_value_parameter;
5345 Parameters set_params = new Parameters (args, null, loc);
5346 a_set = new StatementExpression ((ExpressionStatement) new Assign ((Expression) DecomposeQI(p_fld.Name, loc),
5347 (Expression) new SimpleName("value", loc), loc), loc);
5349 set_block = new Block (current_block, set_params, loc, Location.Null);
5350 set_block.AddStatement ((Statement) a_set);
5351 acc_set = new Accessor (set_block, attrs);
5354 a_get = (Statement) new Return ((Expression) DecomposeQI(p_fld.Name, loc), loc);
5355 get_block = new Block (current_block, null, loc, Location.Null);
5356 get_block.AddStatement ((Statement) a_get);
5357 acc_get = new Accessor (get_block, attrs);
5359 p = new Property (p_type, name, mod_flags, (Accessor) acc_get, (Accessor) acc_set, attrs, loc);
5366 current_block = new Block (current_block, current_local_parameters,
5367 lexer.Location, Location.Null);
5374 while (current_block.Implicit)
5375 current_block = current_block.Parent;
5377 res = current_block;
5379 current_block.SetEndLocation (lexer.Location);
5380 current_block = current_block.Parent;
5385 void push_into_stack(int BlockStart, Location l)
5387 end_of_block.Push(BlockStart);
5388 loc_end_of_block.Push(l);
5391 void pop_out_of_stack(int BlockEnd, Location l)
5393 if(BlockEnd != Token.EOF) {
5394 int current = (int)end_of_block.Pop();
5395 Location current_loc = (Location)loc_end_of_block.Pop();
5396 if(BlockEnd != current) {
5397 // Block end is missing
5398 // eg: For 'Sub' BlockEnd should be 'End Sub'
5400 if(error_end_blocks[BlockEnd,2] > error_end_blocks[current,2]) {
5401 while(error_end_blocks[BlockEnd,2] > error_end_blocks[current,2])
5403 if(error_end_blocks[BlockEnd,2] > error_end_blocks[current,2])
5404 Report.Error(error_end_blocks[current,0],current_loc,"'"+end_blocks[current,0]+"' is not having matching '"+end_blocks[current,1]+"'");
5405 current = (int)end_of_block.Pop();
5406 current_loc = (Location)loc_end_of_block.Pop();
5410 // Extra end is present, but works for lesser priority
5411 // (for priority see opt_end_block opt_block_types return values
5412 // eg: 'EndIf' without 'If' inside 'Sub'
5413 // Also certain other errors like 'Sub' having a 'End Module' etc
5414 // can be handled here
5416 if(error_end_blocks[BlockEnd,2] < error_end_blocks[current,2]) {
5417 Report.Error(error_end_blocks[BlockEnd,1],l,"'"+end_blocks[BlockEnd,1]+"' is not having a corresponding '"+end_blocks[BlockEnd,0]+"'");
5418 end_of_block.Push(current);
5419 loc_end_of_block.Push(current_loc);
5421 // Extra end is present but with equal priorty
5423 if((error_end_blocks[BlockEnd,2] == error_end_blocks[current,2]) && BlockEnd != current) {
5424 while((error_end_blocks[BlockEnd,2] == error_end_blocks[current,2]) && BlockEnd != current) {
5425 temp_block.Push(current);
5426 loc_temp_block.Push(current_loc);
5427 current = (int)end_of_block.Pop();
5428 current_loc = (Location)loc_end_of_block.Pop();
5431 if(BlockEnd == current) {
5432 while(temp_block.Count !=0)
5434 int lapse = (int) temp_block.Pop();
5435 Location lapse_location = (Location)loc_temp_block.Pop();
5436 Report.Error(error_end_blocks[lapse,0],lapse_location,"'"+end_blocks[lapse,0]+"' is not having matching '"+end_blocks[lapse,1]+"'");
5441 Report.Error(error_end_blocks[BlockEnd,1],l,"'"+end_blocks[BlockEnd,1]+"' is not having a corresponding '"+end_blocks[BlockEnd,0]+"'");
5442 end_of_block.Push(current);
5443 loc_end_of_block.Push(current_loc);
5444 while(temp_block.Count !=0) {
5445 int lapse = (int) temp_block.Pop();
5446 Location lapse_location = (Location)loc_temp_block.Pop();
5447 end_of_block.Push(lapse);
5448 loc_end_of_block.Push(lapse_location);
5455 while(end_of_block.Count !=0) {
5456 int lapse = (int) end_of_block.Pop();
5457 Location lapse_location = (Location)loc_end_of_block.Pop();
5458 Report.Error(error_end_blocks[lapse,0],lapse_location,"'"+end_blocks[lapse,0]+"' is not having matching '"+end_blocks[lapse,1]+"'");
5463 private void AddHandler (Expression evt_definition, Expression handler_exp)
5465 AddHandler (current_block, evt_definition, handler_exp);
5468 void CheckAttributeTarget (string a)
5472 case "assembly" : case "field" : case "method" : case "param" : case "property" : case "type" :
5476 Location l = lexer.Location;
5477 Report.Error (658, l, "`" + a + "' is an invalid attribute target");
5482 private void AddHandler (Block b, Expression evt_id, Expression handles_exp)
5484 Location loc = lexer.Location;
5486 Statement addhnd = (Statement) new AddHandler (evt_id,
5489 b.AddStatement (addhnd);
5492 private void RaiseEvent (string evt_name, ArrayList args)
5494 Location loc = lexer.Location;
5496 Invocation evt_call = new Invocation (DecomposeQI(evt_name, loc), args, lexer.Location);
5497 Statement s = (Statement)(new StatementExpression ((ExpressionStatement) evt_call, loc));
5498 current_block.AddStatement (s);
5501 private void RemoveHandler (Block b, Expression evt_definition, Expression handler_exp)
5503 Location loc = lexer.Location;
5505 Statement rmhnd = (Statement) new RemoveHandler (evt_definition,
5508 b.AddStatement (rmhnd);
5512 // This method is used to get at the complete string representation of
5513 // a fully-qualified type name, hiding inside a MemberAccess ;-)
5514 // This is necessary because local_variable_type admits primary_expression
5515 // as the type of the variable. So we do some extra checking
5517 string GetQualifiedIdentifier (Expression expr)
5519 if (expr is SimpleName)
5520 return ((SimpleName)expr).Name;
5521 else if (expr is MemberAccess)
5522 return GetQualifiedIdentifier (((MemberAccess)expr).Expr) + "." + ((MemberAccess) expr).Identifier;
5524 throw new Exception ("Expr has to be either SimpleName or MemberAccess! (" + expr + ")");
5528 private void RemoveHandler (Expression evt_definition, Expression handler_exp)
5530 RemoveHandler (current_block, evt_definition, handler_exp);
5533 private ConstructorInitializer CheckConstructorInitializer (ref ArrayList s)
5535 ConstructorInitializer ci = null;
5538 if (s[0] is StatementExpression && ((StatementExpression) s[0]).expr is Invocation) {
5539 Invocation i = (Invocation) ((StatementExpression) s[0]).expr;
5541 if (i.expr is BaseAccess) {
5542 BaseAccess ba = (BaseAccess) i.expr;
5543 if (ba.member == "New" || ba.member == ".ctor") {
5544 ci = new ConstructorBaseInitializer (i.Arguments, current_local_parameters, lexer.Location);
5548 if (i.expr.ToString() == "Mono.MonoBASIC.This..ctor") {
5549 ci = new ConstructorThisInitializer (i.Arguments, current_local_parameters, lexer.Location);
5557 void Error_ExpectingTypeName (Location l, Expression expr)
5559 if (expr is Invocation){
5560 Report.Error (1002, l, "; expected");
5562 Report.Error (-1, l, "Invalid Type definition");
5566 public static Expression SetLeftHandFlag (Expression expr) {
5567 if (expr is Invocation) {
5568 Invocation e = (Invocation) expr;
5569 e.IsLeftHand = true;
5571 } else if (expr is MemberAccess) {
5572 MemberAccess e = (MemberAccess) expr;
5573 e.IsLeftHand = true;
5580 public static Expression SetValueRequiredFlag (Expression expr) {
5581 if (expr is Invocation) {
5582 Invocation e = (Invocation) expr;
5583 e.IsRetvalRequired = true;
5587 if (expr is Binary) {
5588 Binary binary = (Binary) expr;
5589 binary.Left = SetValueRequiredFlag (binary.Left);
5590 binary.Right = SetValueRequiredFlag (binary.Right);
5593 if (expr is Unary) {
5594 Unary unary = (Unary) expr;
5595 unary.Expr = SetValueRequiredFlag (unary.Expr);
5601 static bool AlwaysAccept (MemberInfo m, object filterCriteria) {
5605 private void ReportError9998()
5607 Report.Error (29998, lexer.Location, "This construct is only available in MonoBASIC extended syntax.");
5610 protected override int parse ()
5612 RootContext.InitializeImports(ImportsList);
5613 current_namespace = new Namespace (null, RootContext.RootNamespace);
5614 current_container = RootContext.Tree.Types;
5615 current_container.Namespace = current_namespace;
5616 oob_stack = new Stack ();
5617 switch_stack = new Stack ();
5618 expr_stack = new Stack ();
5619 tmp_blocks = new Stack();
5620 with_stack = new Stack();
5621 statement_stack = new Stack();
5622 end_of_block = new Stack ();
5623 loc_end_of_block = new Stack ();
5624 temp_block = new Stack();
5625 loc_temp_block = new Stack();
5627 allow_global_attribs = true;
5628 expecting_global_attribs = false;
5629 expecting_local_attribs = false;
5630 local_attrib_section_added = false;
5632 UseExtendedSyntax = name.EndsWith(".mbs");
5633 OptionExplicit = InitialOptionExplicit || UseExtendedSyntax;
5634 OptionStrict = InitialOptionStrict || UseExtendedSyntax;
5635 OptionCompareBinary = InitialOptionCompareBinary;
5637 lexer = new Tokenizer (input, name, defines);
5639 ifElseStateMachine = new IfElseStateMachine();
5640 tokenizerController = new TokenizerController(lexer);
5643 if (yacc_verbose_flag > 0)
5644 yyparse (lexer, new yydebug.yyDebugSimple ());
5650 catch(MBASException e) {
5651 Report.Error(e.code, e.loc, e.Message);
5653 catch (Exception e) {
5654 if (Report.Stacktrace)
5655 Console.WriteLine(e);
5656 Report.Error (29999, lexer.Location, "Parsing error");
5659 RootContext.VerifyImports();
5661 return Report.Errors;
5667 ifElseStateMachine.HandleToken(IfElseStateMachine.Token.EOF);
5669 catch(ApplicationException) {
5670 throw new MBASException(ifElseStateMachine.Error, lexer.Location, ifElseStateMachine.ErrString);
5673 if(in_external_source)
5674 Report.Error (30579, lexer.Location, "'#ExternalSource' directives must end with matching '#End ExternalSource'");
5676 if(in_marked_region > 0)
5677 Report.Error (30205, lexer.Location, "'#Region' directive must be followed by a matching '#End Region'");
5680 void HandleConditionalDirective(IfElseStateMachine.Token tok, BoolLiteral expr)
5683 tokenizerController.PositionTokenizerCursor(tok, expr);
5685 catch(ApplicationException) {
5686 tok = IfElseStateMachine.Token.EOF;
5688 ifElseStateMachine.HandleToken(tok);
5690 catch(ApplicationException) {
5691 throw new MBASException(ifElseStateMachine.Error, lexer.Location, ifElseStateMachine.ErrString);