--- parser3/src/main/compile.y 2001/02/23 09:43:14 1.25 +++ parser3/src/main/compile.y 2001/02/24 09:56:02 1.33 @@ -1,5 +1,5 @@ /* - $Id: compile.y,v 1.25 2001/02/23 09:43:14 paf Exp $ + $Id: compile.y,v 1.33 2001/02/24 09:56:02 paf Exp $ */ %{ @@ -124,19 +124,13 @@ name_without_curly_rdive_code: name_adva /* put */ -put: '$' name_expr_dive '(' constructor_value ')' { -/* - TODO: подсмотреть в $3, и если там первым элементом self, - то выкинуть его и делать не WITH_WRITE, а WITH_SELF - если ничего не осталось - $self(xxx) - обругать -*/ +put: '$' name_expr_wdive '(' constructor_value ')' { $$=$2; /* stack: context,name */ P($$, $4); /* stack: context,name,constructor_value */ OP($$, OP_CONSTRUCT); /* value=pop; name=pop; context=pop; construct(context,name,value) */ }; -name_expr_dive: name_expr_dive_write | name_expr_dive_root; -name_expr_dive_write: name_expr_dive_code { +name_expr_wdive: name_expr_wdive_write | name_expr_wdive_root; +name_expr_wdive_write: name_expr_dive_code { $$=N(POOL); Array *diving_code=$1; String *first_name=LA2S(diving_code); @@ -151,7 +145,7 @@ name_expr_dive_write: name_expr_dive_cod } /* diving code; stack: current context */ }; -name_expr_dive_root: ':' name_expr_dive_code { +name_expr_wdive_root: ':' name_expr_dive_code { $$=N(POOL); OP($$, OP_WITH_ROOT); /* stack: starting context */ P($$, $2); /* diving code; stack: context,name */ @@ -161,8 +155,9 @@ constructor_value: constructor_one_param_value | constructor_two_params_value /* $var(=;2*2) $var(%d;2*2) $var(+;1) */ ; + constructor_one_param_value: - empty /* optimized $var() case */ + empty_value /* optimized $var() case */ | STRING /* optimized $var(STRING) case */ | complex_constructor_param_value /* $var(something complex) */ ; @@ -172,10 +167,9 @@ complex_constructor_param_value: complex P($$, $1); /* some codes to that context */ OP($$, OP_REDUCE_EWPOOL); /* context=pop; stack: context.value() */ }; -complex_constructor_param_body: - codes__excluding_sole_str_literal -| codes__str__followed_by__excluding_sole_str_literal -; +complex_constructor_param_body: codes__excluding_sole_str_literal; +codes__excluding_sole_str_literal: action | code codes { $$=$1; P($$, $2) }; + constructor_two_params_value: STRING ';' constructor_one_param_value { char *operator_or_fmt=LA2S($1)->cstr(); $$=N(POOL); @@ -195,28 +189,10 @@ constructor_two_params_value: STRING ';' /* stack: ncontext name value */ }; - /* call */ -call: '^' name_expr_dive store_params EON { /* ^field.$method{vasya} */ -/* - TODO: подсмотреть в $3, и если там в первом элементе первая буква ":" - то выкинуть её и делать не OP_WITH_READ, а WITH_ROOT - TODO: подсмотреть в $3, и если там первым элементом self, - то выкинуть его и делать не OP_WITH_READ, а WITH_SELF - TODO: - если первым в $3 идёт result - то - выкинуть его - если там ещё что-то осталось, - то - не OP_WITH_READ, а WITH_RESULT - иначе // ^result(value) - обругать безобразие -*/ - $$=N(POOL); - OP($$, OP_WITH_READ); /* stack: starting context */ - P($$, $2); /* diving code; stack: context,method_name */ +call: '^' name_without_curly_rdive store_params EON { /* ^field.$method{vasya} */ + $$=$2; /* with_xxx,diving code; stack: context,method_name */ OP($$, OP_GET_METHOD_FRAME); /* stack: context,method_frame */ P($$, $3); /* filling method_frame.store_params */ OP($$, OP_CALL); /* method_frame=pop; ncontext=pop; call(ncontext,method_frame) */ @@ -225,18 +201,26 @@ call: '^' name_expr_dive store_params EO store_params: store_param | store_params store_param { $$=$1; P($$, $2) }; store_param: store_round_param | store_curly_param; store_round_param: '(' store_param_parts ')' {$$=$2}; -store_param_parts: store_param_part | store_param_parts ';' store_param_part { $$=$1; P($$, $3) }; -store_param_part: constructor_one_param_value { - $$=$1; - OP($$, OP_STORE_PARAM); -} +store_param_parts: + store_param_part +| store_param_parts ';' store_param_part { $$=$1; P($$, $3) } +; store_curly_param: '{' maybe_codes '}' { $$=N(POOL); - OP($$, OP_CODE_ARRAY); - AA($$, $2); - OP($$, OP_CREATE_JUNCTION); + PCA($$, $2); OP($$, OP_STORE_PARAM); }; +store_param_part: + empty /* optimized () case */ +| STRING { /* optimized (STRING) case */ + $$=$1; + OP($$, OP_STORE_PARAM); +} +| complex_constructor_param_value { /* (something complex) */ + $$=$1; + OP($$, OP_STORE_PARAM); +} +; /* name */ @@ -301,28 +285,18 @@ with: '$' name_without_curly_rdive '{' c OP($$, OP_WRITE); }; -/* codes_in_brackets */ +/* basics */ -codes__str__followed_by__excluding_sole_str_literal: - write_str_literal codes__excluding_sole_str_literal { - $$=$1; - P($$, $2); -} -; -codes__excluding_sole_str_literal: - action -| codes__excluding_sole_str_literal write_str_literal { - $$=$1; - P($$, $2); -} -; write_str_literal: STRING { - $$=$1; - OP($$, OP_WRITE); + if(LA2S($1)->size()) { + $$=$1; + OP($$, OP_WRITE); + } else { + // optimized case of special end of macro. see yylex + $$=N(POOL); + } }; - -/* */ - +empty_value: /* empty */ { $$=L(NEW VString(POOL)) }; empty: /* empty */ { $$=N(POOL) }; %% @@ -466,7 +440,7 @@ int yylex(YYSTYPE *lvalp, void *pc) { c==' '|| c=='\t' || c=='\n' || c==')' || c=='}') { pop_LS(PC); - PC->source--; PC->col--; + PC->source--; if(--PC->col<0) { PC->line--; PC->col=-1; } result=EON; goto break2; } @@ -634,13 +608,12 @@ int yylex(YYSTYPE *lvalp, void *pc) { goto break2; } pop_LS(PC); - PC->source--; PC->col--; + PC->source--; if(--PC->col<0) { PC->line--; PC->col=-1; } result=EON; goto break2; } if(c==0) { result=-1; -// PC->source--; PC->col--; break; } } @@ -653,8 +626,10 @@ break2: // strip last \n before LS_DEF_NAME or EOF if((c=='@' || c==0) && end[-1]=='\n') end--; - // append last piece - PC->string->APPEND(begin, end-begin, PC->file, begin_line/*, start_col*/); + if(end!=begin) { + // append last piece + PC->string->APPEND(begin, end-begin, PC->file, begin_line/*, start_col*/); + } // create STRING value: array of OP_VALUE+vstring *lvalp=L(NEW VString(PC->string)); // new pieces storage