ESP32: remove use of luaM_free in file module (#2631)
* file: remove use of luaM_free * added safe pushlstring function
This commit is contained in:
parent
2339726097
commit
d1eab2396c
|
@ -65,4 +65,9 @@ inline bool luaX_valid_ref(lua_ref_t ref) {
|
||||||
return ref > 0;
|
return ref > 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// luaX_pushlstring is the same as lua_pushlstring except it will return nonzero in case of error
|
||||||
|
// (instead of throwing an exception and never returning) and will put the error message on the top of the stack.
|
||||||
|
int luaX_pushlstring(lua_State* L, const char* s, size_t l);
|
||||||
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -115,3 +115,26 @@ void luaX_set_ref(lua_State* L, int idx, lua_ref_t* ref) {
|
||||||
lua_pushvalue(L, idx); // push on the stack the referenced index
|
lua_pushvalue(L, idx); // push on the stack the referenced index
|
||||||
*ref = luaL_ref(L, LUA_REGISTRYINDEX); // set the reference (pops 1 value)
|
*ref = luaL_ref(L, LUA_REGISTRYINDEX); // set the reference (pops 1 value)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// pushlstring_t is a helper struct to provide a protected lua_pushlstring call
|
||||||
|
typedef struct {
|
||||||
|
const char* s;
|
||||||
|
size_t l;
|
||||||
|
} pushlstring_t;
|
||||||
|
|
||||||
|
// safe_pushlstring is a private function meant to be called in protected mode.
|
||||||
|
static int safe_pushlstring(lua_State* L) {
|
||||||
|
pushlstring_t *ps = (pushlstring_t*)lua_touserdata(L,-1);
|
||||||
|
lua_pushlstring(L, ps->s, ps->l);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// luaX_pushlstring is the same as lua_pushlstring except it will return nonzero in case of error
|
||||||
|
// (instead of throwing an exception and never returning) and will put the error message on the top of the stack.
|
||||||
|
int luaX_pushlstring(lua_State* L, const char* s, size_t l) {
|
||||||
|
lua_pushcfunction(L, &safe_pushlstring);
|
||||||
|
pushlstring_t* ps =(pushlstring_t*) lua_newuserdata(L, sizeof(pushlstring_t));
|
||||||
|
ps->s = s;
|
||||||
|
ps->l = l;
|
||||||
|
return lua_pcall(L, 1, 1, 0);
|
||||||
|
}
|
||||||
|
|
|
@ -2,6 +2,7 @@
|
||||||
|
|
||||||
#include "module.h"
|
#include "module.h"
|
||||||
#include "lauxlib.h"
|
#include "lauxlib.h"
|
||||||
|
#include "lnodeaux.h"
|
||||||
#include "lmem.h"
|
#include "lmem.h"
|
||||||
#include "platform.h"
|
#include "platform.h"
|
||||||
|
|
||||||
|
@ -140,7 +141,6 @@ static int file_obj_free( lua_State *L )
|
||||||
if (ud->fd) {
|
if (ud->fd) {
|
||||||
// close file if it's still open
|
// close file if it's still open
|
||||||
vfs_close(ud->fd);
|
vfs_close(ud->fd);
|
||||||
ud->fd = 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -383,12 +383,7 @@ static int file_stat( lua_State* L )
|
||||||
// g_read()
|
// g_read()
|
||||||
static int file_g_read( lua_State* L, int n, int16_t end_char, int fd )
|
static int file_g_read( lua_State* L, int n, int16_t end_char, int fd )
|
||||||
{
|
{
|
||||||
static char *heap_mem = NULL;
|
char *heap_mem = NULL;
|
||||||
// free leftover memory
|
|
||||||
if (heap_mem) {
|
|
||||||
luaM_free(L, heap_mem);
|
|
||||||
heap_mem = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(n <= 0)
|
if(n <= 0)
|
||||||
n = FILE_READ_CHUNK;
|
n = FILE_READ_CHUNK;
|
||||||
|
@ -396,19 +391,19 @@ static int file_g_read( lua_State* L, int n, int16_t end_char, int fd )
|
||||||
if(end_char < 0 || end_char >255)
|
if(end_char < 0 || end_char >255)
|
||||||
end_char = EOF;
|
end_char = EOF;
|
||||||
|
|
||||||
|
|
||||||
if(!fd)
|
if(!fd)
|
||||||
return luaL_error(L, "open a file first");
|
return luaL_error(L, "open a file first");
|
||||||
|
|
||||||
char *p;
|
char *p;
|
||||||
int i;
|
int i;
|
||||||
|
size_t bufsize = n;
|
||||||
|
|
||||||
if (n > LUAL_BUFFERSIZE) {
|
if (n > LUAL_BUFFERSIZE) {
|
||||||
// get buffer from heap
|
// get buffer from heap
|
||||||
p = heap_mem = luaM_malloc(L, n);
|
p = heap_mem = luaM_malloc(L, bufsize);
|
||||||
} else {
|
} else {
|
||||||
// small chunks go onto the stack
|
// small chunks go onto the stack
|
||||||
p = alloca(n);
|
p = alloca(bufsize);
|
||||||
}
|
}
|
||||||
|
|
||||||
n = vfs_read(fd, p, n);
|
n = vfs_read(fd, p, n);
|
||||||
|
@ -424,21 +419,24 @@ static int file_g_read( lua_State* L, int n, int16_t end_char, int fd )
|
||||||
i = n;
|
i = n;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int err = 0;
|
||||||
|
|
||||||
if (i == 0 || n == VFS_RES_ERR) {
|
if (i == 0 || n == VFS_RES_ERR) {
|
||||||
if (heap_mem) {
|
|
||||||
luaM_free(L, heap_mem);
|
|
||||||
heap_mem = NULL;
|
|
||||||
}
|
|
||||||
lua_pushnil(L);
|
lua_pushnil(L);
|
||||||
return 1;
|
} else {
|
||||||
|
vfs_lseek(fd, -(n - i), VFS_SEEK_CUR);
|
||||||
|
err = luaX_pushlstring(L, p, i); // On error it will return nonzero and leave a message on top of the stack.
|
||||||
}
|
}
|
||||||
|
|
||||||
vfs_lseek(fd, -(n - i), VFS_SEEK_CUR);
|
|
||||||
lua_pushlstring(L, p, i);
|
|
||||||
if (heap_mem) {
|
if (heap_mem) {
|
||||||
luaM_free(L, heap_mem);
|
luaM_freearray(L, heap_mem, bufsize, char);
|
||||||
heap_mem = NULL;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (err){
|
||||||
|
lua_error(L); // luaX_pushlstring failed and the error message is on top of the stack. Throw it.
|
||||||
|
// never returns
|
||||||
|
}
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue