aboutsummaryrefslogtreecommitdiff
path: root/testes
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2019-03-19 10:53:18 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2019-03-19 10:53:18 -0300
commit9b37a4695ebf50b37b5b4fb279ae948f23b5b6a0 (patch)
tree2a6b0f6c1c2eb962bb383175eb0a67ea81a4564d /testes
parent1e0c73d5b643707335b06abd2546a83d9439d14c (diff)
downloadlua-9b37a4695ebf50b37b5b4fb279ae948f23b5b6a0.tar.gz
lua-9b37a4695ebf50b37b5b4fb279ae948f23b5b6a0.tar.bz2
lua-9b37a4695ebf50b37b5b4fb279ae948f23b5b6a0.zip
New semantics for the integer 'for' loop
The numerical 'for' loop over integers now uses a precomputed counter to control its number of iteractions. This change eliminates several weird cases caused by overflows (wrap-around) in the control variable. (It also ensures that every integer loop halts.) Also, the special opcodes for the usual case of step==1 were removed. (The new code is already somewhat complex for the usual case, but efficient.)
Diffstat (limited to 'testes')
-rw-r--r--testes/code.lua4
-rw-r--r--testes/db.lua2
-rw-r--r--testes/nextvar.lua73
3 files changed, 71 insertions, 8 deletions
diff --git a/testes/code.lua b/testes/code.lua
index 834ff5e2..128ca2cb 100644
--- a/testes/code.lua
+++ b/testes/code.lua
@@ -303,9 +303,9 @@ check(function (x) return x & 2.0 end, 'LOADF', 'BAND', 'RETURN1')
303 303
304-- basic 'for' loops 304-- basic 'for' loops
305check(function () for i = -10, 10.5 do end end, 305check(function () for i = -10, 10.5 do end end,
306'LOADI', 'LOADK', 'LOADI', 'FORPREP1', 'FORLOOP1', 'RETURN0') 306'LOADI', 'LOADK', 'LOADI', 'FORPREP', 'FORLOOP', 'RETURN0')
307check(function () for i = 0xfffffff, 10.0, 1 do end end, 307check(function () for i = 0xfffffff, 10.0, 1 do end end,
308'LOADK', 'LOADF', 'LOADI', 'FORPREP1', 'FORLOOP1', 'RETURN0') 308'LOADK', 'LOADF', 'LOADI', 'FORPREP', 'FORLOOP', 'RETURN0')
309 309
310-- bug in constant folding for 5.1 310-- bug in constant folding for 5.1
311check(function () return -nil end, 'LOADNIL', 'UNM', 'RETURN1') 311check(function () return -nil end, 'LOADNIL', 'UNM', 'RETURN1')
diff --git a/testes/db.lua b/testes/db.lua
index 976962b0..0858dd20 100644
--- a/testes/db.lua
+++ b/testes/db.lua
@@ -162,7 +162,7 @@ test([[for i,v in pairs{'a','b'} do
162end 162end
163]], {1,2,1,2,1,3}) 163]], {1,2,1,2,1,3})
164 164
165test([[for i=1,4 do a=1 end]], {1,1,1,1,1}) 165test([[for i=1,4 do a=1 end]], {1,1,1,1}, true)
166 166
167 167
168do -- testing line info/trace with large gaps in source 168do -- testing line info/trace with large gaps in source
diff --git a/testes/nextvar.lua b/testes/nextvar.lua
index d2306ed1..e769ccdd 100644
--- a/testes/nextvar.lua
+++ b/testes/nextvar.lua
@@ -76,7 +76,7 @@ while a < lim do
76 a = math.ceil(a*1.3) 76 a = math.ceil(a*1.3)
77end 77end
78 78
79 79
80local function check (t, na, nh) 80local function check (t, na, nh)
81 local a, h = T.querytab(t) 81 local a, h = T.querytab(t)
82 if a ~= na or h ~= nh then 82 if a ~= na or h ~= nh then
@@ -100,7 +100,7 @@ local s = 'return {'
100for i=1,lim do 100for i=1,lim do
101 s = s..i..',' 101 s = s..i..','
102 local s = s 102 local s = s
103 for k=0,lim do 103 for k=0,lim do
104 local t = load(s..'}', '')() 104 local t = load(s..'}', '')()
105 assert(#t == i) 105 assert(#t == i)
106 check(t, fb(i), mp2(k)) 106 check(t, fb(i), mp2(k))
@@ -279,7 +279,7 @@ do -- clear global table
279end 279end
280 280
281 281
282-- 282--
283 283
284local function checknext (a) 284local function checknext (a)
285 local b = {} 285 local b = {}
@@ -500,7 +500,7 @@ else --[
500 mt.__newindex = nil 500 mt.__newindex = nil
501 mt.__len = nil 501 mt.__len = nil
502 local tab2 = {} 502 local tab2 = {}
503 local u2 = T.newuserdata(0) 503 local u2 = T.newuserdata(0)
504 debug.setmetatable(u2, {__newindex = function (_, k, v) tab2[k] = v end}) 504 debug.setmetatable(u2, {__newindex = function (_, k, v) tab2[k] = v end})
505 table.move(u, 1, 4, 1, u2) 505 table.move(u, 1, 4, 1, u2)
506 assert(#tab2 == 4 and tab2[1] == tab[1] and tab2[4] == tab[4]) 506 assert(#tab2 == 4 and tab2[1] == tab[1] and tab2[4] == tab[4])
@@ -601,6 +601,69 @@ do -- checking types
601 601
602end 602end
603 603
604
605do -- testing other strange cases for numeric 'for'
606
607 local function checkfor (from, to, step, t)
608 local c = 0
609 for i = from, to, step do
610 c = c + 1
611 assert(i == t[c])
612 end
613 assert(c == #t)
614 end
615
616 local maxi = math.maxinteger
617 local mini = math.mininteger
618
619 checkfor(mini, maxi, maxi, {mini, -1, maxi - 1})
620
621 checkfor(mini, math.huge, maxi, {mini, -1, maxi - 1})
622
623 checkfor(maxi, mini, mini, {maxi, -1})
624
625 checkfor(maxi, mini, -maxi, {maxi, 0, -maxi})
626
627 checkfor(maxi, -math.huge, mini, {maxi, -1})
628
629 checkfor(maxi, mini, 1, {})
630 checkfor(mini, maxi, -1, {})
631
632 checkfor(maxi - 6, maxi, 3, {maxi - 6, maxi - 3, maxi})
633 checkfor(mini + 4, mini, -2, {mini + 4, mini + 2, mini})
634
635 local step = maxi // 10
636 local c = mini
637 for i = mini, maxi, step do
638 assert(i == c)
639 c = c + step
640 end
641
642 c = maxi
643 for i = maxi, mini, -step do
644 assert(i == c)
645 c = c - step
646 end
647
648 checkfor(maxi, maxi, maxi, {maxi})
649 checkfor(maxi, maxi, mini, {maxi})
650 checkfor(mini, mini, maxi, {mini})
651 checkfor(mini, mini, mini, {mini})
652end
653
654
655checkerror("'for' step is zero", function ()
656 for i = 1, 10, 0 do end
657end)
658
659checkerror("'for' step is zero", function ()
660 for i = 1, -10, 0 do end
661end)
662
663checkerror("'for' step is zero", function ()
664 for i = 1.0, -10, 0.0 do end
665end)
666
604collectgarbage() 667collectgarbage()
605 668
606 669
@@ -657,7 +720,7 @@ a[3] = 30
657-- testing ipairs with metamethods 720-- testing ipairs with metamethods
658a = {n=10} 721a = {n=10}
659setmetatable(a, { __index = function (t,k) 722setmetatable(a, { __index = function (t,k)
660 if k <= t.n then return k * 10 end 723 if k <= t.n then return k * 10 end
661 end}) 724 end})
662i = 0 725i = 0
663for k,v in ipairs(a) do 726for k,v in ipairs(a) do