Mercurial > hg > octave-nkf
comparison libinterp/parse-tree/oct-parse.in.yy @ 16287:04a7953496a7
create base class for parser; use reference for curr_lexer
* lex.h, lex.ll (octave_base_parser): New base class for parser
class. Move most of previous octave_parser class here. Use reference
for curr_lexer object instead of pointer. Change all uses.
(octave_parser): Derive from octave_base_parser.
author | John W. Eaton <jwe@octave.org> |
---|---|
date | Tue, 12 Mar 2013 00:18:28 -0400 |
parents | 3389152014ca |
children | fe3b9a51e625 |
comparison
equal
deleted
inserted
replaced
16285:3389152014ca | 16287:04a7953496a7 |
---|---|
105 static std::map<std::string, std::string> autoload_map; | 105 static std::map<std::string, std::string> autoload_map; |
106 | 106 |
107 // Forward declarations for some functions defined at the bottom of | 107 // Forward declarations for some functions defined at the bottom of |
108 // the file. | 108 // the file. |
109 | 109 |
110 static void yyerror (octave_parser& curr_parser, const char *s); | 110 static void yyerror (octave_base_parser& curr_parser, const char *s); |
111 | 111 |
112 // Finish building a statement. | 112 // Finish building a statement. |
113 template <class T> | 113 template <class T> |
114 static tree_statement * | 114 static tree_statement * |
115 make_statement (T *arg) | 115 make_statement (T *arg) |
124 { \ | 124 { \ |
125 yyerrok; \ | 125 yyerrok; \ |
126 if (! parser_symtab_context.empty ()) \ | 126 if (! parser_symtab_context.empty ()) \ |
127 parser_symtab_context.pop (); \ | 127 parser_symtab_context.pop (); \ |
128 if ((interactive || forced_interactive) \ | 128 if ((interactive || forced_interactive) \ |
129 && ! (curr_lexer)->input_from_eval_string ()) \ | 129 && ! curr_lexer.input_from_eval_string ()) \ |
130 YYACCEPT; \ | 130 YYACCEPT; \ |
131 else \ | 131 else \ |
132 YYABORT; \ | 132 YYABORT; \ |
133 } \ | 133 } \ |
134 while (0) | 134 while (0) |
135 | 135 |
136 #define curr_lexer curr_parser.curr_lexer | 136 #define curr_lexer curr_parser.curr_lexer |
137 #define scanner curr_lexer->scanner | 137 #define scanner curr_lexer.scanner |
138 | 138 |
139 %} | 139 %} |
140 | 140 |
141 // Bison declarations. | 141 // Bison declarations. |
142 | 142 |
154 // care to properly save and restore (typically with an unwind_protect | 154 // care to properly save and restore (typically with an unwind_protect |
155 // object) relevant global values before and after the nested call. | 155 // object) relevant global values before and after the nested call. |
156 | 156 |
157 %define api.pure | 157 %define api.pure |
158 %PUSH_PULL_DECL% | 158 %PUSH_PULL_DECL% |
159 %parse-param { octave_parser& curr_parser } | 159 %parse-param { octave_base_parser& curr_parser } |
160 %lex-param { void *scanner } | 160 %lex-param { void *scanner } |
161 | 161 |
162 %union | 162 %union |
163 { | 163 { |
164 // The type of the basic tokens returned by the lexer. | 164 // The type of the basic tokens returned by the lexer. |
324 | 324 |
325 input1 : '\n' | 325 input1 : '\n' |
326 { $$ = 0; } | 326 { $$ = 0; } |
327 | END_OF_INPUT | 327 | END_OF_INPUT |
328 { | 328 { |
329 curr_lexer->end_of_input = true; | 329 curr_lexer.end_of_input = true; |
330 $$ = 0; | 330 $$ = 0; |
331 } | 331 } |
332 | simple_list | 332 | simple_list |
333 { $$ = $1; } | 333 { $$ = $1; } |
334 | simple_list '\n' | 334 | simple_list '\n' |
482 ; | 482 ; |
483 | 483 |
484 fcn_handle : '@' FCN_HANDLE | 484 fcn_handle : '@' FCN_HANDLE |
485 { | 485 { |
486 $$ = curr_parser.make_fcn_handle ($2); | 486 $$ = curr_parser.make_fcn_handle ($2); |
487 curr_lexer->looking_at_function_handle--; | 487 curr_lexer.looking_at_function_handle--; |
488 } | 488 } |
489 ; | 489 ; |
490 | 490 |
491 anon_fcn_handle : '@' param_list statement | 491 anon_fcn_handle : '@' param_list statement |
492 { | 492 { |
493 $$ = curr_parser.make_anon_fcn_handle ($2, $3); | 493 $$ = curr_parser.make_anon_fcn_handle ($2, $3); |
494 curr_lexer->nesting_level.remove (); | 494 curr_lexer.nesting_level.remove (); |
495 } | 495 } |
496 ; | 496 ; |
497 | 497 |
498 primary_expr : identifier | 498 primary_expr : identifier |
499 { $$ = $1; } | 499 { $$ = $1; } |
501 { $$ = $1; } | 501 { $$ = $1; } |
502 | fcn_handle | 502 | fcn_handle |
503 { $$ = $1; } | 503 { $$ = $1; } |
504 | matrix | 504 | matrix |
505 { | 505 { |
506 curr_lexer->looking_at_matrix_or_assign_lhs = false; | 506 curr_lexer.looking_at_matrix_or_assign_lhs = false; |
507 $$ = $1; | 507 $$ = $1; |
508 } | 508 } |
509 | cell | 509 | cell |
510 { $$ = $1; } | 510 { $$ = $1; } |
511 | meta_identifier | 511 | meta_identifier |
551 $$ = $1; | 551 $$ = $1; |
552 } | 552 } |
553 ; | 553 ; |
554 | 554 |
555 indirect_ref_op : '.' | 555 indirect_ref_op : '.' |
556 { curr_lexer->looking_at_indirect_ref = true; } | 556 { curr_lexer.looking_at_indirect_ref = true; } |
557 ; | 557 ; |
558 | 558 |
559 oper_expr : primary_expr | 559 oper_expr : primary_expr |
560 { $$ = $1; } | 560 { $$ = $1; } |
561 | oper_expr PLUS_PLUS | 561 | oper_expr PLUS_PLUS |
658 assign_lhs : simple_expr | 658 assign_lhs : simple_expr |
659 { | 659 { |
660 $$ = curr_parser.validate_matrix_for_assignment ($1); | 660 $$ = curr_parser.validate_matrix_for_assignment ($1); |
661 | 661 |
662 if ($$) | 662 if ($$) |
663 { curr_lexer->looking_at_matrix_or_assign_lhs = false; } | 663 { curr_lexer.looking_at_matrix_or_assign_lhs = false; } |
664 else | 664 else |
665 { | 665 { |
666 // validate_matrix_for_assignment deleted $1. | 666 // validate_matrix_for_assignment deleted $1. |
667 ABORT_PARSE; | 667 ABORT_PARSE; |
668 } | 668 } |
749 // ===================== | 749 // ===================== |
750 | 750 |
751 declaration : GLOBAL decl1 | 751 declaration : GLOBAL decl1 |
752 { | 752 { |
753 $$ = curr_parser.make_decl_command (GLOBAL, $1, $2); | 753 $$ = curr_parser.make_decl_command (GLOBAL, $1, $2); |
754 curr_lexer->looking_at_decl_list = false; | 754 curr_lexer.looking_at_decl_list = false; |
755 } | 755 } |
756 | PERSISTENT decl1 | 756 | PERSISTENT decl1 |
757 { | 757 { |
758 $$ = curr_parser.make_decl_command (PERSISTENT, $1, $2); | 758 $$ = curr_parser.make_decl_command (PERSISTENT, $1, $2); |
759 curr_lexer->looking_at_decl_list = false; | 759 curr_lexer.looking_at_decl_list = false; |
760 } | 760 } |
761 ; | 761 ; |
762 | 762 |
763 decl1 : decl2 | 763 decl1 : decl2 |
764 { $$ = new tree_decl_init_list ($1); } | 764 { $$ = new tree_decl_init_list ($1); } |
768 $$ = $1; | 768 $$ = $1; |
769 } | 769 } |
770 ; | 770 ; |
771 | 771 |
772 decl_param_init : // empty | 772 decl_param_init : // empty |
773 { curr_lexer->looking_at_initializer_expression = true; } | 773 { curr_lexer.looking_at_initializer_expression = true; } |
774 | 774 |
775 decl2 : identifier | 775 decl2 : identifier |
776 { $$ = new tree_decl_elt ($1); } | 776 { $$ = new tree_decl_elt ($1); } |
777 | identifier '=' decl_param_init expression | 777 | identifier '=' decl_param_init expression |
778 { | 778 { |
779 curr_lexer->looking_at_initializer_expression = false; | 779 curr_lexer.looking_at_initializer_expression = false; |
780 $$ = new tree_decl_elt ($1, $4); | 780 $$ = new tree_decl_elt ($1, $4); |
781 } | 781 } |
782 | magic_tilde | 782 | magic_tilde |
783 { | 783 { |
784 $$ = new tree_decl_elt ($1); | 784 $$ = new tree_decl_elt ($1); |
815 } | 815 } |
816 ; | 816 ; |
817 | 817 |
818 if_cmd_list1 : expression opt_sep opt_list | 818 if_cmd_list1 : expression opt_sep opt_list |
819 { | 819 { |
820 $1->mark_braindead_shortcircuit (curr_lexer->fcn_file_full_name); | 820 $1->mark_braindead_shortcircuit (curr_lexer.fcn_file_full_name); |
821 | 821 |
822 $$ = curr_parser.start_if_command ($1, $3); | 822 $$ = curr_parser.start_if_command ($1, $3); |
823 } | 823 } |
824 | if_cmd_list1 elseif_clause | 824 | if_cmd_list1 elseif_clause |
825 { | 825 { |
828 } | 828 } |
829 ; | 829 ; |
830 | 830 |
831 elseif_clause : ELSEIF stash_comment opt_sep expression opt_sep opt_list | 831 elseif_clause : ELSEIF stash_comment opt_sep expression opt_sep opt_list |
832 { | 832 { |
833 $4->mark_braindead_shortcircuit (curr_lexer->fcn_file_full_name); | 833 $4->mark_braindead_shortcircuit (curr_lexer.fcn_file_full_name); |
834 | 834 |
835 $$ = curr_parser.make_elseif_clause ($1, $4, $6, $2); | 835 $$ = curr_parser.make_elseif_clause ($1, $4, $6, $2); |
836 } | 836 } |
837 ; | 837 ; |
838 | 838 |
887 // Looping | 887 // Looping |
888 // ======= | 888 // ======= |
889 | 889 |
890 loop_command : WHILE stash_comment expression opt_sep opt_list END | 890 loop_command : WHILE stash_comment expression opt_sep opt_list END |
891 { | 891 { |
892 $3->mark_braindead_shortcircuit (curr_lexer->fcn_file_full_name); | 892 $3->mark_braindead_shortcircuit (curr_lexer.fcn_file_full_name); |
893 | 893 |
894 if (! ($$ = curr_parser.make_while_command ($1, $3, $5, $6, $2))) | 894 if (! ($$ = curr_parser.make_while_command ($1, $3, $5, $6, $2))) |
895 ABORT_PARSE; | 895 ABORT_PARSE; |
896 } | 896 } |
897 | DO stash_comment opt_sep opt_list UNTIL expression | 897 | DO stash_comment opt_sep opt_list UNTIL expression |
984 | 984 |
985 symbol_table::set_scope (symbol_table::alloc_scope ()); | 985 symbol_table::set_scope (symbol_table::alloc_scope ()); |
986 | 986 |
987 curr_parser.function_scopes.push_back (symbol_table::current_scope ()); | 987 curr_parser.function_scopes.push_back (symbol_table::current_scope ()); |
988 | 988 |
989 if (! curr_lexer->reading_script_file | 989 if (! curr_lexer.reading_script_file |
990 && curr_parser.curr_fcn_depth == 1 | 990 && curr_parser.curr_fcn_depth == 1 |
991 && ! curr_parser.parsing_subfunctions) | 991 && ! curr_parser.parsing_subfunctions) |
992 curr_parser.primary_fcn_scope = symbol_table::current_scope (); | 992 curr_parser.primary_fcn_scope = symbol_table::current_scope (); |
993 | 993 |
994 if (curr_lexer->reading_script_file | 994 if (curr_lexer.reading_script_file |
995 && curr_parser.curr_fcn_depth > 1) | 995 && curr_parser.curr_fcn_depth > 1) |
996 curr_parser.bison_error ("nested functions not implemented in this context"); | 996 curr_parser.bison_error ("nested functions not implemented in this context"); |
997 } | 997 } |
998 ; | 998 ; |
999 | 999 |
1001 // List of function parameters | 1001 // List of function parameters |
1002 // =========================== | 1002 // =========================== |
1003 | 1003 |
1004 param_list_beg : '(' | 1004 param_list_beg : '(' |
1005 { | 1005 { |
1006 curr_lexer->looking_at_parameter_list = true; | 1006 curr_lexer.looking_at_parameter_list = true; |
1007 | 1007 |
1008 if (curr_lexer->looking_at_function_handle) | 1008 if (curr_lexer.looking_at_function_handle) |
1009 { | 1009 { |
1010 parser_symtab_context.push (); | 1010 parser_symtab_context.push (); |
1011 symbol_table::set_scope (symbol_table::alloc_scope ()); | 1011 symbol_table::set_scope (symbol_table::alloc_scope ()); |
1012 curr_lexer->looking_at_function_handle--; | 1012 curr_lexer.looking_at_function_handle--; |
1013 curr_lexer->looking_at_anon_fcn_args = true; | 1013 curr_lexer.looking_at_anon_fcn_args = true; |
1014 } | 1014 } |
1015 } | 1015 } |
1016 ; | 1016 ; |
1017 | 1017 |
1018 param_list_end : ')' | 1018 param_list_end : ')' |
1019 { | 1019 { |
1020 curr_lexer->looking_at_parameter_list = false; | 1020 curr_lexer.looking_at_parameter_list = false; |
1021 curr_lexer->looking_for_object_index = false; | 1021 curr_lexer.looking_for_object_index = false; |
1022 } | 1022 } |
1023 ; | 1023 ; |
1024 | 1024 |
1025 param_list : param_list_beg param_list1 param_list_end | 1025 param_list : param_list_beg param_list1 param_list_end |
1026 { $$ = $2; } | 1026 { $$ = $2; } |
1057 // List of function return value names | 1057 // List of function return value names |
1058 // =================================== | 1058 // =================================== |
1059 | 1059 |
1060 return_list : '[' ']' | 1060 return_list : '[' ']' |
1061 { | 1061 { |
1062 curr_lexer->looking_at_return_list = false; | 1062 curr_lexer.looking_at_return_list = false; |
1063 $$ = new tree_parameter_list (); | 1063 $$ = new tree_parameter_list (); |
1064 } | 1064 } |
1065 | return_list1 | 1065 | return_list1 |
1066 { | 1066 { |
1067 curr_lexer->looking_at_return_list = false; | 1067 curr_lexer.looking_at_return_list = false; |
1068 if ($1->validate (tree_parameter_list::out)) | 1068 if ($1->validate (tree_parameter_list::out)) |
1069 $$ = $1; | 1069 $$ = $1; |
1070 else | 1070 else |
1071 ABORT_PARSE; | 1071 ABORT_PARSE; |
1072 } | 1072 } |
1073 | '[' return_list1 ']' | 1073 | '[' return_list1 ']' |
1074 { | 1074 { |
1075 curr_lexer->looking_at_return_list = false; | 1075 curr_lexer.looking_at_return_list = false; |
1076 if ($2->validate (tree_parameter_list::out)) | 1076 if ($2->validate (tree_parameter_list::out)) |
1077 $$ = $2; | 1077 $$ = $2; |
1078 else | 1078 else |
1079 ABORT_PARSE; | 1079 ABORT_PARSE; |
1080 } | 1080 } |
1093 // Script or function file | 1093 // Script or function file |
1094 // ======================= | 1094 // ======================= |
1095 | 1095 |
1096 file : INPUT_FILE opt_nl opt_list END_OF_INPUT | 1096 file : INPUT_FILE opt_nl opt_list END_OF_INPUT |
1097 { | 1097 { |
1098 if (! curr_lexer->reading_fcn_file) | 1098 if (! curr_lexer.reading_fcn_file) |
1099 { | 1099 { |
1100 tree_statement *end_of_script | 1100 tree_statement *end_of_script |
1101 = curr_parser.make_end ("endscript", | 1101 = curr_parser.make_end ("endscript", |
1102 curr_lexer->input_line_number, | 1102 curr_lexer.input_line_number, |
1103 curr_lexer->current_input_column); | 1103 curr_lexer.current_input_column); |
1104 | 1104 |
1105 curr_parser.make_script ($3, end_of_script); | 1105 curr_parser.make_script ($3, end_of_script); |
1106 } | 1106 } |
1107 | 1107 |
1108 $$ = 0; | 1108 $$ = 0; |
1114 // =================== | 1114 // =================== |
1115 | 1115 |
1116 function_beg : push_fcn_symtab FCN stash_comment | 1116 function_beg : push_fcn_symtab FCN stash_comment |
1117 { | 1117 { |
1118 $$ = $3; | 1118 $$ = $3; |
1119 if (curr_lexer->reading_classdef_file | 1119 if (curr_lexer.reading_classdef_file |
1120 || curr_lexer->parsing_classdef) | 1120 || curr_lexer.parsing_classdef) |
1121 curr_lexer->maybe_classdef_get_set_method = true; | 1121 curr_lexer.maybe_classdef_get_set_method = true; |
1122 } | 1122 } |
1123 ; | 1123 ; |
1124 | 1124 |
1125 function : function_beg function1 | 1125 function : function_beg function1 |
1126 { | 1126 { |
1136 | 1136 |
1137 fcn_name : identifier | 1137 fcn_name : identifier |
1138 { | 1138 { |
1139 std::string id_name = $1->name (); | 1139 std::string id_name = $1->name (); |
1140 | 1140 |
1141 curr_lexer->parsed_function_name.top () = true; | 1141 curr_lexer.parsed_function_name.top () = true; |
1142 curr_lexer->maybe_classdef_get_set_method = false; | 1142 curr_lexer.maybe_classdef_get_set_method = false; |
1143 | 1143 |
1144 $$ = $1; | 1144 $$ = $1; |
1145 } | 1145 } |
1146 | GET '.' identifier | 1146 | GET '.' identifier |
1147 { | 1147 { |
1148 curr_lexer->parsed_function_name.top () = true; | 1148 curr_lexer.parsed_function_name.top () = true; |
1149 curr_lexer->maybe_classdef_get_set_method = false; | 1149 curr_lexer.maybe_classdef_get_set_method = false; |
1150 $$ = $3; | 1150 $$ = $3; |
1151 } | 1151 } |
1152 | SET '.' identifier | 1152 | SET '.' identifier |
1153 { | 1153 { |
1154 curr_lexer->parsed_function_name.top () = true; | 1154 curr_lexer.parsed_function_name.top () = true; |
1155 curr_lexer->maybe_classdef_get_set_method = false; | 1155 curr_lexer.maybe_classdef_get_set_method = false; |
1156 $$ = $3; | 1156 $$ = $3; |
1157 } | 1157 } |
1158 ; | 1158 ; |
1159 | 1159 |
1160 function1 : fcn_name function2 | 1160 function1 : fcn_name function2 |
1183 ABORT_PARSE; | 1183 ABORT_PARSE; |
1184 } | 1184 } |
1185 | END_OF_INPUT | 1185 | END_OF_INPUT |
1186 { | 1186 { |
1187 // A lot of tests are based on the assumption that this is OK | 1187 // A lot of tests are based on the assumption that this is OK |
1188 // if (curr_lexer->reading_script_file) | 1188 // if (curr_lexer.reading_script_file) |
1189 // { | 1189 // { |
1190 // curr_parser.bison_error ("function body open at end of script"); | 1190 // curr_parser.bison_error ("function body open at end of script"); |
1191 // YYABORT; | 1191 // YYABORT; |
1192 // } | 1192 // } |
1193 | 1193 |
1197 "if one function is explicitly ended, " | 1197 "if one function is explicitly ended, " |
1198 "so must all the others"); | 1198 "so must all the others"); |
1199 YYABORT; | 1199 YYABORT; |
1200 } | 1200 } |
1201 | 1201 |
1202 if (! (curr_lexer->reading_fcn_file || curr_lexer->reading_script_file | 1202 if (! (curr_lexer.reading_fcn_file || curr_lexer.reading_script_file |
1203 || (curr_lexer)->input_from_eval_string ())) | 1203 || curr_lexer.input_from_eval_string ())) |
1204 { | 1204 { |
1205 curr_parser.bison_error ("function body open at end of input"); | 1205 curr_parser.bison_error ("function body open at end of input"); |
1206 YYABORT; | 1206 YYABORT; |
1207 } | 1207 } |
1208 | 1208 |
1209 if (curr_lexer->reading_classdef_file) | 1209 if (curr_lexer.reading_classdef_file) |
1210 { | 1210 { |
1211 curr_parser.bison_error ("classdef body open at end of input"); | 1211 curr_parser.bison_error ("classdef body open at end of input"); |
1212 YYABORT; | 1212 YYABORT; |
1213 } | 1213 } |
1214 | 1214 |
1215 $$ = curr_parser.make_end ("endfunction", | 1215 $$ = curr_parser.make_end ("endfunction", |
1216 curr_lexer->input_line_number, | 1216 curr_lexer.input_line_number, |
1217 curr_lexer->current_input_column); | 1217 curr_lexer.current_input_column); |
1218 } | 1218 } |
1219 ; | 1219 ; |
1220 | 1220 |
1221 // ======== | 1221 // ======== |
1222 // Classdef | 1222 // Classdef |
1223 // ======== | 1223 // ======== |
1224 | 1224 |
1225 classdef_beg : CLASSDEF stash_comment | 1225 classdef_beg : CLASSDEF stash_comment |
1226 { | 1226 { |
1227 $$ = 0; | 1227 $$ = 0; |
1228 curr_lexer->parsing_classdef = true; | 1228 curr_lexer.parsing_classdef = true; |
1229 } | 1229 } |
1230 ; | 1230 ; |
1231 | 1231 |
1232 classdef_end : END | 1232 classdef_end : END |
1233 { | 1233 { |
1234 curr_lexer->parsing_classdef = false; | 1234 curr_lexer.parsing_classdef = false; |
1235 | 1235 |
1236 if (curr_parser.end_token_ok ($1, token::classdef_end)) | 1236 if (curr_parser.end_token_ok ($1, token::classdef_end)) |
1237 $$ = curr_parser.make_end ("endclassdef", $1->line (), $1->column ()); | 1237 $$ = curr_parser.make_end ("endclassdef", $1->line (), $1->column ()); |
1238 else | 1238 else |
1239 ABORT_PARSE; | 1239 ABORT_PARSE; |
1441 // Generic error messages. | 1441 // Generic error messages. |
1442 | 1442 |
1443 #undef curr_lexer | 1443 #undef curr_lexer |
1444 | 1444 |
1445 static void | 1445 static void |
1446 yyerror (octave_parser& curr_parser, const char *s) | 1446 yyerror (octave_base_parser& curr_parser, const char *s) |
1447 { | 1447 { |
1448 curr_parser.bison_error (s); | 1448 curr_parser.bison_error (s); |
1449 } | 1449 } |
1450 | 1450 |
1451 octave_parser::~octave_parser (void) | 1451 octave_base_parser::~octave_base_parser (void) |
1452 { | 1452 { |
1453 #if defined (OCTAVE_USE_PUSH_PARSER) | 1453 #if defined (OCTAVE_USE_PUSH_PARSER) |
1454 yypstate_delete (static_cast<yypstate *> (parser_state)); | 1454 yypstate_delete (static_cast<yypstate *> (parser_state)); |
1455 #endif | 1455 #endif |
1456 | 1456 |
1457 delete stmt_list; | 1457 delete stmt_list; |
1458 | 1458 |
1459 delete curr_lexer; | 1459 delete &curr_lexer; |
1460 } | 1460 } |
1461 void octave_parser::init (void) | 1461 |
1462 void octave_base_parser::init (void) | |
1462 { | 1463 { |
1463 #if defined (OCTAVE_USE_PUSH_PARSER) | 1464 #if defined (OCTAVE_USE_PUSH_PARSER) |
1464 parser_state = yypstate_new (); | 1465 parser_state = yypstate_new (); |
1465 #endif | 1466 #endif |
1466 | 1467 |
1467 CURR_LEXER = curr_lexer; | 1468 CURR_LEXER = &curr_lexer; |
1468 } | 1469 } |
1469 | 1470 |
1470 void | 1471 void |
1471 octave_parser::reset (void) | 1472 octave_base_parser::reset (void) |
1472 { | 1473 { |
1473 delete stmt_list; | 1474 delete stmt_list; |
1474 | 1475 |
1475 stmt_list = 0; | 1476 stmt_list = 0; |
1476 | 1477 |
1477 curr_lexer->reset (); | 1478 curr_lexer.reset (); |
1478 } | |
1479 | |
1480 int | |
1481 octave_parser::run (void) | |
1482 { | |
1483 int status = 0; | |
1484 | |
1485 #if defined (OCTAVE_USE_PUSH_PARSER) | |
1486 | |
1487 do | |
1488 { | |
1489 YYSTYPE lval; | |
1490 | |
1491 int token = octave_lex (&lval, scanner); | |
1492 | |
1493 yypstate *pstate = static_cast<yypstate *> (parser_state); | |
1494 | |
1495 status = octave_push_parse (pstate, token, &lval, *this); | |
1496 } | |
1497 while (status == YYPUSH_MORE); | |
1498 | |
1499 #else | |
1500 | |
1501 status = octave_parse (*this); | |
1502 | |
1503 #endif | |
1504 | |
1505 return status; | |
1506 } | 1479 } |
1507 | 1480 |
1508 // Error mesages for mismatched end tokens. | 1481 // Error mesages for mismatched end tokens. |
1509 | 1482 |
1510 void | 1483 void |
1511 octave_parser::end_error (const char *type, token::end_tok_type ettype, | 1484 octave_base_parser::end_error (const char *type, token::end_tok_type ettype, |
1512 int l, int c) | 1485 int l, int c) |
1513 { | 1486 { |
1514 static const char *fmt | 1487 static const char *fmt |
1515 = "'%s' command matched by '%s' near line %d column %d"; | 1488 = "'%s' command matched by '%s' near line %d column %d"; |
1516 | 1489 |
1517 switch (ettype) | 1490 switch (ettype) |
1559 } | 1532 } |
1560 | 1533 |
1561 // Check to see that end tokens are properly matched. | 1534 // Check to see that end tokens are properly matched. |
1562 | 1535 |
1563 bool | 1536 bool |
1564 octave_parser::end_token_ok (token *tok, token::end_tok_type expected) | 1537 octave_base_parser::end_token_ok (token *tok, token::end_tok_type expected) |
1565 { | 1538 { |
1566 bool retval = true; | 1539 bool retval = true; |
1567 | 1540 |
1568 token::end_tok_type ettype = tok->ettype (); | 1541 token::end_tok_type ettype = tok->ettype (); |
1569 | 1542 |
1629 | 1602 |
1630 // Maybe print a warning if an assignment expression is used as the | 1603 // Maybe print a warning if an assignment expression is used as the |
1631 // test in a logical expression. | 1604 // test in a logical expression. |
1632 | 1605 |
1633 void | 1606 void |
1634 octave_parser::maybe_warn_assign_as_truth_value (tree_expression *expr) | 1607 octave_base_parser::maybe_warn_assign_as_truth_value (tree_expression *expr) |
1635 { | 1608 { |
1636 if (expr->is_assignment_expression () | 1609 if (expr->is_assignment_expression () |
1637 && expr->paren_count () < 2) | 1610 && expr->paren_count () < 2) |
1638 { | 1611 { |
1639 if (curr_lexer->fcn_file_full_name.empty ()) | 1612 if (curr_lexer.fcn_file_full_name.empty ()) |
1640 warning_with_id | 1613 warning_with_id |
1641 ("Octave:assign-as-truth-value", | 1614 ("Octave:assign-as-truth-value", |
1642 "suggest parenthesis around assignment used as truth value"); | 1615 "suggest parenthesis around assignment used as truth value"); |
1643 else | 1616 else |
1644 warning_with_id | 1617 warning_with_id |
1645 ("Octave:assign-as-truth-value", | 1618 ("Octave:assign-as-truth-value", |
1646 "suggest parenthesis around assignment used as truth value near line %d, column %d in file '%s'", | 1619 "suggest parenthesis around assignment used as truth value near line %d, column %d in file '%s'", |
1647 expr->line (), expr->column (), curr_lexer->fcn_file_full_name.c_str ()); | 1620 expr->line (), expr->column (), curr_lexer.fcn_file_full_name.c_str ()); |
1648 } | 1621 } |
1649 } | 1622 } |
1650 | 1623 |
1651 // Maybe print a warning about switch labels that aren't constants. | 1624 // Maybe print a warning about switch labels that aren't constants. |
1652 | 1625 |
1653 void | 1626 void |
1654 octave_parser::maybe_warn_variable_switch_label (tree_expression *expr) | 1627 octave_base_parser::maybe_warn_variable_switch_label (tree_expression *expr) |
1655 { | 1628 { |
1656 if (! expr->is_constant ()) | 1629 if (! expr->is_constant ()) |
1657 { | 1630 { |
1658 if (curr_lexer->fcn_file_full_name.empty ()) | 1631 if (curr_lexer.fcn_file_full_name.empty ()) |
1659 warning_with_id ("Octave:variable-switch-label", | 1632 warning_with_id ("Octave:variable-switch-label", |
1660 "variable switch label"); | 1633 "variable switch label"); |
1661 else | 1634 else |
1662 warning_with_id | 1635 warning_with_id |
1663 ("Octave:variable-switch-label", | 1636 ("Octave:variable-switch-label", |
1664 "variable switch label near line %d, column %d in file '%s'", | 1637 "variable switch label near line %d, column %d in file '%s'", |
1665 expr->line (), expr->column (), curr_lexer->fcn_file_full_name.c_str ()); | 1638 expr->line (), expr->column (), curr_lexer.fcn_file_full_name.c_str ()); |
1666 } | 1639 } |
1667 } | 1640 } |
1668 | 1641 |
1669 static tree_expression * | 1642 static tree_expression * |
1670 fold (tree_binary_expression *e) | 1643 fold (tree_binary_expression *e) |
1756 } | 1729 } |
1757 | 1730 |
1758 // Finish building a range. | 1731 // Finish building a range. |
1759 | 1732 |
1760 tree_expression * | 1733 tree_expression * |
1761 octave_parser::finish_colon_expression (tree_colon_expression *e) | 1734 octave_base_parser::finish_colon_expression (tree_colon_expression *e) |
1762 { | 1735 { |
1763 tree_expression *retval = e; | 1736 tree_expression *retval = e; |
1764 | 1737 |
1765 unwind_protect frame; | 1738 unwind_protect frame; |
1766 | 1739 |
1820 } | 1793 } |
1821 | 1794 |
1822 // Make a constant. | 1795 // Make a constant. |
1823 | 1796 |
1824 tree_constant * | 1797 tree_constant * |
1825 octave_parser::make_constant (int op, token *tok_val) | 1798 octave_base_parser::make_constant (int op, token *tok_val) |
1826 { | 1799 { |
1827 int l = tok_val->line (); | 1800 int l = tok_val->line (); |
1828 int c = tok_val->column (); | 1801 int c = tok_val->column (); |
1829 | 1802 |
1830 tree_constant *retval = 0; | 1803 tree_constant *retval = 0; |
1883 } | 1856 } |
1884 | 1857 |
1885 // Make a function handle. | 1858 // Make a function handle. |
1886 | 1859 |
1887 tree_fcn_handle * | 1860 tree_fcn_handle * |
1888 octave_parser::make_fcn_handle (token *tok_val) | 1861 octave_base_parser::make_fcn_handle (token *tok_val) |
1889 { | 1862 { |
1890 int l = tok_val->line (); | 1863 int l = tok_val->line (); |
1891 int c = tok_val->column (); | 1864 int c = tok_val->column (); |
1892 | 1865 |
1893 tree_fcn_handle *retval = new tree_fcn_handle (tok_val->text (), l, c); | 1866 tree_fcn_handle *retval = new tree_fcn_handle (tok_val->text (), l, c); |
1896 } | 1869 } |
1897 | 1870 |
1898 // Make an anonymous function handle. | 1871 // Make an anonymous function handle. |
1899 | 1872 |
1900 tree_anon_fcn_handle * | 1873 tree_anon_fcn_handle * |
1901 octave_parser::make_anon_fcn_handle (tree_parameter_list *param_list, | 1874 octave_base_parser::make_anon_fcn_handle (tree_parameter_list *param_list, |
1902 tree_statement *stmt) | 1875 tree_statement *stmt) |
1903 { | 1876 { |
1904 // FIXME -- need to get these from the location of the @ symbol. | 1877 // FIXME -- need to get these from the location of the @ symbol. |
1905 int l = curr_lexer->input_line_number; | 1878 int l = curr_lexer.input_line_number; |
1906 int c = curr_lexer->current_input_column; | 1879 int c = curr_lexer.current_input_column; |
1907 | 1880 |
1908 tree_parameter_list *ret_list = 0; | 1881 tree_parameter_list *ret_list = 0; |
1909 | 1882 |
1910 symbol_table::scope_id fcn_scope = symbol_table::current_scope (); | 1883 symbol_table::scope_id fcn_scope = symbol_table::current_scope (); |
1911 | 1884 |
1922 | 1895 |
1923 tree_anon_fcn_handle *retval | 1896 tree_anon_fcn_handle *retval |
1924 = new tree_anon_fcn_handle (param_list, ret_list, body, fcn_scope, l, c); | 1897 = new tree_anon_fcn_handle (param_list, ret_list, body, fcn_scope, l, c); |
1925 // FIXME: Stash the filename. This does not work and produces | 1898 // FIXME: Stash the filename. This does not work and produces |
1926 // errors when executed. | 1899 // errors when executed. |
1927 //retval->stash_file_name (curr_lexer->fcn_file_name); | 1900 //retval->stash_file_name (curr_lexer.fcn_file_name); |
1928 | 1901 |
1929 return retval; | 1902 return retval; |
1930 } | 1903 } |
1931 | 1904 |
1932 // Build a binary expression. | 1905 // Build a binary expression. |
1933 | 1906 |
1934 tree_expression * | 1907 tree_expression * |
1935 octave_parser::make_binary_op (int op, tree_expression *op1, token *tok_val, | 1908 octave_base_parser::make_binary_op (int op, tree_expression *op1, |
1936 tree_expression *op2) | 1909 token *tok_val, tree_expression *op2) |
1937 { | 1910 { |
1938 octave_value::binary_op t = octave_value::unknown_binary_op; | 1911 octave_value::binary_op t = octave_value::unknown_binary_op; |
1939 | 1912 |
1940 switch (op) | 1913 switch (op) |
1941 { | 1914 { |
2034 } | 2007 } |
2035 | 2008 |
2036 // Build a boolean expression. | 2009 // Build a boolean expression. |
2037 | 2010 |
2038 tree_expression * | 2011 tree_expression * |
2039 octave_parser::make_boolean_op (int op, tree_expression *op1, token *tok_val, | 2012 octave_base_parser::make_boolean_op (int op, tree_expression *op1, |
2040 tree_expression *op2) | 2013 token *tok_val, tree_expression *op2) |
2041 { | 2014 { |
2042 tree_boolean_expression::type t; | 2015 tree_boolean_expression::type t; |
2043 | 2016 |
2044 switch (op) | 2017 switch (op) |
2045 { | 2018 { |
2066 } | 2039 } |
2067 | 2040 |
2068 // Build a prefix expression. | 2041 // Build a prefix expression. |
2069 | 2042 |
2070 tree_expression * | 2043 tree_expression * |
2071 octave_parser::make_prefix_op (int op, tree_expression *op1, token *tok_val) | 2044 octave_base_parser::make_prefix_op (int op, tree_expression *op1, |
2045 token *tok_val) | |
2072 { | 2046 { |
2073 octave_value::unary_op t = octave_value::unknown_unary_op; | 2047 octave_value::unary_op t = octave_value::unknown_unary_op; |
2074 | 2048 |
2075 switch (op) | 2049 switch (op) |
2076 { | 2050 { |
2109 } | 2083 } |
2110 | 2084 |
2111 // Build a postfix expression. | 2085 // Build a postfix expression. |
2112 | 2086 |
2113 tree_expression * | 2087 tree_expression * |
2114 octave_parser::make_postfix_op (int op, tree_expression *op1, token *tok_val) | 2088 octave_base_parser::make_postfix_op (int op, tree_expression *op1, |
2089 token *tok_val) | |
2115 { | 2090 { |
2116 octave_value::unary_op t = octave_value::unknown_unary_op; | 2091 octave_value::unary_op t = octave_value::unknown_unary_op; |
2117 | 2092 |
2118 switch (op) | 2093 switch (op) |
2119 { | 2094 { |
2148 } | 2123 } |
2149 | 2124 |
2150 // Build an unwind-protect command. | 2125 // Build an unwind-protect command. |
2151 | 2126 |
2152 tree_command * | 2127 tree_command * |
2153 octave_parser::make_unwind_command (token *unwind_tok, | 2128 octave_base_parser::make_unwind_command (token *unwind_tok, |
2154 tree_statement_list *body, | 2129 tree_statement_list *body, |
2155 tree_statement_list *cleanup_stmts, | 2130 tree_statement_list *cleanup_stmts, |
2156 token *end_tok, | 2131 token *end_tok, |
2157 octave_comment_list *lc, | 2132 octave_comment_list *lc, |
2158 octave_comment_list *mc) | 2133 octave_comment_list *mc) |
2159 { | 2134 { |
2160 tree_command *retval = 0; | 2135 tree_command *retval = 0; |
2161 | 2136 |
2162 if (end_token_ok (end_tok, token::unwind_protect_end)) | 2137 if (end_token_ok (end_tok, token::unwind_protect_end)) |
2163 { | 2138 { |
2174 } | 2149 } |
2175 | 2150 |
2176 // Build a try-catch command. | 2151 // Build a try-catch command. |
2177 | 2152 |
2178 tree_command * | 2153 tree_command * |
2179 octave_parser::make_try_command (token *try_tok, tree_statement_list *body, | 2154 octave_base_parser::make_try_command (token *try_tok, |
2180 tree_statement_list *cleanup_stmts, | 2155 tree_statement_list *body, |
2181 token *end_tok, | 2156 tree_statement_list *cleanup_stmts, |
2182 octave_comment_list *lc, | 2157 token *end_tok, |
2183 octave_comment_list *mc) | 2158 octave_comment_list *lc, |
2159 octave_comment_list *mc) | |
2184 { | 2160 { |
2185 tree_command *retval = 0; | 2161 tree_command *retval = 0; |
2186 | 2162 |
2187 if (end_token_ok (end_tok, token::try_catch_end)) | 2163 if (end_token_ok (end_tok, token::try_catch_end)) |
2188 { | 2164 { |
2199 } | 2175 } |
2200 | 2176 |
2201 // Build a while command. | 2177 // Build a while command. |
2202 | 2178 |
2203 tree_command * | 2179 tree_command * |
2204 octave_parser::make_while_command (token *while_tok, tree_expression *expr, | 2180 octave_base_parser::make_while_command (token *while_tok, |
2205 tree_statement_list *body, token *end_tok, | 2181 tree_expression *expr, |
2206 octave_comment_list *lc) | 2182 tree_statement_list *body, |
2183 token *end_tok, | |
2184 octave_comment_list *lc) | |
2207 { | 2185 { |
2208 tree_command *retval = 0; | 2186 tree_command *retval = 0; |
2209 | 2187 |
2210 maybe_warn_assign_as_truth_value (expr); | 2188 maybe_warn_assign_as_truth_value (expr); |
2211 | 2189 |
2212 if (end_token_ok (end_tok, token::while_end)) | 2190 if (end_token_ok (end_tok, token::while_end)) |
2213 { | 2191 { |
2214 octave_comment_list *tc = octave_comment_buffer::get_comment (); | 2192 octave_comment_list *tc = octave_comment_buffer::get_comment (); |
2215 | 2193 |
2216 curr_lexer->looping--; | 2194 curr_lexer.looping--; |
2217 | 2195 |
2218 int l = while_tok->line (); | 2196 int l = while_tok->line (); |
2219 int c = while_tok->column (); | 2197 int c = while_tok->column (); |
2220 | 2198 |
2221 retval = new tree_while_command (expr, body, lc, tc, l, c); | 2199 retval = new tree_while_command (expr, body, lc, tc, l, c); |
2225 } | 2203 } |
2226 | 2204 |
2227 // Build a do-until command. | 2205 // Build a do-until command. |
2228 | 2206 |
2229 tree_command * | 2207 tree_command * |
2230 octave_parser::make_do_until_command (token *until_tok, | 2208 octave_base_parser::make_do_until_command (token *until_tok, |
2231 tree_statement_list *body, | 2209 tree_statement_list *body, |
2232 tree_expression *expr, | 2210 tree_expression *expr, |
2233 octave_comment_list *lc) | 2211 octave_comment_list *lc) |
2234 { | 2212 { |
2235 tree_command *retval = 0; | 2213 tree_command *retval = 0; |
2236 | 2214 |
2237 maybe_warn_assign_as_truth_value (expr); | 2215 maybe_warn_assign_as_truth_value (expr); |
2238 | 2216 |
2239 octave_comment_list *tc = octave_comment_buffer::get_comment (); | 2217 octave_comment_list *tc = octave_comment_buffer::get_comment (); |
2240 | 2218 |
2241 curr_lexer->looping--; | 2219 curr_lexer.looping--; |
2242 | 2220 |
2243 int l = until_tok->line (); | 2221 int l = until_tok->line (); |
2244 int c = until_tok->column (); | 2222 int c = until_tok->column (); |
2245 | 2223 |
2246 retval = new tree_do_until_command (expr, body, lc, tc, l, c); | 2224 retval = new tree_do_until_command (expr, body, lc, tc, l, c); |
2249 } | 2227 } |
2250 | 2228 |
2251 // Build a for command. | 2229 // Build a for command. |
2252 | 2230 |
2253 tree_command * | 2231 tree_command * |
2254 octave_parser::make_for_command (int tok_id, token *for_tok, | 2232 octave_base_parser::make_for_command (int tok_id, token *for_tok, |
2255 tree_argument_list *lhs, | 2233 tree_argument_list *lhs, |
2256 tree_expression *expr, | 2234 tree_expression *expr, |
2257 tree_expression *maxproc, | 2235 tree_expression *maxproc, |
2258 tree_statement_list *body, token *end_tok, | 2236 tree_statement_list *body, |
2259 octave_comment_list *lc) | 2237 token *end_tok, |
2238 octave_comment_list *lc) | |
2260 { | 2239 { |
2261 tree_command *retval = 0; | 2240 tree_command *retval = 0; |
2262 | 2241 |
2263 bool parfor = tok_id == PARFOR; | 2242 bool parfor = tok_id == PARFOR; |
2264 | 2243 |
2265 if (end_token_ok (end_tok, parfor ? token::parfor_end : token::for_end)) | 2244 if (end_token_ok (end_tok, parfor ? token::parfor_end : token::for_end)) |
2266 { | 2245 { |
2267 octave_comment_list *tc = octave_comment_buffer::get_comment (); | 2246 octave_comment_list *tc = octave_comment_buffer::get_comment (); |
2268 | 2247 |
2269 curr_lexer->looping--; | 2248 curr_lexer.looping--; |
2270 | 2249 |
2271 int l = for_tok->line (); | 2250 int l = for_tok->line (); |
2272 int c = for_tok->column (); | 2251 int c = for_tok->column (); |
2273 | 2252 |
2274 if (lhs->length () == 1) | 2253 if (lhs->length () == 1) |
2294 } | 2273 } |
2295 | 2274 |
2296 // Build a break command. | 2275 // Build a break command. |
2297 | 2276 |
2298 tree_command * | 2277 tree_command * |
2299 octave_parser::make_break_command (token *break_tok) | 2278 octave_base_parser::make_break_command (token *break_tok) |
2300 { | 2279 { |
2301 tree_command *retval = 0; | 2280 tree_command *retval = 0; |
2302 | 2281 |
2303 int l = break_tok->line (); | 2282 int l = break_tok->line (); |
2304 int c = break_tok->column (); | 2283 int c = break_tok->column (); |
2309 } | 2288 } |
2310 | 2289 |
2311 // Build a continue command. | 2290 // Build a continue command. |
2312 | 2291 |
2313 tree_command * | 2292 tree_command * |
2314 octave_parser::make_continue_command (token *continue_tok) | 2293 octave_base_parser::make_continue_command (token *continue_tok) |
2315 { | 2294 { |
2316 tree_command *retval = 0; | 2295 tree_command *retval = 0; |
2317 | 2296 |
2318 int l = continue_tok->line (); | 2297 int l = continue_tok->line (); |
2319 int c = continue_tok->column (); | 2298 int c = continue_tok->column (); |
2324 } | 2303 } |
2325 | 2304 |
2326 // Build a return command. | 2305 // Build a return command. |
2327 | 2306 |
2328 tree_command * | 2307 tree_command * |
2329 octave_parser::make_return_command (token *return_tok) | 2308 octave_base_parser::make_return_command (token *return_tok) |
2330 { | 2309 { |
2331 tree_command *retval = 0; | 2310 tree_command *retval = 0; |
2332 | 2311 |
2333 int l = return_tok->line (); | 2312 int l = return_tok->line (); |
2334 int c = return_tok->column (); | 2313 int c = return_tok->column (); |
2339 } | 2318 } |
2340 | 2319 |
2341 // Start an if command. | 2320 // Start an if command. |
2342 | 2321 |
2343 tree_if_command_list * | 2322 tree_if_command_list * |
2344 octave_parser::start_if_command (tree_expression *expr, | 2323 octave_base_parser::start_if_command (tree_expression *expr, |
2345 tree_statement_list *list) | 2324 tree_statement_list *list) |
2346 { | 2325 { |
2347 maybe_warn_assign_as_truth_value (expr); | 2326 maybe_warn_assign_as_truth_value (expr); |
2348 | 2327 |
2349 tree_if_clause *t = new tree_if_clause (expr, list); | 2328 tree_if_clause *t = new tree_if_clause (expr, list); |
2350 | 2329 |
2352 } | 2331 } |
2353 | 2332 |
2354 // Finish an if command. | 2333 // Finish an if command. |
2355 | 2334 |
2356 tree_if_command * | 2335 tree_if_command * |
2357 octave_parser::finish_if_command (token *if_tok, tree_if_command_list *list, | 2336 octave_base_parser::finish_if_command (token *if_tok, |
2358 token *end_tok, octave_comment_list *lc) | 2337 tree_if_command_list *list, |
2338 token *end_tok, | |
2339 octave_comment_list *lc) | |
2359 { | 2340 { |
2360 tree_if_command *retval = 0; | 2341 tree_if_command *retval = 0; |
2361 | 2342 |
2362 if (end_token_ok (end_tok, token::if_end)) | 2343 if (end_token_ok (end_tok, token::if_end)) |
2363 { | 2344 { |
2384 } | 2365 } |
2385 | 2366 |
2386 // Build an elseif clause. | 2367 // Build an elseif clause. |
2387 | 2368 |
2388 tree_if_clause * | 2369 tree_if_clause * |
2389 octave_parser::make_elseif_clause (token *elseif_tok, tree_expression *expr, | 2370 octave_base_parser::make_elseif_clause (token *elseif_tok, |
2390 tree_statement_list *list, | 2371 tree_expression *expr, |
2391 octave_comment_list *lc) | 2372 tree_statement_list *list, |
2373 octave_comment_list *lc) | |
2392 { | 2374 { |
2393 maybe_warn_assign_as_truth_value (expr); | 2375 maybe_warn_assign_as_truth_value (expr); |
2394 | 2376 |
2395 int l = elseif_tok->line (); | 2377 int l = elseif_tok->line (); |
2396 int c = elseif_tok->column (); | 2378 int c = elseif_tok->column (); |
2399 } | 2381 } |
2400 | 2382 |
2401 // Finish a switch command. | 2383 // Finish a switch command. |
2402 | 2384 |
2403 tree_switch_command * | 2385 tree_switch_command * |
2404 octave_parser::finish_switch_command (token *switch_tok, tree_expression *expr, | 2386 octave_base_parser::finish_switch_command (token *switch_tok, |
2405 tree_switch_case_list *list, | 2387 tree_expression *expr, |
2406 token *end_tok, octave_comment_list *lc) | 2388 tree_switch_case_list *list, |
2389 token *end_tok, | |
2390 octave_comment_list *lc) | |
2407 { | 2391 { |
2408 tree_switch_command *retval = 0; | 2392 tree_switch_command *retval = 0; |
2409 | 2393 |
2410 if (end_token_ok (end_tok, token::switch_end)) | 2394 if (end_token_ok (end_tok, token::switch_end)) |
2411 { | 2395 { |
2432 } | 2416 } |
2433 | 2417 |
2434 // Build a switch case. | 2418 // Build a switch case. |
2435 | 2419 |
2436 tree_switch_case * | 2420 tree_switch_case * |
2437 octave_parser::make_switch_case (token *case_tok, tree_expression *expr, | 2421 octave_base_parser::make_switch_case (token *case_tok, |
2438 tree_statement_list *list, | 2422 tree_expression *expr, |
2439 octave_comment_list *lc) | 2423 tree_statement_list *list, |
2424 octave_comment_list *lc) | |
2440 { | 2425 { |
2441 maybe_warn_variable_switch_label (expr); | 2426 maybe_warn_variable_switch_label (expr); |
2442 | 2427 |
2443 int l = case_tok->line (); | 2428 int l = case_tok->line (); |
2444 int c = case_tok->column (); | 2429 int c = case_tok->column (); |
2447 } | 2432 } |
2448 | 2433 |
2449 // Build an assignment to a variable. | 2434 // Build an assignment to a variable. |
2450 | 2435 |
2451 tree_expression * | 2436 tree_expression * |
2452 octave_parser::make_assign_op (int op, tree_argument_list *lhs, token *eq_tok, | 2437 octave_base_parser::make_assign_op (int op, tree_argument_list *lhs, |
2453 tree_expression *rhs) | 2438 token *eq_tok, tree_expression *rhs) |
2454 { | 2439 { |
2455 tree_expression *retval = 0; | 2440 tree_expression *retval = 0; |
2456 | 2441 |
2457 octave_value::assign_op t = octave_value::unknown_assign_op; | 2442 octave_value::assign_op t = octave_value::unknown_assign_op; |
2458 | 2443 |
2543 } | 2528 } |
2544 | 2529 |
2545 // Define a script. | 2530 // Define a script. |
2546 | 2531 |
2547 void | 2532 void |
2548 octave_parser::make_script (tree_statement_list *cmds, | 2533 octave_base_parser::make_script (tree_statement_list *cmds, |
2549 tree_statement *end_script) | 2534 tree_statement *end_script) |
2550 { | 2535 { |
2551 if (! cmds) | 2536 if (! cmds) |
2552 cmds = new tree_statement_list (); | 2537 cmds = new tree_statement_list (); |
2553 | 2538 |
2554 cmds->append (end_script); | 2539 cmds->append (end_script); |
2555 | 2540 |
2556 octave_user_script *script | 2541 octave_user_script *script |
2557 = new octave_user_script (curr_lexer->fcn_file_full_name, | 2542 = new octave_user_script (curr_lexer.fcn_file_full_name, |
2558 curr_lexer->fcn_file_name, | 2543 curr_lexer.fcn_file_name, |
2559 cmds, curr_lexer->help_text); | 2544 cmds, curr_lexer.help_text); |
2560 | 2545 |
2561 curr_lexer->help_text = ""; | 2546 curr_lexer.help_text = ""; |
2562 | 2547 |
2563 octave_time now; | 2548 octave_time now; |
2564 | 2549 |
2565 script->stash_fcn_file_time (now); | 2550 script->stash_fcn_file_time (now); |
2566 | 2551 |
2568 } | 2553 } |
2569 | 2554 |
2570 // Begin defining a function. | 2555 // Begin defining a function. |
2571 | 2556 |
2572 octave_user_function * | 2557 octave_user_function * |
2573 octave_parser::start_function (tree_parameter_list *param_list, | 2558 octave_base_parser::start_function (tree_parameter_list *param_list, |
2574 tree_statement_list *body, | 2559 tree_statement_list *body, |
2575 tree_statement *end_fcn_stmt) | 2560 tree_statement *end_fcn_stmt) |
2576 { | 2561 { |
2577 // We'll fill in the return list later. | 2562 // We'll fill in the return list later. |
2578 | 2563 |
2579 if (! body) | 2564 if (! body) |
2580 body = new tree_statement_list (); | 2565 body = new tree_statement_list (); |
2594 | 2579 |
2595 return fcn; | 2580 return fcn; |
2596 } | 2581 } |
2597 | 2582 |
2598 tree_statement * | 2583 tree_statement * |
2599 octave_parser::make_end (const std::string& type, int l, int c) | 2584 octave_base_parser::make_end (const std::string& type, int l, int c) |
2600 { | 2585 { |
2601 return make_statement (new tree_no_op_command (type, l, c)); | 2586 return make_statement (new tree_no_op_command (type, l, c)); |
2602 } | 2587 } |
2603 | 2588 |
2604 // Do most of the work for defining a function. | 2589 // Do most of the work for defining a function. |
2605 | 2590 |
2606 octave_user_function * | 2591 octave_user_function * |
2607 octave_parser::frob_function (const std::string& fname, | 2592 octave_base_parser::frob_function (const std::string& fname, |
2608 octave_user_function *fcn) | 2593 octave_user_function *fcn) |
2609 { | 2594 { |
2610 std::string id_name = fname; | 2595 std::string id_name = fname; |
2611 | 2596 |
2612 // If input is coming from a file, issue a warning if the name of | 2597 // If input is coming from a file, issue a warning if the name of |
2613 // the file does not match the name of the function stated in the | 2598 // the file does not match the name of the function stated in the |
2614 // file. Matlab doesn't provide a diagnostic (it ignores the stated | 2599 // file. Matlab doesn't provide a diagnostic (it ignores the stated |
2615 // name). | 2600 // name). |
2616 if (! autoloading && curr_lexer->reading_fcn_file | 2601 if (! autoloading && curr_lexer.reading_fcn_file |
2617 && curr_fcn_depth == 1 && ! parsing_subfunctions) | 2602 && curr_fcn_depth == 1 && ! parsing_subfunctions) |
2618 { | 2603 { |
2619 // FIXME -- should curr_lexer->fcn_file_name already be | 2604 // FIXME -- should curr_lexer.fcn_file_name already be |
2620 // preprocessed when we get here? It seems to only be a | 2605 // preprocessed when we get here? It seems to only be a |
2621 // problem with relative file names. | 2606 // problem with relative file names. |
2622 | 2607 |
2623 std::string nm = curr_lexer->fcn_file_name; | 2608 std::string nm = curr_lexer.fcn_file_name; |
2624 | 2609 |
2625 size_t pos = nm.find_last_of (file_ops::dir_sep_chars ()); | 2610 size_t pos = nm.find_last_of (file_ops::dir_sep_chars ()); |
2626 | 2611 |
2627 if (pos != std::string::npos) | 2612 if (pos != std::string::npos) |
2628 nm = curr_lexer->fcn_file_name.substr (pos+1); | 2613 nm = curr_lexer.fcn_file_name.substr (pos+1); |
2629 | 2614 |
2630 if (nm != id_name) | 2615 if (nm != id_name) |
2631 { | 2616 { |
2632 warning_with_id | 2617 warning_with_id |
2633 ("Octave:function-name-clash", | 2618 ("Octave:function-name-clash", |
2634 "function name '%s' does not agree with function file name '%s'", | 2619 "function name '%s' does not agree with function file name '%s'", |
2635 id_name.c_str (), curr_lexer->fcn_file_full_name.c_str ()); | 2620 id_name.c_str (), curr_lexer.fcn_file_full_name.c_str ()); |
2636 | 2621 |
2637 id_name = nm; | 2622 id_name = nm; |
2638 } | 2623 } |
2639 } | 2624 } |
2640 | 2625 |
2641 if (curr_lexer->reading_fcn_file || curr_lexer->reading_classdef_file || autoloading) | 2626 if (curr_lexer.reading_fcn_file || curr_lexer.reading_classdef_file || autoloading) |
2642 { | 2627 { |
2643 octave_time now; | 2628 octave_time now; |
2644 | 2629 |
2645 fcn->stash_fcn_file_name (curr_lexer->fcn_file_full_name); | 2630 fcn->stash_fcn_file_name (curr_lexer.fcn_file_full_name); |
2646 fcn->stash_fcn_file_time (now); | 2631 fcn->stash_fcn_file_time (now); |
2647 fcn->mark_as_system_fcn_file (); | 2632 fcn->mark_as_system_fcn_file (); |
2648 | 2633 |
2649 if (fcn_file_from_relative_lookup) | 2634 if (fcn_file_from_relative_lookup) |
2650 fcn->mark_relative (); | 2635 fcn->mark_relative (); |
2651 | 2636 |
2652 if (curr_fcn_depth > 1 || parsing_subfunctions) | 2637 if (curr_fcn_depth > 1 || parsing_subfunctions) |
2653 { | 2638 { |
2654 fcn->stash_parent_fcn_name (curr_lexer->fcn_file_name); | 2639 fcn->stash_parent_fcn_name (curr_lexer.fcn_file_name); |
2655 | 2640 |
2656 if (curr_fcn_depth > 1) | 2641 if (curr_fcn_depth > 1) |
2657 fcn->stash_parent_fcn_scope (function_scopes[function_scopes.size ()-2]); | 2642 fcn->stash_parent_fcn_scope (function_scopes[function_scopes.size ()-2]); |
2658 else | 2643 else |
2659 fcn->stash_parent_fcn_scope (primary_fcn_scope); | 2644 fcn->stash_parent_fcn_scope (primary_fcn_scope); |
2660 } | 2645 } |
2661 | 2646 |
2662 if (curr_lexer->parsing_class_method) | 2647 if (curr_lexer.parsing_class_method) |
2663 { | 2648 { |
2664 if (curr_class_name == id_name) | 2649 if (curr_class_name == id_name) |
2665 fcn->mark_as_class_constructor (); | 2650 fcn->mark_as_class_constructor (); |
2666 else | 2651 else |
2667 fcn->mark_as_class_method (); | 2652 fcn->mark_as_class_method (); |
2676 if (fs && fs.is_newer (now)) | 2661 if (fs && fs.is_newer (now)) |
2677 warning_with_id ("Octave:future-time-stamp", | 2662 warning_with_id ("Octave:future-time-stamp", |
2678 "time stamp for '%s' is in the future", nm.c_str ()); | 2663 "time stamp for '%s' is in the future", nm.c_str ()); |
2679 } | 2664 } |
2680 else if (! input_from_tmp_history_file | 2665 else if (! input_from_tmp_history_file |
2681 && ! curr_lexer->force_script | 2666 && ! curr_lexer.force_script |
2682 && curr_lexer->reading_script_file | 2667 && curr_lexer.reading_script_file |
2683 && curr_lexer->fcn_file_name == id_name) | 2668 && curr_lexer.fcn_file_name == id_name) |
2684 { | 2669 { |
2685 warning ("function '%s' defined within script file '%s'", | 2670 warning ("function '%s' defined within script file '%s'", |
2686 id_name.c_str (), curr_lexer->fcn_file_full_name.c_str ()); | 2671 id_name.c_str (), curr_lexer.fcn_file_full_name.c_str ()); |
2687 } | 2672 } |
2688 | 2673 |
2689 fcn->stash_function_name (id_name); | 2674 fcn->stash_function_name (id_name); |
2690 fcn->stash_fcn_location (curr_lexer->input_line_number, | 2675 fcn->stash_fcn_location (curr_lexer.input_line_number, |
2691 curr_lexer->current_input_column); | 2676 curr_lexer.current_input_column); |
2692 | 2677 |
2693 if (! curr_lexer->help_text.empty () && curr_fcn_depth == 1 | 2678 if (! curr_lexer.help_text.empty () && curr_fcn_depth == 1 |
2694 && ! parsing_subfunctions) | 2679 && ! parsing_subfunctions) |
2695 { | 2680 { |
2696 fcn->document (curr_lexer->help_text); | 2681 fcn->document (curr_lexer.help_text); |
2697 | 2682 |
2698 curr_lexer->help_text = ""; | 2683 curr_lexer.help_text = ""; |
2699 } | 2684 } |
2700 | 2685 |
2701 if (curr_lexer->reading_fcn_file && curr_fcn_depth == 1 | 2686 if (curr_lexer.reading_fcn_file && curr_fcn_depth == 1 |
2702 && ! parsing_subfunctions) | 2687 && ! parsing_subfunctions) |
2703 primary_fcn_ptr = fcn; | 2688 primary_fcn_ptr = fcn; |
2704 | 2689 |
2705 return fcn; | 2690 return fcn; |
2706 } | 2691 } |
2707 | 2692 |
2708 tree_function_def * | 2693 tree_function_def * |
2709 octave_parser::finish_function (tree_parameter_list *ret_list, | 2694 octave_base_parser::finish_function (tree_parameter_list *ret_list, |
2710 octave_user_function *fcn, | 2695 octave_user_function *fcn, |
2711 octave_comment_list *lc) | 2696 octave_comment_list *lc) |
2712 { | 2697 { |
2713 tree_function_def *retval = 0; | 2698 tree_function_def *retval = 0; |
2714 | 2699 |
2715 if (ret_list) | 2700 if (ret_list) |
2716 ret_list->mark_as_formal_parameters (); | 2701 ret_list->mark_as_formal_parameters (); |
2749 } | 2734 } |
2750 | 2735 |
2751 if (curr_fcn_depth == 1 && fcn) | 2736 if (curr_fcn_depth == 1 && fcn) |
2752 symbol_table::update_nest (fcn->scope ()); | 2737 symbol_table::update_nest (fcn->scope ()); |
2753 | 2738 |
2754 if (! curr_lexer->reading_fcn_file && curr_fcn_depth == 1) | 2739 if (! curr_lexer.reading_fcn_file && curr_fcn_depth == 1) |
2755 { | 2740 { |
2756 // We are either reading a script file or defining a function | 2741 // We are either reading a script file or defining a function |
2757 // at the command line, so this definition creates a | 2742 // at the command line, so this definition creates a |
2758 // tree_function object that is placed in the parse tree. | 2743 // tree_function object that is placed in the parse tree. |
2759 // Otherwise, it is just inserted in the symbol table, | 2744 // Otherwise, it is just inserted in the symbol table, |
2769 | 2754 |
2770 return retval; | 2755 return retval; |
2771 } | 2756 } |
2772 | 2757 |
2773 void | 2758 void |
2774 octave_parser::recover_from_parsing_function (void) | 2759 octave_base_parser::recover_from_parsing_function (void) |
2775 { | 2760 { |
2776 if (parser_symtab_context.empty ()) | 2761 if (parser_symtab_context.empty ()) |
2777 panic_impossible (); | 2762 panic_impossible (); |
2778 | 2763 |
2779 parser_symtab_context.pop (); | 2764 parser_symtab_context.pop (); |
2780 | 2765 |
2781 if (curr_lexer->reading_fcn_file && curr_fcn_depth == 1 | 2766 if (curr_lexer.reading_fcn_file && curr_fcn_depth == 1 |
2782 && ! parsing_subfunctions) | 2767 && ! parsing_subfunctions) |
2783 parsing_subfunctions = true; | 2768 parsing_subfunctions = true; |
2784 | 2769 |
2785 curr_fcn_depth--; | 2770 curr_fcn_depth--; |
2786 function_scopes.pop_back (); | 2771 function_scopes.pop_back (); |
2787 | 2772 |
2788 curr_lexer->defining_func--; | 2773 curr_lexer.defining_func--; |
2789 curr_lexer->parsed_function_name.pop (); | 2774 curr_lexer.parsed_function_name.pop (); |
2790 curr_lexer->looking_at_return_list = false; | 2775 curr_lexer.looking_at_return_list = false; |
2791 curr_lexer->looking_at_parameter_list = false; | 2776 curr_lexer.looking_at_parameter_list = false; |
2792 } | 2777 } |
2793 | 2778 |
2794 // Make an index expression. | 2779 // Make an index expression. |
2795 | 2780 |
2796 tree_index_expression * | 2781 tree_index_expression * |
2797 octave_parser::make_index_expression (tree_expression *expr, | 2782 octave_base_parser::make_index_expression (tree_expression *expr, |
2798 tree_argument_list *args, char type) | 2783 tree_argument_list *args, |
2784 char type) | |
2799 { | 2785 { |
2800 tree_index_expression *retval = 0; | 2786 tree_index_expression *retval = 0; |
2801 | 2787 |
2802 if (args && args->has_magic_tilde ()) | 2788 if (args && args->has_magic_tilde ()) |
2803 { | 2789 { |
2825 } | 2811 } |
2826 | 2812 |
2827 // Make an indirect reference expression. | 2813 // Make an indirect reference expression. |
2828 | 2814 |
2829 tree_index_expression * | 2815 tree_index_expression * |
2830 octave_parser::make_indirect_ref (tree_expression *expr, | 2816 octave_base_parser::make_indirect_ref (tree_expression *expr, |
2831 const std::string& elt) | 2817 const std::string& elt) |
2832 { | 2818 { |
2833 tree_index_expression *retval = 0; | 2819 tree_index_expression *retval = 0; |
2834 | 2820 |
2835 int l = expr->line (); | 2821 int l = expr->line (); |
2836 int c = expr->column (); | 2822 int c = expr->column (); |
2844 retval = tmp; | 2830 retval = tmp; |
2845 } | 2831 } |
2846 else | 2832 else |
2847 retval = new tree_index_expression (expr, elt, l, c); | 2833 retval = new tree_index_expression (expr, elt, l, c); |
2848 | 2834 |
2849 curr_lexer->looking_at_indirect_ref = false; | 2835 curr_lexer.looking_at_indirect_ref = false; |
2850 | 2836 |
2851 return retval; | 2837 return retval; |
2852 } | 2838 } |
2853 | 2839 |
2854 // Make an indirect reference expression with dynamic field name. | 2840 // Make an indirect reference expression with dynamic field name. |
2855 | 2841 |
2856 tree_index_expression * | 2842 tree_index_expression * |
2857 octave_parser::make_indirect_ref (tree_expression *expr, tree_expression *elt) | 2843 octave_base_parser::make_indirect_ref (tree_expression *expr, tree_expression *elt) |
2858 { | 2844 { |
2859 tree_index_expression *retval = 0; | 2845 tree_index_expression *retval = 0; |
2860 | 2846 |
2861 int l = expr->line (); | 2847 int l = expr->line (); |
2862 int c = expr->column (); | 2848 int c = expr->column (); |
2870 retval = tmp; | 2856 retval = tmp; |
2871 } | 2857 } |
2872 else | 2858 else |
2873 retval = new tree_index_expression (expr, elt, l, c); | 2859 retval = new tree_index_expression (expr, elt, l, c); |
2874 | 2860 |
2875 curr_lexer->looking_at_indirect_ref = false; | 2861 curr_lexer.looking_at_indirect_ref = false; |
2876 | 2862 |
2877 return retval; | 2863 return retval; |
2878 } | 2864 } |
2879 | 2865 |
2880 // Make a declaration command. | 2866 // Make a declaration command. |
2881 | 2867 |
2882 tree_decl_command * | 2868 tree_decl_command * |
2883 octave_parser::make_decl_command (int tok, token *tok_val, | 2869 octave_base_parser::make_decl_command (int tok, token *tok_val, |
2884 tree_decl_init_list *lst) | 2870 tree_decl_init_list *lst) |
2885 { | 2871 { |
2886 tree_decl_command *retval = 0; | 2872 tree_decl_command *retval = 0; |
2887 | 2873 |
2888 int l = tok_val->line (); | 2874 int l = tok_val->line (); |
2889 int c = tok_val->column (); | 2875 int c = tok_val->column (); |
2897 case PERSISTENT: | 2883 case PERSISTENT: |
2898 if (curr_fcn_depth > 0) | 2884 if (curr_fcn_depth > 0) |
2899 retval = new tree_persistent_command (lst, l, c); | 2885 retval = new tree_persistent_command (lst, l, c); |
2900 else | 2886 else |
2901 { | 2887 { |
2902 if (curr_lexer->reading_script_file) | 2888 if (curr_lexer.reading_script_file) |
2903 warning ("ignoring persistent declaration near line %d of file '%s'", | 2889 warning ("ignoring persistent declaration near line %d of file '%s'", |
2904 l, curr_lexer->fcn_file_full_name.c_str ()); | 2890 l, curr_lexer.fcn_file_full_name.c_str ()); |
2905 else | 2891 else |
2906 warning ("ignoring persistent declaration near line %d", l); | 2892 warning ("ignoring persistent declaration near line %d", l); |
2907 } | 2893 } |
2908 break; | 2894 break; |
2909 | 2895 |
2914 | 2900 |
2915 return retval; | 2901 return retval; |
2916 } | 2902 } |
2917 | 2903 |
2918 bool | 2904 bool |
2919 octave_parser::validate_array_list (tree_expression *e) | 2905 octave_base_parser::validate_array_list (tree_expression *e) |
2920 { | 2906 { |
2921 bool retval = true; | 2907 bool retval = true; |
2922 | 2908 |
2923 tree_array_list *al = dynamic_cast<tree_array_list *> (e); | 2909 tree_array_list *al = dynamic_cast<tree_array_list *> (e); |
2924 | 2910 |
2939 | 2925 |
2940 return retval; | 2926 return retval; |
2941 } | 2927 } |
2942 | 2928 |
2943 tree_argument_list * | 2929 tree_argument_list * |
2944 octave_parser::validate_matrix_for_assignment (tree_expression *e) | 2930 octave_base_parser::validate_matrix_for_assignment (tree_expression *e) |
2945 { | 2931 { |
2946 tree_argument_list *retval = 0; | 2932 tree_argument_list *retval = 0; |
2947 | 2933 |
2948 if (e->is_constant ()) | 2934 if (e->is_constant ()) |
2949 { | 2935 { |
2993 } | 2979 } |
2994 | 2980 |
2995 // Finish building an array_list. | 2981 // Finish building an array_list. |
2996 | 2982 |
2997 tree_expression * | 2983 tree_expression * |
2998 octave_parser::finish_array_list (tree_array_list *array_list) | 2984 octave_base_parser::finish_array_list (tree_array_list *array_list) |
2999 { | 2985 { |
3000 tree_expression *retval = array_list; | 2986 tree_expression *retval = array_list; |
3001 | 2987 |
3002 unwind_protect frame; | 2988 unwind_protect frame; |
3003 | 2989 |
3038 } | 3024 } |
3039 | 3025 |
3040 // Finish building a matrix list. | 3026 // Finish building a matrix list. |
3041 | 3027 |
3042 tree_expression * | 3028 tree_expression * |
3043 octave_parser::finish_matrix (tree_matrix *m) | 3029 octave_base_parser::finish_matrix (tree_matrix *m) |
3044 { | 3030 { |
3045 return finish_array_list (m); | 3031 return finish_array_list (m); |
3046 } | 3032 } |
3047 | 3033 |
3048 // Finish building a cell list. | 3034 // Finish building a cell list. |
3049 | 3035 |
3050 tree_expression * | 3036 tree_expression * |
3051 octave_parser::finish_cell (tree_cell *c) | 3037 octave_base_parser::finish_cell (tree_cell *c) |
3052 { | 3038 { |
3053 return finish_array_list (c); | 3039 return finish_array_list (c); |
3054 } | 3040 } |
3055 | 3041 |
3056 void | 3042 void |
3057 octave_parser::maybe_warn_missing_semi (tree_statement_list *t) | 3043 octave_base_parser::maybe_warn_missing_semi (tree_statement_list *t) |
3058 { | 3044 { |
3059 if (curr_fcn_depth > 0) | 3045 if (curr_fcn_depth > 0) |
3060 { | 3046 { |
3061 tree_statement *tmp = t->back (); | 3047 tree_statement *tmp = t->back (); |
3062 | 3048 |
3063 if (tmp->is_expression ()) | 3049 if (tmp->is_expression ()) |
3064 warning_with_id | 3050 warning_with_id |
3065 ("Octave:missing-semicolon", | 3051 ("Octave:missing-semicolon", |
3066 "missing semicolon near line %d, column %d in file '%s'", | 3052 "missing semicolon near line %d, column %d in file '%s'", |
3067 tmp->line (), tmp->column (), curr_lexer->fcn_file_full_name.c_str ()); | 3053 tmp->line (), tmp->column (), curr_lexer.fcn_file_full_name.c_str ()); |
3068 } | 3054 } |
3069 } | 3055 } |
3070 | 3056 |
3071 tree_statement_list * | 3057 tree_statement_list * |
3072 octave_parser::set_stmt_print_flag (tree_statement_list *list, char sep, | 3058 octave_base_parser::set_stmt_print_flag (tree_statement_list *list, |
3073 bool warn_missing_semi) | 3059 char sep, bool warn_missing_semi) |
3074 { | 3060 { |
3075 tree_statement *tmp = list->back (); | 3061 tree_statement *tmp = list->back (); |
3076 | 3062 |
3077 switch (sep) | 3063 switch (sep) |
3078 { | 3064 { |
3104 | 3090 |
3105 return list; | 3091 return list; |
3106 } | 3092 } |
3107 | 3093 |
3108 tree_statement_list * | 3094 tree_statement_list * |
3109 octave_parser::make_statement_list (tree_statement *stmt) | 3095 octave_base_parser::make_statement_list (tree_statement *stmt) |
3110 { | 3096 { |
3111 return new tree_statement_list (stmt); | 3097 return new tree_statement_list (stmt); |
3112 } | 3098 } |
3113 | 3099 |
3114 tree_statement_list * | 3100 tree_statement_list * |
3115 octave_parser::append_statement_list (tree_statement_list *list, char sep, | 3101 octave_base_parser::append_statement_list (tree_statement_list *list, |
3116 tree_statement *stmt, | 3102 char sep, tree_statement *stmt, |
3117 bool warn_missing_semi) | 3103 bool warn_missing_semi) |
3118 { | 3104 { |
3119 set_stmt_print_flag (list, sep, warn_missing_semi); | 3105 set_stmt_print_flag (list, sep, warn_missing_semi); |
3120 | 3106 |
3121 list->append (stmt); | 3107 list->append (stmt); |
3122 | 3108 |
3123 return list; | 3109 return list; |
3124 } | 3110 } |
3125 | 3111 |
3126 void | 3112 void |
3127 octave_parser::bison_error (const char *s) | 3113 octave_base_parser::bison_error (const char *s) |
3128 { | 3114 { |
3129 int err_col = curr_lexer->current_input_column - 1; | 3115 int err_col = curr_lexer.current_input_column - 1; |
3130 | 3116 |
3131 std::ostringstream output_buf; | 3117 std::ostringstream output_buf; |
3132 | 3118 |
3133 if (curr_lexer->reading_fcn_file || curr_lexer->reading_script_file || curr_lexer->reading_classdef_file) | 3119 if (curr_lexer.reading_fcn_file || curr_lexer.reading_script_file || curr_lexer.reading_classdef_file) |
3134 output_buf << "parse error near line " << curr_lexer->input_line_number | 3120 output_buf << "parse error near line " << curr_lexer.input_line_number |
3135 << " of file " << curr_lexer->fcn_file_full_name; | 3121 << " of file " << curr_lexer.fcn_file_full_name; |
3136 else | 3122 else |
3137 output_buf << "parse error:"; | 3123 output_buf << "parse error:"; |
3138 | 3124 |
3139 if (s && strcmp (s, "parse error") != 0) | 3125 if (s && strcmp (s, "parse error") != 0) |
3140 output_buf << "\n\n " << s; | 3126 output_buf << "\n\n " << s; |
3141 | 3127 |
3142 output_buf << "\n\n"; | 3128 output_buf << "\n\n"; |
3143 | 3129 |
3144 std::string curr_line = curr_lexer->current_input_line; | 3130 std::string curr_line = curr_lexer.current_input_line; |
3145 | 3131 |
3146 if (! curr_line.empty ()) | 3132 if (! curr_line.empty ()) |
3147 { | 3133 { |
3148 size_t len = curr_line.length (); | 3134 size_t len = curr_line.length (); |
3149 | 3135 |
3166 output_buf << "\n"; | 3152 output_buf << "\n"; |
3167 | 3153 |
3168 std::string msg = output_buf.str (); | 3154 std::string msg = output_buf.str (); |
3169 | 3155 |
3170 parse_error ("%s", msg.c_str ()); | 3156 parse_error ("%s", msg.c_str ()); |
3157 } | |
3158 | |
3159 int | |
3160 octave_parser::run (void) | |
3161 { | |
3162 return octave_parse (*this); | |
3171 } | 3163 } |
3172 | 3164 |
3173 static void | 3165 static void |
3174 safe_fclose (FILE *f) | 3166 safe_fclose (FILE *f) |
3175 { | 3167 { |
3214 | 3206 |
3215 frame.add_fcn (safe_fclose, ffile); | 3207 frame.add_fcn (safe_fclose, ffile); |
3216 | 3208 |
3217 if (ffile) | 3209 if (ffile) |
3218 { | 3210 { |
3219 // octave_parser constructor sets this for us. | 3211 // octave_base_parser constructor sets this for us. |
3220 frame.protect_var (CURR_LEXER); | 3212 frame.protect_var (CURR_LEXER); |
3221 | 3213 |
3222 octave_parser curr_parser (ffile); | 3214 octave_parser curr_parser (ffile); |
3223 | 3215 |
3224 curr_parser.curr_class_name = dispatch_type; | 3216 curr_parser.curr_class_name = dispatch_type; |
3225 curr_parser.autoloading = autoload; | 3217 curr_parser.autoloading = autoload; |
3226 curr_parser.fcn_file_from_relative_lookup = relative_lookup; | 3218 curr_parser.fcn_file_from_relative_lookup = relative_lookup; |
3227 | 3219 |
3228 curr_parser.curr_lexer->force_script = force_script; | 3220 curr_parser.curr_lexer.force_script = force_script; |
3229 curr_parser.curr_lexer->prep_for_file (); | 3221 curr_parser.curr_lexer.prep_for_file (); |
3230 curr_parser.curr_lexer->parsing_class_method = ! dispatch_type.empty (); | 3222 curr_parser.curr_lexer.parsing_class_method = ! dispatch_type.empty (); |
3231 | 3223 |
3232 curr_parser.curr_lexer->fcn_file_name = file; | 3224 curr_parser.curr_lexer.fcn_file_name = file; |
3233 curr_parser.curr_lexer->fcn_file_full_name = full_file; | 3225 curr_parser.curr_lexer.fcn_file_full_name = full_file; |
3234 | 3226 |
3235 int status = curr_parser.run (); | 3227 int status = curr_parser.run (); |
3236 | 3228 |
3237 fcn_ptr = curr_parser.primary_fcn_ptr; | 3229 fcn_ptr = curr_parser.primary_fcn_ptr; |
3238 | 3230 |
3910 { | 3902 { |
3911 octave_value_list retval; | 3903 octave_value_list retval; |
3912 | 3904 |
3913 unwind_protect frame; | 3905 unwind_protect frame; |
3914 | 3906 |
3915 // octave_parser constructor sets this for us. | 3907 // octave_base_parser constructor sets this for us. |
3916 frame.protect_var (CURR_LEXER); | 3908 frame.protect_var (CURR_LEXER); |
3917 | 3909 |
3918 octave_parser curr_parser (eval_str); | 3910 octave_parser curr_parser (eval_str); |
3919 | 3911 |
3920 do | 3912 do |
3970 || tree_return_command::returning | 3962 || tree_return_command::returning |
3971 || tree_break_command::breaking | 3963 || tree_break_command::breaking |
3972 || tree_continue_command::continuing) | 3964 || tree_continue_command::continuing) |
3973 break; | 3965 break; |
3974 } | 3966 } |
3975 else if (curr_parser.curr_lexer->end_of_input) | 3967 else if (curr_parser.curr_lexer.end_of_input) |
3976 break; | 3968 break; |
3977 } | 3969 } |
3978 } | 3970 } |
3979 while (parse_status == 0); | 3971 while (parse_status == 0); |
3980 | 3972 |