aboutsummaryrefslogtreecommitdiff
path: root/testes
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2021-01-21 10:27:22 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2021-01-21 10:27:22 -0300
commit0e9254dfa03d95c3aa2888cf78e9a30bc88d41bc (patch)
treeca3c956e03f8ecc03eb7ed155c8b6f5e3ebef801 /testes
parent6ccd24eff58340c00db2877c4558a63c6b859442 (diff)
downloadlua-0e9254dfa03d95c3aa2888cf78e9a30bc88d41bc.tar.gz
lua-0e9254dfa03d95c3aa2888cf78e9a30bc88d41bc.tar.bz2
lua-0e9254dfa03d95c3aa2888cf78e9a30bc88d41bc.zip
Correct order of return hooks vs. close metamethods
The return hook should be called only after closing variables (which are still part of the function). C functions were calling the hook before the metamethods.
Diffstat (limited to 'testes')
-rw-r--r--testes/locals.lua77
1 files changed, 70 insertions, 7 deletions
diff --git a/testes/locals.lua b/testes/locals.lua
index 24a95d18..a25b2b9f 100644
--- a/testes/locals.lua
+++ b/testes/locals.lua
@@ -521,6 +521,14 @@ do -- tbc inside close methods
521end 521end
522 522
523 523
524local function checktable (t1, t2)
525 assert(#t1 == #t2)
526 for i = 1, #t1 do
527 assert(t1[i] == t2[i])
528 end
529end
530
531
524if rawget(_G, "T") then 532if rawget(_G, "T") then
525 533
526 -- memory error inside closing function 534 -- memory error inside closing function
@@ -632,6 +640,68 @@ if rawget(_G, "T") then
632 print'+' 640 print'+'
633 end 641 end
634 642
643
644 do
645 -- '__close' vs. return hooks in C functions
646 local trace = {}
647
648 local function hook (event)
649 trace[#trace + 1] = event .. " " .. (debug.getinfo(2).name or "?")
650 end
651
652 -- create tbc variables to be used by C function
653 local x = func2close(function (_,msg)
654 trace[#trace + 1] = "x"
655 end)
656
657 local y = func2close(function (_,msg)
658 trace[#trace + 1] = "y"
659 end)
660
661 debug.sethook(hook, "r")
662 local t = {T.testC([[
663 toclose 2 # x
664 pushnum 10
665 pushint 20
666 toclose 3 # y
667 return 2
668 ]], x, y)}
669 debug.sethook()
670
671 -- hooks ran before return hook from 'testC'
672 checktable(trace,
673 {"return sethook", "y", "return ?", "x", "return ?", "return testC"})
674 -- results are correct
675 checktable(t, {10, 20})
676 end
677
678end
679
680
681do -- '__close' vs. return hooks in Lua functions
682 local trace = {}
683
684 local function hook (event)
685 trace[#trace + 1] = event .. " " .. debug.getinfo(2).name
686 end
687
688 local function foo (...)
689 local x <close> = func2close(function (_,msg)
690 trace[#trace + 1] = "x"
691 end)
692
693 local y <close> = func2close(function (_,msg)
694 debug.sethook(hook, "r")
695 end)
696
697 return ...
698 end
699
700 local t = {foo(10,20,30)}
701 debug.sethook()
702 checktable(t, {10, 20, 30})
703 checktable(trace,
704 {"return sethook", "return close", "x", "return close", "return foo"})
635end 705end
636 706
637 707
@@ -640,13 +710,6 @@ print "to-be-closed variables in coroutines"
640do 710do
641 -- yielding inside closing metamethods 711 -- yielding inside closing metamethods
642 712
643 local function checktable (t1, t2)
644 assert(#t1 == #t2)
645 for i = 1, #t1 do
646 assert(t1[i] == t2[i])
647 end
648 end
649
650 local trace = {} 713 local trace = {}
651 local co = coroutine.wrap(function () 714 local co = coroutine.wrap(function ()
652 715