diff options
author | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2020-12-29 10:23:02 -0300 |
---|---|---|
committer | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2020-12-29 10:23:02 -0300 |
commit | 59e565d9555c07e82808d8c1db8f4f4d159b5e5c (patch) | |
tree | 7dced733d2e01a6060d656afad903539ac2fedc9 /testes | |
parent | 6188f3a654c0380db08eb40a5465ce8e71c784f5 (diff) | |
download | lua-59e565d9555c07e82808d8c1db8f4f4d159b5e5c.tar.gz lua-59e565d9555c07e82808d8c1db8f4f4d159b5e5c.tar.bz2 lua-59e565d9555c07e82808d8c1db8f4f4d159b5e5c.zip |
No need to recheck close method before calling it
A to-be-closed variable is constant and it must have a close metamethod
when it is created. A program has to go out of its way (e.g., by
changing the variable's metamethod) to invalidate that check. So,
it is not worth to test that again. If the program tampers with the
metamethod, Lua will raise a regular error when attempting to call it.
Diffstat (limited to 'testes')
-rw-r--r-- | testes/locals.lua | 46 |
1 files changed, 44 insertions, 2 deletions
diff --git a/testes/locals.lua b/testes/locals.lua index 84e0b03a..1b43609b 100644 --- a/testes/locals.lua +++ b/testes/locals.lua | |||
@@ -459,8 +459,50 @@ do -- errors due to non-closable values | |||
459 | getmetatable(xyz).__close = nil -- remove metamethod | 459 | getmetatable(xyz).__close = nil -- remove metamethod |
460 | end | 460 | end |
461 | local stat, msg = pcall(foo) | 461 | local stat, msg = pcall(foo) |
462 | assert(not stat and | 462 | assert(not stat and string.find(msg, "attempt to call a nil value")) |
463 | string.find(msg, "attempt to close non%-closable variable 'xyz'")) | 463 | end |
464 | |||
465 | |||
466 | do -- tbc inside close methods | ||
467 | local track = {} | ||
468 | local function foo () | ||
469 | local x <close> = func2close(function () | ||
470 | local xx <close> = func2close(function (_, msg) | ||
471 | assert(msg == nil) | ||
472 | track[#track + 1] = "xx" | ||
473 | end) | ||
474 | track[#track + 1] = "x" | ||
475 | end) | ||
476 | track[#track + 1] = "foo" | ||
477 | return 20, 30, 40 | ||
478 | end | ||
479 | local a, b, c, d = foo() | ||
480 | assert(a == 20 and b == 30 and c == 40 and d == nil) | ||
481 | assert(track[1] == "foo" and track[2] == "x" and track[3] == "xx") | ||
482 | |||
483 | -- again, with errors | ||
484 | local track = {} | ||
485 | local function foo () | ||
486 | local x0 <close> = func2close(function (_, msg) | ||
487 | assert(msg == 202) | ||
488 | track[#track + 1] = "x0" | ||
489 | end) | ||
490 | local x <close> = func2close(function () | ||
491 | local xx <close> = func2close(function (_, msg) | ||
492 | assert(msg == 101) | ||
493 | track[#track + 1] = "xx" | ||
494 | error(202) | ||
495 | end) | ||
496 | track[#track + 1] = "x" | ||
497 | error(101) | ||
498 | end) | ||
499 | track[#track + 1] = "foo" | ||
500 | return 20, 30, 40 | ||
501 | end | ||
502 | local st, msg = pcall(foo) | ||
503 | assert(not st and msg == 202) | ||
504 | assert(track[1] == "foo" and track[2] == "x" and track[3] == "xx" and | ||
505 | track[4] == "x0") | ||
464 | end | 506 | end |
465 | 507 | ||
466 | 508 | ||