refactor heredoc identifier

This commit is contained in:
FUKUZAWA-Tadashi
2013-03-13 00:06:19 +09:00
committed by Masaki Muranaka
parent 7c1526da6f
commit 3bcaeb09b4
3 changed files with 81 additions and 102 deletions
+1 -2
View File
@@ -74,8 +74,7 @@ enum mrb_string_type {
str_sword = (STR_FUNC_PARSING|STR_FUNC_WORD|STR_FUNC_ARRAY),
str_dword = (STR_FUNC_PARSING|STR_FUNC_WORD|STR_FUNC_ARRAY|STR_FUNC_EXPAND),
str_ssym = (STR_FUNC_PARSING|STR_FUNC_SYMBOL),
str_sheredoc = (STR_FUNC_PARSING|STR_FUNC_HEREDOC),
str_dheredoc = (STR_FUNC_PARSING|STR_FUNC_HEREDOC|STR_FUNC_EXPAND),
str_heredoc = (STR_FUNC_PARSING|STR_FUNC_HEREDOC),
};
/* heredoc structure */
+77 -99
View File
@@ -874,49 +874,6 @@ end_strterm(parser_state *p)
p->lex_strterm = NULL;
}
static node*
heredoc_start_sb(parser_state *p, const char* term, size_t term_len, string_type type, int allow_indent)
{
node *newnode = new_heredoc(p);
parser_heredoc_info *inf = (parser_heredoc_info*)newnode->cdr;
inf->term = term;
inf->term_len = term_len;
inf->type = type;
inf->allow_indent = allow_indent;
inf->line_head = TRUE;
inf->doc = NULL;
p->heredocs = push(p->heredocs, newnode);
if (p->parsing_heredoc == NULL) {
node *c = p->heredocs;
while (c->cdr)
c = c->cdr;
p->parsing_heredoc = c;
}
p->heredoc_starts_nextline = TRUE;
p->lstate = EXPR_END;
return newnode;
}
static node*
heredoc_start(parser_state *p, node *beg, node *str, string_type type)
{
char *bs = (char*)beg->cdr->car;
int allow_indent = (bs[2] == '-');
const char *s = (char*)str->cdr->car;
size_t len = (intptr_t)str->cdr->cdr;
return heredoc_start_sb(p, s, len, type, allow_indent);
}
static node*
heredoc_start_sym(parser_state *p, node *beg, mrb_sym sym, string_type type)
{
char *bs = (char*)beg->cdr->car;
int allow_indent = (bs[2] == '-');
size_t len;
const char *s = mrb_sym2name_len(p->mrb, sym, &len);
return heredoc_start_sb(p, s, len, type, allow_indent);
}
parser_heredoc_info *
parsing_heredoc_inf(parser_state *p)
{
@@ -947,7 +904,6 @@ heredoc_end(parser_state *p)
%}
%expect 2
%pure_parser
%parse-param {parser_state *p}
%lex-param {parser_state *p}
@@ -1064,7 +1020,7 @@ heredoc_end(parser_state *p)
%token tSTAR /* * */
%token tAMPER /* & */
%token tLAMBDA /* -> */
%token tSYMBEG tREGEXP_BEG tWORDS_BEG tQWORDS_BEG
%token tSYMBEG tREGEXP_BEG tWORDS_BEG
%token tSTRING_BEG tSTRING_DVAR tLAMBEG
%token <nd> tHEREDOC_BEG /* <<, <<- */
%token tHEREDOC_END tLITERAL_DELIM
@@ -2615,18 +2571,6 @@ string_interp : tSTRING_MID
p->lex_strterm = $<nd>2;
$$ = list2($1, $3);
}
| string_interp
tSTRING_PART
{
$<nd>$ = p->lex_strterm;
p->lex_strterm = NULL;
}
compstmt
'}'
{
p->lex_strterm = $<nd>3;
$$ = push(push($1, $2), $4);
}
| tLITERAL_DELIM
{
$$ = list1(new_literal_delim(p));
@@ -2643,25 +2587,9 @@ regexp : tREGEXP_BEG tREGEXP
}
;
heredoc : tHEREDOC_BEG tSTRING_BEG tSTRING
{
$$ = heredoc_start(p, $1, $3, str_dheredoc);
}
| tHEREDOC_BEG tSTRING
{
$$ = heredoc_start(p, $1, $2, str_sheredoc);
}
| tHEREDOC_BEG tIDENTIFIER
{
$$ = heredoc_start_sym(p, $1, $2, str_dheredoc);
}
| tHEREDOC_BEG tCONSTANT
{
$$ = heredoc_start_sym(p, $1, $2, str_dheredoc);
}
heredoc : tHEREDOC_BEG
;
opt_heredoc_bodies : none
| heredoc_bodies
;
@@ -2690,14 +2618,6 @@ words : tWORDS_BEG tSTRING
{
$$ = new_words(p, push($2, $3));
}
| tQWORDS_BEG tSTRING
{
$$ = new_words(p, list1($2));
}
| tQWORDS_BEG string_rep tSTRING
{
$$ = new_words(p, push($2, $3));
}
;
@@ -3734,7 +3654,77 @@ parse_string(parser_state *p)
yylval.nd = new_str(p, tok(p), toklen(p));
return tSTRING;
}
static int
heredoc_identifier(parser_state *p)
{
int c;
int type = str_heredoc;
int indent = FALSE;
int quote = FALSE;
node *newnode;
parser_heredoc_info *info;
c = nextc(p);
if (ISSPACE(c) || c == '=') {
pushback(p, c);
return 0;
}
if (c == '-') {
indent = TRUE;
c = nextc(p);
}
if (c == '\'' || c == '"') {
int term = c;
if (c == '\'')
quote = TRUE;
newtok(p);
while ((c = nextc(p)) != -1 && c != term) {
if (c == '\n')
c = -1;
tokadd(p, c);
}
if (c == -1) {
yyerror(p, "unterminated here document identifier");
return 0;
}
} else {
if (! identchar(c)) {
pushback(p, c);
if (indent) pushback(p, '-');
return 0;
}
newtok(p);
do {
tokadd(p, c);
} while ((c = nextc(p)) != -1 && identchar(c));
pushback(p, c);
}
tokfix(p);
newnode = new_heredoc(p);
info = (parser_heredoc_info*)newnode->cdr;
info->term = strndup(tok(p), toklen(p));
info->term_len = toklen(p);
if (! quote)
type |= STR_FUNC_EXPAND;
info->type = type;
info->allow_indent = indent;
info->line_head = TRUE;
info->doc = NULL;
p->heredocs = push(p->heredocs, newnode);
if (p->parsing_heredoc == NULL) {
node *n = p->heredocs;
while (n->cdr)
n = n->cdr;
p->parsing_heredoc = n;
}
p->heredoc_starts_nextline = TRUE;
p->lstate = EXPR_END;
yylval.nd = newnode;
return tHEREDOC_BEG;
}
static int
arg_ambiguous(parser_state *p)
@@ -3749,7 +3739,6 @@ static int
parser_yylex(parser_state *p)
{
register int c;
int c2;
int space_seen = 0;
int cmd_state;
enum mrb_lex_state_enum last_state;
@@ -3916,20 +3905,9 @@ parser_yylex(parser_state *p)
p->lstate != EXPR_CLASS &&
!IS_END() &&
(!IS_ARG() || space_seen)) {
/* heredocument check */
newtok(p); tokadd(p, '<'); tokadd(p, '<');
c2 = nextc(p);
if (c2 == '-') {
tokadd(p, c2);
c2 = nextc(p);
}
pushback(p, c2);
if (!ISSPACE(c2)) {
tokfix(p);
yylval.nd = new_str(p, tok(p), toklen(p));
p->lstate = EXPR_DOT;
return tHEREDOC_BEG;
}
int token = heredoc_identifier(p);
if (token)
return token;
}
if (p->lstate == EXPR_FNAME || p->lstate == EXPR_DOT) {
p->lstate = EXPR_ARG;
@@ -4625,7 +4603,7 @@ parser_yylex(parser_state *p)
case 'w':
p->lex_strterm = new_strterm(p, str_sword, term, paren);
return tQWORDS_BEG;
return tWORDS_BEG;
case 'r':
p->lex_strterm = new_strterm(p, str_regexp, term, paren);
+3 -1
View File
@@ -195,9 +195,11 @@ assert('Literals Symbol', '8.7.6.6') do
f = %s[asd \[
qwe]
g = %s/foo#{1+2}bar/
h = %s{{foo bar}}
a == :'asd qwe' and b == :"foo bar" and c == :a3b and d == :asd and
e == :' foo )' and f == :"asd [\nqwe" and g == :'foo#{1+2}bar'
e == :' foo )' and f == :"asd [\nqwe" and g == :'foo#{1+2}bar' and
h == :'{foo bar}'
end
# Not Implemented ATM assert('Literals Regular expression', '8.7.6.5') do