mirror of
https://github.com/ZDoom/raze-gles.git
synced 2024-11-11 07:11:39 +00:00
Lunatic translator: else if* -> elseif, fix codegen for "if {}".
The first transformation makes the "control structure too long" error appear only with larger if/else cascades, though it's still possible. git-svn-id: https://svn.eduke32.com/eduke32@3569 1a8010ca-5511-0410-912e-c29ae57300e0
This commit is contained in:
parent
56ea732ccd
commit
c7e90f2ed4
2 changed files with 57 additions and 42 deletions
|
@ -96,7 +96,7 @@ local g_defaultDir = nil
|
||||||
|
|
||||||
-- Warning options. Key names are the same as cmdline options, e.g.
|
-- Warning options. Key names are the same as cmdline options, e.g.
|
||||||
-- -Wno-bad-identifier for disabling the "bad identifier" warning.
|
-- -Wno-bad-identifier for disabling the "bad identifier" warning.
|
||||||
local g_warn = { ["not-redefined"]=true, ["bad-identifier"]=true,
|
local g_warn = { ["not-redefined"]=true, ["bad-identifier"]=false,
|
||||||
["number-conversion"]=true, ["system-gamevar"]=true, }
|
["number-conversion"]=true, ["system-gamevar"]=true, }
|
||||||
|
|
||||||
-- Code generation and output options.
|
-- Code generation and output options.
|
||||||
|
@ -1698,7 +1698,7 @@ local handle =
|
||||||
local gv = g_gamevar[identifier]
|
local gv = g_gamevar[identifier]
|
||||||
if (gv and bit.band(gv.flags, GVFLAG.PERX_MASK)==GVFLAG.PERACTOR) then
|
if (gv and bit.band(gv.flags, GVFLAG.PERX_MASK)==GVFLAG.PERACTOR) then
|
||||||
-- Per-player are kind of global without multiplayer anyway. TODO_MP
|
-- Per-player are kind of global without multiplayer anyway. TODO_MP
|
||||||
errprintf("can only %s global or per-player gamevars", g_lastkw,
|
errprintf("can only %s global or per-player gamevars",
|
||||||
dosave and "save" or "read")
|
dosave and "save" or "read")
|
||||||
return "_BADRSGV()"
|
return "_BADRSGV()"
|
||||||
end
|
end
|
||||||
|
@ -2532,11 +2532,8 @@ local function after_inner_cmd_Cmt(subj, pos, ...)
|
||||||
end
|
end
|
||||||
|
|
||||||
local capts = {...}
|
local capts = {...}
|
||||||
if (type(capts[1])=="string" and capts[2]==nil) then
|
assert(type(capts[1])=="string" and capts[2]==nil)
|
||||||
return true, attachlinenum(capts, pos)
|
return true, attachlinenum(capts, pos)
|
||||||
end
|
|
||||||
|
|
||||||
return true
|
|
||||||
end
|
end
|
||||||
|
|
||||||
local function after_if_cmd_Cmt(subj, pos, ...)
|
local function after_if_cmd_Cmt(subj, pos, ...)
|
||||||
|
@ -2545,16 +2542,14 @@ local function after_if_cmd_Cmt(subj, pos, ...)
|
||||||
end
|
end
|
||||||
|
|
||||||
local capts = {...}
|
local capts = {...}
|
||||||
if (capts[1] ~= nil) then
|
assert(capts[1] ~= nil)
|
||||||
assert(#capts <= 3)
|
assert(#capts <= 3)
|
||||||
for i=1,#capts do
|
for i=1,#capts do
|
||||||
assert(type(capts[i]=="string"))
|
assert(type(capts[i]=="string"))
|
||||||
end
|
|
||||||
-- attachlinenum(capts, pos)
|
|
||||||
return true, unpack(capts)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
return true
|
-- TODO: make if* commands have line numbers.
|
||||||
|
return true, unpack(capts)
|
||||||
end
|
end
|
||||||
|
|
||||||
local function after_cmd_Cmt(subj, pos, ...)
|
local function after_cmd_Cmt(subj, pos, ...)
|
||||||
|
@ -2697,6 +2692,30 @@ local t_good_identifier = Range("AZ", "az", "__") * Range("AZ", "az", "__", "09"
|
||||||
local t_broken_identifier = BadIdent(-((tok.number + t_good_identifier) * (sp1 + Set("[]:"))) *
|
local t_broken_identifier = BadIdent(-((tok.number + t_good_identifier) * (sp1 + Set("[]:"))) *
|
||||||
(alphanum + Set(BAD_ID_CHARS0)) * (alphanum + Set(BAD_ID_CHARS1))^0)
|
(alphanum + Set(BAD_ID_CHARS0)) * (alphanum + Set(BAD_ID_CHARS1))^0)
|
||||||
|
|
||||||
|
---
|
||||||
|
local function do_flatten_codetab(code, intotab)
|
||||||
|
for i=1,math.huge do
|
||||||
|
local elt = code[i]
|
||||||
|
|
||||||
|
if (type(elt)=="string") then
|
||||||
|
intotab[#intotab+1] = elt
|
||||||
|
elseif (type(elt)=="table") then
|
||||||
|
do_flatten_codetab(elt, intotab)
|
||||||
|
else
|
||||||
|
assert(elt==nil)
|
||||||
|
return
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Return a "string buffer" table that can be table.concat'ed
|
||||||
|
-- to get the code string.
|
||||||
|
local function flatten_codetab(codetab)
|
||||||
|
local tmpcode = {}
|
||||||
|
do_flatten_codetab(codetab, tmpcode)
|
||||||
|
return tmpcode
|
||||||
|
end
|
||||||
|
|
||||||
function on.if_else_end(ifconds, ifstmt, elsestmt, ...)
|
function on.if_else_end(ifconds, ifstmt, elsestmt, ...)
|
||||||
assert(#{...}==0)
|
assert(#{...}==0)
|
||||||
assert(type(ifconds)=="table" and #ifconds>=1)
|
assert(type(ifconds)=="table" and #ifconds>=1)
|
||||||
|
@ -2731,13 +2750,25 @@ function on.if_else_end(ifconds, ifstmt, elsestmt, ...)
|
||||||
|
|
||||||
local code = {
|
local code = {
|
||||||
format("if %s then", conds),
|
format("if %s then", conds),
|
||||||
ifstmt,
|
assert(ifstmt),
|
||||||
}
|
}
|
||||||
|
|
||||||
code[#code+1] = deferred[1]
|
code[#code+1] = deferred[1]
|
||||||
|
|
||||||
if (elsestmt~=nil) then
|
if (elsestmt~=nil) then
|
||||||
code[#code+1] = "else"
|
local elseifp = false
|
||||||
|
|
||||||
|
if (type(elsestmt)=="table") then
|
||||||
|
elsestmt = flatten_codetab(elsestmt)
|
||||||
|
|
||||||
|
if (#elsestmt>=2 and elsestmt[1]:match("^if ") and elsestmt[#elsestmt]=="end") then
|
||||||
|
elsestmt[1] = elsestmt[1]:sub(4)
|
||||||
|
elsestmt[#elsestmt] = nil
|
||||||
|
elseifp = true
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
code[#code+1] = elseifp and "elseif" or "else"
|
||||||
code[#code+1] = elsestmt
|
code[#code+1] = elsestmt
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -2897,7 +2928,7 @@ local Grammar = Pat{
|
||||||
+ Keyw("whilevarn") * sp1 * tok.rvar * sp1 * tok.define / on.while_begin
|
+ Keyw("whilevarn") * sp1 * tok.rvar * sp1 * tok.define / on.while_begin
|
||||||
* sp1 * Var("single_stmt") * (lpeg.Cc(nil) / on.while_end),
|
* sp1 * Var("single_stmt") * (lpeg.Cc(nil) / on.while_end),
|
||||||
|
|
||||||
stmt_common = Keyw("{") * sp1 * "}" -- space separation of commands in CON is for a reason!
|
stmt_common = Keyw("{") * sp1 * "}" / "do end" -- space separation of commands in CON is for a reason!
|
||||||
+ Keyw("{") * sp1 * lpeg.Ct(stmt_list) * sp1 * "}"
|
+ Keyw("{") * sp1 * lpeg.Ct(stmt_list) * sp1 * "}"
|
||||||
+ con_inner_command + Var("switch_stmt") + lpeg.Ct(Var("while_stmt")),
|
+ con_inner_command + Var("switch_stmt") + lpeg.Ct(Var("while_stmt")),
|
||||||
|
|
||||||
|
@ -2927,30 +2958,6 @@ local function setup_newlineidxs(contents)
|
||||||
return newlineidxs
|
return newlineidxs
|
||||||
end
|
end
|
||||||
|
|
||||||
---
|
|
||||||
local function do_flatten_codetab(code, intotab)
|
|
||||||
for i=1,math.huge do
|
|
||||||
local elt = code[i]
|
|
||||||
|
|
||||||
if (type(elt)=="string") then
|
|
||||||
intotab[#intotab+1] = elt
|
|
||||||
elseif (type(elt)=="table") then
|
|
||||||
do_flatten_codetab(elt, intotab)
|
|
||||||
else
|
|
||||||
assert(elt==nil)
|
|
||||||
return
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
-- Return a "string buffer" table that can be table.concat'ed
|
|
||||||
-- to get the code string.
|
|
||||||
local function flatten_codetab(codetab)
|
|
||||||
local tmpcode = {}
|
|
||||||
do_flatten_codetab(codetab, tmpcode)
|
|
||||||
return tmpcode
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
--== Lua -> CON line number mapping for error messages ==--
|
--== Lua -> CON line number mapping for error messages ==--
|
||||||
|
|
||||||
|
|
|
@ -55,4 +55,12 @@ onevent EVENT_JUMP
|
||||||
}
|
}
|
||||||
else ifcanseetarget
|
else ifcanseetarget
|
||||||
quote 31
|
quote 31
|
||||||
|
else ifvare 1 1
|
||||||
|
{
|
||||||
|
// Test empty brace-enclosed statement under if condition.
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
quote Q
|
||||||
|
}
|
||||||
endevent
|
endevent
|
||||||
|
|
Loading…
Reference in a new issue