1
0
Fork 0
mirror of https://github.com/opentx/opentx.git synced 2025-07-20 23:05:12 +03:00

#1471 - libio added to Lua. For tests, can be simplified and expanded

This commit is contained in:
bsongis 2015-03-16 20:10:16 +01:00
parent 7863bb23b9
commit 4e55213ae6
5 changed files with 114 additions and 52 deletions

View file

@ -937,7 +937,7 @@ ifeq ($(PCB), TARANIS)
CPPSRC += lua_api.cpp
LUASRC = lua/src/lapi.c lua/src/lcode.c lua/src/lctype.c lua/src/ldebug.c lua/src/ldo.c lua/src/ldump.c lua/src/lfunc.c lua/src/lgc.c lua/src/llex.c lua/src/lmem.c \
lua/src/lobject.c lua/src/lopcodes.c lua/src/lparser.c lua/src/lstate.c lua/src/lstring.c lua/src/ltable.c lua/src/lrotable.c lua/src/ltm.c lua/src/lundump.c lua/src/lvm.c lua/src/lzio.c \
lua/src/lbaselib.c lua/src/linit.c lua/src/lmathlib.c lua/src/lbitlib.c lua/src/loadlib.c lua/src/lauxlib.c lua/src/ltablib.c lua/src/lcorolib.c
lua/src/lbaselib.c lua/src/linit.c lua/src/lmathlib.c lua/src/lbitlib.c lua/src/loadlib.c lua/src/lauxlib.c lua/src/ltablib.c lua/src/lcorolib.c lua/src/liolib.c
SRC += $(LUASRC)
LUADEP = lua_exports.inc
ifeq ($(USE_BIN_ALLOCATOR), YES)

View file

@ -26,8 +26,10 @@ typedef struct luaL_Reg {
extern const luaL_Reg baselib[];
extern const luaL_Reg mathlib[];
extern const luaL_Reg opentxLib[];
extern const luaL_Reg bitlib[];
extern const luaL_Reg iolib[];
extern const luaL_Reg opentxLib[];
extern const luaL_Reg lcdLib[];
extern const luaL_Reg modelLib[];
@ -191,14 +193,17 @@ LUALIB_API char *(luaL_buffinitsize) (lua_State *L, luaL_Buffer *B, size_t sz);
#define LUA_FILEHANDLE "FILE*"
#if defined(USE_FATFS)
#define FILE FIL
#endif
typedef struct luaL_Stream {
#if defined(USE_FATFS)
FIL *f; /* stream (NULL for incompletely created streams) */
FIL f;
#else
FILE *f; /* stream (NULL for incompletely created streams) */
#endif
lua_CFunction closef; /* to close stream (NULL for closed streams) */
#endif
} luaL_Stream;
/* }====================================================== */

View file

@ -31,7 +31,7 @@ static const luaL_Reg loadedlibs[] = {
// {LUA_LOADLIBNAME, luaopen_package},
// {LUA_COLIBNAME, luaopen_coroutine},
// {LUA_TABLIBNAME, luaopen_table},
// {LUA_IOLIBNAME, luaopen_io},
{LUA_IOLIBNAME, luaopen_io},
// {LUA_OSLIBNAME, luaopen_os},
// {LUA_STRLIBNAME, luaopen_string},
// {LUA_BITLIBNAME, luaopen_bit32},
@ -45,6 +45,7 @@ const luaR_table lua_rotable[] =
{
{LUA_MATHLIBNAME, mathlib, mathlib_vals},
{LUA_BITLIBNAME, bitlib, NULL},
{LUA_IOLIBNAME, iolib, NULL},
{"lcd", lcdLib, NULL},
{"model", modelLib, NULL},
{"__baselib", baselib, NULL},

View file

@ -121,8 +121,9 @@ typedef luaL_Stream LStream;
#define tolstream(L) ((LStream *)luaL_checkudata(L, 1, LUA_FILEHANDLE))
#define isclosed(p) ((p)->closef == NULL)
#if !defined(USE_FATFS)
#define isclosed(p) ((p)->closef == NULL)
static int io_type (lua_State *L) {
LStream *p;
@ -147,13 +148,18 @@ static int f_tostring (lua_State *L) {
return 1;
}
#endif
static FILE *tofile (lua_State *L) {
LStream *p = tolstream(L);
#if defined(USE_FATFS)
return &p->f;
#else
if (isclosed(p))
luaL_error(L, "attempt to use a closed file");
lua_assert(p->f);
return p->f;
#endif
}
@ -164,36 +170,48 @@ static FILE *tofile (lua_State *L) {
*/
static LStream *newprefile (lua_State *L) {
LStream *p = (LStream *)lua_newuserdata(L, sizeof(LStream));
#if !defined(USE_FATFS)
p->closef = NULL; /* mark file handle as 'closed' */
#endif
luaL_setmetatable(L, LUA_FILEHANDLE);
return p;
}
#if !defined(USE_FATFS)
static int aux_close (lua_State *L) {
#if !defined(USE_FATFS)
LStream *p = tolstream(L);
lua_CFunction cf = p->closef;
p->closef = NULL; /* mark stream as closed */
return (*cf)(L); /* close it */
#else
return 0;
#endif
}
#endif
static int io_close (lua_State *L) {
#if defined(USE_FATFS)
f_close(tofile(L));
return 0;
#else
if (lua_isnone(L, 1)) /* no argument? */
lua_getfield(L, LUA_REGISTRYINDEX, IO_OUTPUT); /* use standard output */
tofile(L); /* make sure argument is an open stream */
return aux_close(L);
#endif
}
#if !defined(USE_FATFS)
static int f_gc (lua_State *L) {
#if !defined(USE_FATFS)
LStream *p = tolstream(L);
if (!isclosed(p) && p->f != NULL)
aux_close(L); /* ignore closed and incompletely open files */
#endif
return 0;
}
/*
** function to close regular files
*/
@ -202,34 +220,49 @@ static int io_fclose (lua_State *L) {
int res = fclose(p->f);
return luaL_fileresult(L, (res == 0), NULL);
}
#endif
static LStream *newfile (lua_State *L) {
LStream *p = newprefile(L);
#if !defined(USE_FATFS)
p->f = NULL;
p->closef = &io_fclose;
#endif
return p;
}
#if !defined(USE_FATFS)
static void opencheck (lua_State *L, const char *fname, const char *mode) {
LStream *p = newfile(L);
p->f = fopen(fname, mode);
if (p->f == NULL)
luaL_error(L, "cannot open file " LUA_QS " (%s)", fname, strerror(errno));
}
#endif
static int io_open (lua_State *L) {
const char *filename = luaL_checkstring(L, 1);
const char *mode = luaL_optstring(L, 2, "r");
const char *md = luaL_optstring(L, 2, "r");
LStream *p = newfile(L);
const char *md = mode; /* to traverse/check mode */
luaL_argcheck(L, lua_checkmode(md), 2, "invalid mode");
p->f = fopen(filename, mode);
#if defined(USE_FATFS)
BYTE mode;
if (!md || *md == 'r')
mode = FA_READ;
else if (*md == 'w')
mode = FA_WRITE;
else
luaL_argerror(L, (2), ("invalid mode"));
FRESULT result = f_open(&p->f, filename, mode);
return result == FR_OK ? 1 : 0;
#else
const char *mode = md; /* to traverse/check mode */
luaL_argcheck(L, lua_checkmode(mode), 2, "invalid mode");
p->f = fopen(filename, md);
return (p->f == NULL) ? luaL_fileresult(L, 0, filename) : 1;
#endif
}
#if !defined(USE_FATFS)
/*
** function to close 'popen' files
@ -239,7 +272,6 @@ static int io_pclose (lua_State *L) {
return luaL_execresult(L, lua_pclose(L, p->f));
}
static int io_popen (lua_State *L) {
const char *filename = luaL_checkstring(L, 1);
const char *mode = luaL_optstring(L, 2, "r");
@ -336,7 +368,6 @@ static int io_lines (lua_State *L) {
return 1;
}
/*
** {======================================================
** READ
@ -356,7 +387,6 @@ static int read_number (lua_State *L, FILE *f) {
}
}
static int test_eof (lua_State *L, FILE *f) {
int c = lua_getc(f);
ungetc(c, f);
@ -386,7 +416,6 @@ static int read_line (lua_State *L, FILE *f, int chop) {
}
}
#define MAX_SIZE_T (~(size_t)0)
static void read_all (lua_State *L, FILE *f) {
@ -403,21 +432,21 @@ static void read_all (lua_State *L, FILE *f) {
}
luaL_pushresult(&b); /* close buffer */
}
#endif
static int read_chars (lua_State *L, FILE *f, size_t n) {
size_t nr; /* number of chars actually read */
unsigned int nr; /* number of chars actually read */
char *p;
luaL_Buffer b;
luaL_buffinit(L, &b);
p = luaL_prepbuffsize(&b, n); /* prepare buffer to read whole block */
nr = fread(p, sizeof(char), n, f); /* try to read 'n' chars */
FRESULT result = f_read(f, p, n, &nr); /* try to read 'n' chars */
luaL_addsize(&b, nr);
luaL_pushresult(&b); /* close buffer */
return (nr > 0); /* true iff read something */
return (result == FR_OK && nr > 0); /* true iff read something */
}
#if !defined(USE_FATFS)
static int g_read (lua_State *L, FILE *f, int first) {
int nargs = lua_gettop(L) - 1;
int success;
@ -477,7 +506,18 @@ static int f_read (lua_State *L) {
return g_read(L, tofile(L), 2);
}
#else
static int io_read (lua_State *L) {
LStream *p = tolstream(L);
size_t l = (size_t)lua_tointeger(L, 2);
read_chars(L, &p->f, l);
return 1;
}
#endif
#if !defined(USE_FATFS)
static int io_readline (lua_State *L) {
LStream *p = (LStream *)lua_touserdata(L, lua_upvalueindex(1));
int i;
@ -507,6 +547,7 @@ static int io_readline (lua_State *L) {
/* }====================================================== */
#endif
static int g_write (lua_State *L, FILE *f, int arg) {
int nargs = lua_gettop(L) - arg;
@ -515,31 +556,38 @@ static int g_write (lua_State *L, FILE *f, int arg) {
if (lua_type(L, arg) == LUA_TNUMBER) {
/* optimization: could be done exactly as for strings */
status = status &&
fprintf(f, LUA_NUMBER_FMT, lua_tonumber(L, arg)) > 0;
f_printf(f, LUA_NUMBER_FMT, lua_tonumber(L, arg)) > 0;
}
else {
size_t l;
UINT count;
const char *s = luaL_checklstring(L, arg, &l);
status = status && (fwrite(s, sizeof(char), l, f) == l);
status = status && (f_write(f, s, l, &count) == FR_OK && count == l);
}
}
if (status) return 1; /* file handle already on stack top */
else return luaL_fileresult(L, status, NULL);
}
#if !defined(USE_FATFS)
static int io_write (lua_State *L) {
return g_write(L, getiofile(L, IO_OUTPUT), 1);
}
static int f_write (lua_State *L) {
FILE *f = tofile(L);
lua_pushvalue(L, 1); /* push file at the stack top (to be returned) */
return g_write(L, f, 2);
}
#else
static int io_write (lua_State *L) {
FILE *f = tofile(L);
lua_pushvalue(L, 1); /* push file at the stack top (to be returned) */
return g_write(L, f, 2);
}
#endif
#if !defined(USE_FATFS)
static int f_seek (lua_State *L) {
static const int mode[] = {SEEK_SET, SEEK_CUR, SEEK_END};
static const char *const modenames[] = {"set", "cur", "end", NULL};
@ -570,7 +618,7 @@ static int f_setvbuf (lua_State *L) {
}
#if !defined(USE_FATFS)
static int io_flush (lua_State *L) {
return luaL_fileresult(L, fflush(getiofile(L, IO_OUTPUT)) == 0, NULL);
}
@ -579,26 +627,29 @@ static int io_flush (lua_State *L) {
static int f_flush (lua_State *L) {
return luaL_fileresult(L, fflush(tofile(L)) == 0, NULL);
}
#endif
#endif
/*
** functions for 'io' library
*/
static const luaL_Reg iolib[] = {
const luaL_Reg iolib[] = {
{"close", io_close},
{"flush", io_flush},
{"input", io_input},
{"lines", io_lines},
// {"flush", io_flush},
// {"input", io_input},
// {"lines", io_lines},
{"open", io_open},
{"output", io_output},
{"popen", io_popen},
// {"output", io_output},
// {"popen", io_popen},
{"read", io_read},
{"tmpfile", io_tmpfile},
{"type", io_type},
// {"tmpfile", io_tmpfile},
// {"type", io_type},
{"write", io_write},
{NULL, NULL}
};
#if !defined(USE_FATFS)
/*
** methods for file handles
@ -607,7 +658,7 @@ static const luaL_Reg flib[] = {
{"close", io_close},
{"flush", f_flush},
{"lines", f_lines},
{"read", f_read},
{"read", io_read},
{"seek", f_seek},
{"setvbuf", f_setvbuf},
{"write", f_write},
@ -616,16 +667,17 @@ static const luaL_Reg flib[] = {
{NULL, NULL}
};
#endif
static void createmeta (lua_State *L) {
luaL_newmetatable(L, LUA_FILEHANDLE); /* create metatable for file handles */
lua_pushvalue(L, -1); /* push metatable */
lua_setfield(L, -2, "__index"); /* metatable.__index = metatable */
luaL_setfuncs(L, flib, 0); /* add file methods to new metatable */
// lua_setfield(L, -2, "__index"); /* metatable.__index = metatable */
// luaL_setfuncs(L, flib, 0); /* add file methods to new metatable */
lua_pop(L, 1); /* pop new metatable */
}
#if !defined(USE_FATFS)
/*
** function to (not) close the standard files stdin, stdout, and stderr
*/
@ -650,14 +702,15 @@ static void createstdfile (lua_State *L, FILE *f, const char *k,
lua_setfield(L, -2, fname); /* add file to module */
}
#endif
LUAMOD_API int luaopen_io (lua_State *L) {
luaL_newlib(L, iolib); /* new module */
// luaL_newlib(L, iolib); /* new module */
createmeta(L);
/* create (and set) default files */
createstdfile(L, stdin, IO_INPUT, "stdin");
createstdfile(L, stdout, IO_OUTPUT, "stdout");
createstdfile(L, stderr, NULL, "stderr");
return 1;
// createstdfile(L, stdin, IO_INPUT, "stdin");
// createstdfile(L, stdout, IO_OUTPUT, "stdout");
// createstdfile(L, stderr, NULL, "stderr");
// return 1;
return 0;
}

View file

@ -119,6 +119,7 @@ void luaV_gettable (lua_State *L, const TValue *t, TValue *key, StkId val) {
int loop;
if (ttisrotable(t)) {
setnilvalue(val);
TRACE("luaV_gettable(key=%s)", key);
if (ttisstring(key)) {
char keyname[LUA_MAX_ROTABLE_NAME + 1];
lu_byte keytype;
@ -143,8 +144,10 @@ void luaV_gettable (lua_State *L, const TValue *t, TValue *key, StkId val) {
}
/* else will try the tag method */
}
else if (ttisnil(tm = luaT_gettmbyobj(L, t, TM_INDEX)))
else if (ttisnil(tm = luaT_gettmbyobj(L, t, TM_INDEX))) {
TRACE("ERREUR ICI");
luaG_typeerror(L, t, "index");
}
if (ttisfunction(tm) || ttislightfunction(tm)) {
callTM(L, tm, t, key, val, 1);
return;