@@ -86,8 +86,8 @@ Thus, it is a variable which shows the scanner’s state.
8686What states are there? Let’s look at the definitions.
8787
8888▼ `enum lex_state`
89-
90- pre(longlist). 61 static enum lex_state {
89+ <pre class="longlist">
90+ 61 static enum lex_state {
9191 62 EXPR_BEG, /* ignore newline, +/- is a sign. */
9292 63 EXPR_END, /* newline significant, +/- is a operator. */
9393 64 EXPR_ARG, /* newline significant, +/- is a operator. */
@@ -98,7 +98,9 @@ pre(longlist). 61 static enum lex_state {
9898 69 EXPR_DOT, /* right after `.' or `::', no reserved words. */
9999 70 EXPR_CLASS, /* immediate after `class', no here document. */
100100 71 } lex_state;
101+
101102(parse.y)
103+ </pre>
102104
103105The EXPR prefix stands for “expression”. `EXPR_BEG` is “Beginning of
104106expression” and `EXPR_DOT` is “inside the expression, after the dot”.
@@ -617,8 +619,8 @@ operators. In all, there are five - `kUNLESS_MOD kUNTIL_MOD kWHILE_MOD`
617619`kRESCUE_MOD` and `kIF_MOD` The distinction is made here:
618620
619621▼ `yylex`-Reserved word
620-
621- pre(longlist). 4173 struct kwtable *kw;
622+ <pre class="longlist">
623+ 4173 struct kwtable *kw;
6226244174
6236254175 /* See if it is a reserved word. */
6246264176 kw = rb_reserved_word(tok(), toklen());
@@ -644,7 +646,9 @@ pre(longlist). 4173 struct kwtable *kw;
6446464196 return kw->id[1];
6456474197 }
6466484198 }
649+
647650(parse.y)
651+ </pre>
648652
649653This is located at the end of `yylex` after the identifiers are scanned.
650654The part that handles modifiers is the last (innermost) `if`〜`else` Whether
@@ -657,9 +661,11 @@ structure defined in `keywords` and the hash function `rb_reserved_word()` is
657661created by `gperf`. I’ll show the structure here again.
658662
659663▼ `keywords` - `struct kwtable`
664+ <pre class="longlist">
665+ 1 struct kwtable {char *name; int id[2]; enum lex_state state;};
660666
661- pre(longlist). 1 struct kwtable {char *name; int id[2]; enum lex_state state;};
662667(keywords)
668+ </pre>
663669
664670I’ve already explained about `name` and `id[0]` - they are the reserved word
665671name and its symbol. Here I will speak about the remaining members.
@@ -789,16 +795,18 @@ It’s the only part tasked with processing `do` so looking at this code should
789795be enough to understand the criteria for making the distinction.
790796
791797▼ `yylex`-Identifier-Reserved word
792-
793- pre(longlist). 4183 if (kw->id[0] == kDO) {
798+ <pre class="longlist">
799+ 4183 if (kw->id[0] == kDO) {
7948004184 if (COND_P()) return kDO_COND;
7958014185 if (CMDARG_P() && state != EXPR_CMDARG)
7968024186 return kDO_BLOCK;
7978034187 if (state == EXPR_ENDARG)
7988044188 return kDO_BLOCK;
7998054189 return kDO;
8008064190 }
807+
801808(parse.y)
809+ </pre>
802810
803811It’s a little messy, but you only need the part associated with `kDO_COND`.
804812That is because only two comparisons are meaningful.
@@ -1384,8 +1392,8 @@ This is the important part. As shown previously, you can avoid a conflict by
13841392changing the `do` and `'{'` symbols.
13851393
13861394▼ `yylex`-`'{'`
1387-
1388- pre(longlist). 3884 case '{':
1395+ <pre class="longlist">
1396+ 3884 case '{':
138913973885 if (IS_ARG() || lex_state == EXPR_END)
139013983886 c = '{'; /* block (primary) */
139113993887 else if (lex_state == EXPR_ENDARG)
@@ -1396,7 +1404,9 @@ pre(longlist). 3884 case '{':
139614043892 CMDARG_PUSH(0);
139714053893 lex_state = EXPR_BEG;
139814063894 return c;
1407+
13991408(parse.y)
1409+ </pre>
14001410
14011411`IS_ARG()` is defined as
14021412
0 commit comments