Lunatic: embed lpeg and the translator into the binary

git-svn-id: https://svn.eduke32.com/eduke32@2650 1a8010ca-5511-0410-912e-c29ae57300e0
This commit is contained in:
helixhorned 2012-05-13 16:05:16 +00:00
parent ebe227ec1b
commit 88ca3a913a
5 changed files with 77 additions and 36 deletions

View File

@ -141,6 +141,8 @@ MISCGAMEDEPS=
## Lunatic devel ## Lunatic devel
LUAJIT=luajit
# for LJ headers: # for LJ headers:
LUAJIT_WIN_SRC:= g:/mod/LuaJIT-2.0.0-beta8/src LUAJIT_WIN_SRC:= g:/mod/LuaJIT-2.0.0-beta8/src
@ -159,6 +161,10 @@ ifneq (0,$(LUNATIC))
endif endif
GAMEOBJS+= $(OBJ)/lunatic.$o GAMEOBJS+= $(OBJ)/lunatic.$o
GAMEOBJS+= $(OBJ)/../lpeg.$o # TEMP
GAMEOBJS+= $(OBJ)/luaJIT_BC_con_lang.$o \
$(OBJ)/luaJIT_BC_lunacon.$o
# now, take care of having the necessary symbols (sector, wall, etc.) in the # now, take care of having the necessary symbols (sector, wall, etc.) in the
# executable no matter what the debugging level # executable no matter what the debugging level
@ -383,6 +389,11 @@ $(OBJ)/%.$o: $(SRC)/%.c
$(COMPILE_STATUS) $(COMPILE_STATUS)
if $(CC) $(OURCONLYFLAGS) $(OURCFLAGS) -c $< -o $@; then $(COMPILE_OK); else $(COMPILE_FAILED); fi if $(CC) $(OURCONLYFLAGS) $(OURCFLAGS) -c $< -o $@; then $(COMPILE_OK); else $(COMPILE_FAILED); fi
# Create object files directly with luajit
$(OBJ)/luaJIT_BC_%.$o: $(SRC)/lunatic/%.lua
$(COMPILE_STATUS)
if $(LUAJIT) -bg $< $@; then $(COMPILE_OK); else $(COMPILE_FAILED); fi
$(OBJ)/%.$o: $(SRC)/lunatic/%.c $(OBJ)/%.$o: $(SRC)/lunatic/%.c
$(COMPILE_STATUS) $(COMPILE_STATUS)
if $(CC) $(OURCONLYFLAGS) $(OURCFLAGS) -c $< -o $@; then $(COMPILE_OK); else $(COMPILE_FAILED); fi if $(CC) $(OURCONLYFLAGS) $(OURCFLAGS) -c $< -o $@; then $(COMPILE_OK); else $(COMPILE_FAILED); fi

View File

@ -1,6 +1,8 @@
-- INTERNAL -- INTERNAL
-- definitions of BUILD and game types for the Lunatic Interpreter -- definitions of BUILD and game types for the Lunatic Interpreter
_EDUKE32_LUNATIC = true
local ffi = require("ffi") local ffi = require("ffi")
---=== Duke3D engine and game definitions ===--- ---=== Duke3D engine and game definitions ===---
@ -398,15 +400,21 @@ G_.type = type
G_._G = G_ G_._G = G_
--- non-default functions
G_.setevent = setevent -- included in lunatic.c
-- http://lua-users.org/wiki/SandBoxes says "potentially unsafe" -- http://lua-users.org/wiki/SandBoxes says "potentially unsafe"
-- as it allows to see implementations of functions. -- as it allows to see implementations of functions.
local string_dump = string.dump local string_dump = string.dump
string.dump = nil string.dump = nil
--- non-default data and functions
G_._EDUKE32_LUNATIC = _EDUKE32_LUNATIC
G_.setevent = setevent -- included in lunatic.c
---=== Lunatic interpreter setup ===---
local lunacon = require("lunacon")
-- change the environment of this chunk to the table G_ -- change the environment of this chunk to the table G_
setfenv(1, G_) setfenv(1, G_)
@ -453,6 +461,9 @@ gv = {
actor = det, actor = det,
ud = det, ud = det,
luaJIT_BC_con_lang,
luaJIT_BC_lunacon,
} }
local tmpmt = { local tmpmt = {
__index = ffiC, __index = ffiC,

View File

@ -24,4 +24,7 @@ nextsectbunch;
actor; actor;
ud; ud;
luaJIT_BC_con_lang;
luaJIT_BC_lunacon;
}; };

View File

@ -18,7 +18,7 @@ local Pat, Set, Range, Var = lpeg.P, lpeg.S, lpeg.R, lpeg.V
---- All keywords pattern -- needed for CON syntax ---- All keywords pattern -- needed for CON syntax
local con_keyword = dofile("con_lang.lua") local con_keyword = require("con_lang")
local function match_until(matchsp, untilsp) -- (!untilsp matchsp)* in PEG local function match_until(matchsp, untilsp) -- (!untilsp matchsp)* in PEG
@ -872,8 +872,42 @@ local function setup_newlineidxs(contents)
newlineidxs[0] = 0 newlineidxs[0] = 0
end end
---=== stand-alone: ===---
if (not EDUKE32_LUNATIC) then ---=== EXPORTED FUNCTIONS ===---
local function parse(contents)
setup_newlineidxs(contents)
g_badids = {}
g_lastkw = nil
g_lastkwpos = nil
local idx = lpeg.match(Grammar, contents)
if (not idx) then
print("Match failed.")
elseif (idx == #contents+1) then
print("Matched whole contents.")
else
local i, col = getlinecol(idx)
local bi, ei = newlineidxs[i-1]+1, newlineidxs[i]-1
printf("Match succeeded up to %d (line %d, col %d; len=%d)",
idx, i, col, #contents)
-- printf("Line goes from %d to %d", bi, ei)
print(string.sub(contents, bi, ei))
if (g_lastkwpos) then
i, col = getlinecol(g_lastkwpos)
printf("Last keyword was at line %d, col %d: %s", i, col, g_lastkw)
end
end
end
if (not _EDUKE32_LUNATIC) then
--- stand-alone
local io = require("io") local io = require("io")
for argi=1,#arg do for argi=1,#arg do
@ -881,32 +915,9 @@ if (not EDUKE32_LUNATIC) then
printf("\n---- Parsing file \"%s\"", filename); printf("\n---- Parsing file \"%s\"", filename);
local contents = io.open(filename):read("*all") local contents = io.open(filename):read("*all")
setup_newlineidxs(contents) parse(contents)
g_badids = {}
g_lastkw = nil
g_lastkwpos = nil
local idx = lpeg.match(Grammar, contents)
if (not idx) then
print("Match failed.")
elseif (idx == #contents+1) then
print("Matched whole contents.")
else
local i, col = getlinecol(idx)
local bi, ei = newlineidxs[i-1]+1, newlineidxs[i]-1
printf("Match succeeded up to %d (line %d, col %d; len=%d)",
idx, i, col, #contents)
-- printf("Line goes from %d to %d", bi, ei)
print(string.sub(contents, bi, ei))
if (g_lastkwpos) then
i, col = getlinecol(g_lastkwpos)
printf("Last keyword was at line %d, col %d: %s", i, col, g_lastkw)
end
end
end end
else
--- embedded
return { parse=parse }
end end

View File

@ -21,8 +21,11 @@ static uint8_t g_elEvents[MAXEVENTS];
// forward-decls... // forward-decls...
static int32_t SetEvent_luacf(lua_State *L); static int32_t SetEvent_luacf(lua_State *L);
// in lpeg.o
extern int luaopen_lpeg(lua_State *L);
// 0: success, -1: failure
// 0: success, <0: failure
int32_t El_CreateState(El_State *estate, const char *name) int32_t El_CreateState(El_State *estate, const char *name)
{ {
estate->name = Bstrdup(name); estate->name = Bstrdup(name);
@ -39,6 +42,7 @@ int32_t El_CreateState(El_State *estate, const char *name)
} }
luaL_openlibs(estate->L); // XXX: only for internal use and testing, obviously luaL_openlibs(estate->L); // XXX: only for internal use and testing, obviously
luaopen_lpeg(estate->L);
// create misc. global functions in the Lua state // create misc. global functions in the Lua state
lua_pushcfunction(estate->L, SetEvent_luacf); lua_pushcfunction(estate->L, SetEvent_luacf);
@ -120,7 +124,8 @@ int32_t El_RunOnce(El_State *estate, const char *fn)
if (i == LUA_ERRRUN) if (i == LUA_ERRRUN)
{ {
OSD_Printf("state \"%s\" runtime error: %s\n", estate->name, lua_tostring(estate->L, 1)); // get err msg assert(lua_type(estate->L, -1)==LUA_TSTRING);
OSD_Printf("state \"%s\" runtime error: %s\n", estate->name, lua_tostring(estate->L, -1)); // get err msg
lua_pop(estate->L, 1); lua_pop(estate->L, 1);
return 4; return 4;
} }