ruby-changes:50671
From: nobu <ko1@a...>
Date: Mon, 19 Mar 2018 17:21:32 +0900 (JST)
Subject: [ruby-changes:50671] nobu:r62836 (trunk): parse.y: mismatched indentations at middle
nobu 2018-03-19 17:21:26 +0900 (Mon, 19 Mar 2018) New Revision: 62836 https://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=revision&revision=62836 Log: parse.y: mismatched indentations at middle * parse.y (k_rescue, k_ensure, k_when, k_else, k_elsif): warn mismatched indentations at keywords in middle of blocks. Modified files: trunk/parse.y trunk/test/ruby/test_rubyoptions.rb Index: test/ruby/test_rubyoptions.rb =================================================================== --- test/ruby/test_rubyoptions.rb (revision 62835) +++ test/ruby/test_rubyoptions.rb (revision 62836) @@ -445,10 +445,17 @@ class TestRubyOptions < Test::Unit::Test https://github.com/ruby/ruby/blob/trunk/test/ruby/test_rubyoptions.rb#L445 "begin", "if false", "for _ in []", "while false", "def foo", "class X", "module M", ["-> do", "end"], ["-> {", "}"], + ["if false;", "else ; end"], + ["if false;", "elsif false ; end"], + ["begin", "rescue ; end"], + ["begin rescue", "else ; end"], + ["begin", "ensure ; end"], + ["case nil", "when true; end"], ].each do |b, e = 'end'| src = ["#{b}\n", " #{e}\n"] k = b[/\A\S+/] + e = e[/\A\S+/] a.for("no directives with #{b}") do err = ["#{t.path}:2: warning: mismatched indentations at '#{e}' with '#{k}' at 1"] Index: parse.y =================================================================== --- parse.y (revision 62835) +++ parse.y (revision 62836) @@ -738,6 +738,7 @@ PRINTF_ARGS(static void parser_compile_e https://github.com/ruby/ruby/blob/trunk/parse.y#L738 static void token_info_push(struct parser_params*, const char *token, const rb_code_location_t *loc); static void token_info_pop(struct parser_params*, const char *token, const rb_code_location_t *loc); +static void token_info_warn(struct parser_params *p, const char *token, token_info *ptinfo_beg, const rb_code_location_t *loc); %} %pure-parser @@ -2718,6 +2719,36 @@ k_def : keyword_def https://github.com/ruby/ruby/blob/trunk/parse.y#L2719 } ; +k_rescue : keyword_rescue + { + token_info_warn(p, "rescue", p->token_info, &@$); + } + ; + +k_ensure : keyword_ensure + { + token_info_warn(p, "ensure", p->token_info, &@$); + } + ; + +k_when : keyword_when + { + token_info_warn(p, "when", p->token_info, &@$); + } + ; + +k_else : keyword_else + { + token_info_warn(p, "else", p->token_info, &@$); + } + ; + +k_elsif : keyword_elsif + { + token_info_warn(p, "elsif", p->token_info, &@$); + } + ; + k_end : keyword_end { token_info_pop(p, "end", &@$); @@ -2741,7 +2772,7 @@ do : term https://github.com/ruby/ruby/blob/trunk/parse.y#L2772 ; if_tail : opt_else - | keyword_elsif expr_value then + | k_elsif expr_value then compstmt if_tail { @@ -2754,7 +2785,7 @@ if_tail : opt_else https://github.com/ruby/ruby/blob/trunk/parse.y#L2785 ; opt_else : none - | keyword_else compstmt + | k_else compstmt { /*%%%*/ $$ = $2; @@ -3236,7 +3267,7 @@ do_body : {$<vars>$ = dyna_push(p);} https://github.com/ruby/ruby/blob/trunk/parse.y#L3267 } ; -case_body : keyword_when args then +case_body : k_when args then compstmt cases { @@ -3252,7 +3283,7 @@ cases : opt_else https://github.com/ruby/ruby/blob/trunk/parse.y#L3283 | case_body ; -opt_rescue : keyword_rescue exc_list exc_var then +opt_rescue : k_rescue exc_list exc_var then compstmt opt_rescue { @@ -3291,7 +3322,7 @@ exc_var : tASSOC lhs https://github.com/ruby/ruby/blob/trunk/parse.y#L3322 | none ; -opt_ensure : keyword_ensure compstmt +opt_ensure : k_ensure compstmt { /*%%%*/ $$ = $2; @@ -4488,22 +4519,29 @@ token_info_push(struct parser_params *p, https://github.com/ruby/ruby/blob/trunk/parse.y#L4519 static void token_info_pop(struct parser_params *p, const char *token, const rb_code_location_t *loc) { - token_info *ptinfo_beg = p->token_info, ptinfo_end_body, *ptinfo_end = &ptinfo_end_body; - setup_token_info(ptinfo_end, p->lex.pbeg, loc); + token_info *ptinfo_beg = p->token_info; if (!ptinfo_beg) return; p->token_info = ptinfo_beg->next; /* indentation check of matched keywords (begin..end, if..end, etc.) */ - if (!p->token_info_enabled) goto ok; /* the check is off */ - if (ptinfo_beg->linenum == ptinfo_end->linenum) goto ok; /* ignore one-line block */ - if (ptinfo_beg->nonspc || ptinfo_end->nonspc) goto ok; /* ignore keyword in the middle of a line */ - if (ptinfo_beg->column == ptinfo_end->column) goto ok; /* the indents are matched */ + token_info_warn(p, token, ptinfo_beg, loc); + xfree(ptinfo_beg); +} + +static void +token_info_warn(struct parser_params *p, const char *token, token_info *ptinfo_beg, const rb_code_location_t *loc) +{ + token_info ptinfo_end_body, *ptinfo_end = &ptinfo_end_body; + if (!p->token_info_enabled) return; + if (!ptinfo_beg) return; + setup_token_info(ptinfo_end, p->lex.pbeg, loc); + if (ptinfo_beg->linenum == ptinfo_end->linenum) return; /* ignore one-line block */ + if (ptinfo_beg->nonspc || ptinfo_end->nonspc) return; /* ignore keyword in the middle of a line */ + if (ptinfo_beg->column == ptinfo_end->column) return; /* the indents are matched */ rb_warn3L(ptinfo_end->linenum, "mismatched indentations at '%s' with '%s' at %d", WARN_S(token), WARN_S(ptinfo_beg->token), WARN_I(ptinfo_beg->linenum)); -ok: - xfree(ptinfo_beg); } static int -- ML: ruby-changes@q... Info: http://www.atdot.net/~ko1/quickml/