diff options
| author | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2020-10-22 15:54:46 -0300 |
|---|---|---|
| committer | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2020-10-22 15:54:46 -0300 |
| commit | d742a193e57029d973aff0a5eb04d8ddd03fa0ff (patch) | |
| tree | f0850c8f60997909952cbb1db3f499f066fb1188 | |
| parent | e4a38eb0e828e9589c391171e2e1904a3b9698e7 (diff) | |
| download | lua-d742a193e57029d973aff0a5eb04d8ddd03fa0ff.tar.gz lua-d742a193e57029d973aff0a5eb04d8ddd03fa0ff.tar.bz2 lua-d742a193e57029d973aff0a5eb04d8ddd03fa0ff.zip | |
Comments
| -rw-r--r-- | llex.c | 25 | ||||
| -rw-r--r-- | lparser.c | 8 | ||||
| -rw-r--r-- | ltable.c | 27 |
3 files changed, 34 insertions, 26 deletions
| @@ -254,9 +254,10 @@ static int read_numeral (LexState *ls, SemInfo *seminfo) { | |||
| 254 | 254 | ||
| 255 | 255 | ||
| 256 | /* | 256 | /* |
| 257 | ** reads a sequence '[=*[' or ']=*]', leaving the last bracket. | 257 | ** read a sequence '[=*[' or ']=*]', leaving the last bracket. If |
| 258 | ** If sequence is well formed, return its number of '='s + 2; otherwise, | 258 | ** sequence is well formed, return its number of '='s + 2; otherwise, |
| 259 | ** return 1 if there is no '='s or 0 otherwise (an unfinished '[==...'). | 259 | ** return 1 if it is a single bracket (no '='s and no 2nd bracket); |
| 260 | ** otherwise (an unfinished '[==...') return 0. | ||
| 260 | */ | 261 | */ |
| 261 | static size_t skip_sep (LexState *ls) { | 262 | static size_t skip_sep (LexState *ls) { |
| 262 | size_t count = 0; | 263 | size_t count = 0; |
| @@ -481,34 +482,34 @@ static int llex (LexState *ls, SemInfo *seminfo) { | |||
| 481 | } | 482 | } |
| 482 | case '=': { | 483 | case '=': { |
| 483 | next(ls); | 484 | next(ls); |
| 484 | if (check_next1(ls, '=')) return TK_EQ; | 485 | if (check_next1(ls, '=')) return TK_EQ; /* '==' */ |
| 485 | else return '='; | 486 | else return '='; |
| 486 | } | 487 | } |
| 487 | case '<': { | 488 | case '<': { |
| 488 | next(ls); | 489 | next(ls); |
| 489 | if (check_next1(ls, '=')) return TK_LE; | 490 | if (check_next1(ls, '=')) return TK_LE; /* '<=' */ |
| 490 | else if (check_next1(ls, '<')) return TK_SHL; | 491 | else if (check_next1(ls, '<')) return TK_SHL; /* '<<' */ |
| 491 | else return '<'; | 492 | else return '<'; |
| 492 | } | 493 | } |
| 493 | case '>': { | 494 | case '>': { |
| 494 | next(ls); | 495 | next(ls); |
| 495 | if (check_next1(ls, '=')) return TK_GE; | 496 | if (check_next1(ls, '=')) return TK_GE; /* '>=' */ |
| 496 | else if (check_next1(ls, '>')) return TK_SHR; | 497 | else if (check_next1(ls, '>')) return TK_SHR; /* '>>' */ |
| 497 | else return '>'; | 498 | else return '>'; |
| 498 | } | 499 | } |
| 499 | case '/': { | 500 | case '/': { |
| 500 | next(ls); | 501 | next(ls); |
| 501 | if (check_next1(ls, '/')) return TK_IDIV; | 502 | if (check_next1(ls, '/')) return TK_IDIV; /* '//' */ |
| 502 | else return '/'; | 503 | else return '/'; |
| 503 | } | 504 | } |
| 504 | case '~': { | 505 | case '~': { |
| 505 | next(ls); | 506 | next(ls); |
| 506 | if (check_next1(ls, '=')) return TK_NE; | 507 | if (check_next1(ls, '=')) return TK_NE; /* '~=' */ |
| 507 | else return '~'; | 508 | else return '~'; |
| 508 | } | 509 | } |
| 509 | case ':': { | 510 | case ':': { |
| 510 | next(ls); | 511 | next(ls); |
| 511 | if (check_next1(ls, ':')) return TK_DBCOLON; | 512 | if (check_next1(ls, ':')) return TK_DBCOLON; /* '::' */ |
| 512 | else return ':'; | 513 | else return ':'; |
| 513 | } | 514 | } |
| 514 | case '"': case '\'': { /* short literal strings */ | 515 | case '"': case '\'': { /* short literal strings */ |
| @@ -547,7 +548,7 @@ static int llex (LexState *ls, SemInfo *seminfo) { | |||
| 547 | return TK_NAME; | 548 | return TK_NAME; |
| 548 | } | 549 | } |
| 549 | } | 550 | } |
| 550 | else { /* single-char tokens (+ - / ...) */ | 551 | else { /* single-char tokens ('+', '*', '%', '{', '}', ...) */ |
| 551 | int c = ls->current; | 552 | int c = ls->current; |
| 552 | next(ls); | 553 | next(ls); |
| 553 | return c; | 554 | return c; |
| @@ -945,7 +945,7 @@ static void setvararg (FuncState *fs, int nparams) { | |||
| 945 | 945 | ||
| 946 | 946 | ||
| 947 | static void parlist (LexState *ls) { | 947 | static void parlist (LexState *ls) { |
| 948 | /* parlist -> [ param { ',' param } ] */ | 948 | /* parlist -> [ {NAME ','} (NAME | '...') ] */ |
| 949 | FuncState *fs = ls->fs; | 949 | FuncState *fs = ls->fs; |
| 950 | Proto *f = fs->f; | 950 | Proto *f = fs->f; |
| 951 | int nparams = 0; | 951 | int nparams = 0; |
| @@ -953,12 +953,12 @@ static void parlist (LexState *ls) { | |||
| 953 | if (ls->t.token != ')') { /* is 'parlist' not empty? */ | 953 | if (ls->t.token != ')') { /* is 'parlist' not empty? */ |
| 954 | do { | 954 | do { |
| 955 | switch (ls->t.token) { | 955 | switch (ls->t.token) { |
| 956 | case TK_NAME: { /* param -> NAME */ | 956 | case TK_NAME: { |
| 957 | new_localvar(ls, str_checkname(ls)); | 957 | new_localvar(ls, str_checkname(ls)); |
| 958 | nparams++; | 958 | nparams++; |
| 959 | break; | 959 | break; |
| 960 | } | 960 | } |
| 961 | case TK_DOTS: { /* param -> '...' */ | 961 | case TK_DOTS: { |
| 962 | luaX_next(ls); | 962 | luaX_next(ls); |
| 963 | isvararg = 1; | 963 | isvararg = 1; |
| 964 | break; | 964 | break; |
| @@ -1752,7 +1752,7 @@ static void checktoclose (LexState *ls, int level) { | |||
| 1752 | 1752 | ||
| 1753 | 1753 | ||
| 1754 | static void localstat (LexState *ls) { | 1754 | static void localstat (LexState *ls) { |
| 1755 | /* stat -> LOCAL ATTRIB NAME {',' ATTRIB NAME} ['=' explist] */ | 1755 | /* stat -> LOCAL NAME ATTRIB { ',' NAME ATTRIB } ['=' explist] */ |
| 1756 | FuncState *fs = ls->fs; | 1756 | FuncState *fs = ls->fs; |
| 1757 | int toclose = -1; /* index of to-be-closed variable (if any) */ | 1757 | int toclose = -1; /* index of to-be-closed variable (if any) */ |
| 1758 | Vardesc *var; /* last variable */ | 1758 | Vardesc *var; /* last variable */ |
| @@ -166,17 +166,24 @@ static Node *mainpositionTV (const Table *t, const TValue *key) { | |||
| 166 | 166 | ||
| 167 | 167 | ||
| 168 | /* | 168 | /* |
| 169 | ** Check whether key 'k1' is equal to the key in node 'n2'. | 169 | ** Check whether key 'k1' is equal to the key in node 'n2'. This |
| 170 | ** This equality is raw, so there are no metamethods. Floats | 170 | ** equality is raw, so there are no metamethods. Floats with integer |
| 171 | ** with integer values have been normalized, so integers cannot | 171 | ** values have been normalized, so integers cannot be equal to |
| 172 | ** be equal to floats. It is assumed that 'eqshrstr' is simply | 172 | ** floats. It is assumed that 'eqshrstr' is simply pointer equality, so |
| 173 | ** pointer equality, so that short strings are handled in the | 173 | ** that short strings are handled in the default case. |
| 174 | ** default case. | ||
| 175 | ** A true 'deadok' means to accept dead keys as equal to their original | 174 | ** A true 'deadok' means to accept dead keys as equal to their original |
| 176 | ** values, which can only happen if the original key was collectable. | 175 | ** values. All dead keys are compared in the default case, by pointer |
| 177 | ** All dead values are compared in the default case, by pointer | 176 | ** identity. (Only collectable objects can produce dead keys.) Note that |
| 178 | ** identity. (Note that dead long strings are also compared by | 177 | ** dead long strings are also compared by identity. |
| 179 | ** identity). | 178 | ** Once a key is dead, its corresponding value may be collected, and |
| 179 | ** then another value can be created with the same address. If this | ||
| 180 | ** other value is given to 'next', 'equalkey' will signal a false | ||
| 181 | ** positive. In a regular traversal, this situation should never happen, | ||
| 182 | ** as all keys given to 'next' came from the table itself, and therefore | ||
| 183 | ** could not have been collected. Outside a regular traversal, we | ||
| 184 | ** have garbage in, garbage out. What is relevant is that this false | ||
| 185 | ** positive does not break anything. (In particular, 'next' will return | ||
| 186 | ** some other valid item on the table or nil.) | ||
| 180 | */ | 187 | */ |
| 181 | static int equalkey (const TValue *k1, const Node *n2, int deadok) { | 188 | static int equalkey (const TValue *k1, const Node *n2, int deadok) { |
| 182 | if ((rawtt(k1) != keytt(n2)) && /* not the same variants? */ | 189 | if ((rawtt(k1) != keytt(n2)) && /* not the same variants? */ |
