First implementation for 'const' variables

A variable can be declared const, which means it cannot be assigned to,
with the syntax 'local <const> name = exp'.
This commit is contained in:
Roberto Ierusalimschy
2019-05-17 11:11:44 -03:00
parent 347d6961ac
commit d9f40e3f6f
7 changed files with 207 additions and 58 deletions

View File

@@ -59,6 +59,41 @@ assert((x>y) and x or y == 2);
assert(1234567890 == tonumber('1234567890') and 1234567890+1 == 1234567891)
do -- testing operators with diffent kinds of constants
-- operands to consider:
-- * fit in register
-- * constant doesn't fit in register
-- * floats with integral values
local operand = {3, 100, 5.0, -10, -5.0, 10000, -10000}
local operator = {"+", "-", "*", "/", "//", "%", "^",
"&", "|", "^", "<<", ">>",
"==", "~=", "<", ">", "<=", ">=",}
for _, op in ipairs(operator) do
local f = assert(load(string.format([[return function (x,y)
return x %s y
end]], op)))();
for _, o1 in ipairs(operand) do
for _, o2 in ipairs(operand) do
local gab = f(o1, o2)
_ENV.XX = o1
code = string.format("return XX %s %s", op, o2)
res = assert(load(code))()
assert(res == gab)
_ENV.XX = o2
local code = string.format("return (%s) %s XX", o1, op)
local res = assert(load(code))()
assert(res == gab)
code = string.format("return (%s) %s %s", o1, op, o2)
res = assert(load(code))()
assert(res == gab)
end
end
end
end
-- silly loops
repeat until 1; repeat until true;
@@ -175,6 +210,28 @@ assert(a==1 and b==nil)
print'+';
do -- testing constants
local <const> prog = [[local <XXX> x = 10]]
checkload(prog, "unknown attribute 'XXX'")
checkload([[local <const> xxx = 20; xxx = 10]],
":1: assignment to const variable 'xxx'")
checkload([[
local xx;
local <const> xxx = 20;
local yyy;
local function foo ()
local abc = xx + yyy + xxx;
return function () return function () xxx = yyy end end
end
]], ":6: assignment to const variable 'xxx'")
checkload([[
local <toclose> x = nil
x = io.open()
]], ":2: assignment to const variable 'x'")
end
f = [[
return function ( a , b , c , d , e )
@@ -245,12 +302,12 @@ print('testing short-circuit optimizations (' .. _ENV.GLOB1 .. ')')
-- operators with their respective values
local binops = {
local <const> binops = {
{" and ", function (a,b) if not a then return a else return b end end},
{" or ", function (a,b) if a then return a else return b end end},
}
local cases = {}
local <const> cases = {}
-- creates all combinations of '(cases[i] op cases[n-i])' plus
-- 'not(cases[i] op cases[n-i])' (syntax + value)