mirror of
https://github.com/opentx/opentx.git
synced 2025-07-17 21:35:27 +03:00
Fixes #1643 - Thanks to projectkk2glider for his help on this one
Conflicts: radio/src/lua.cpp radio/src/opentx.cpp
This commit is contained in:
parent
04f9eb5c0f
commit
500602e8cc
8 changed files with 417 additions and 219 deletions
|
@ -289,6 +289,10 @@ USB = JOYSTICK
|
|||
# NO - normal behaviour, show real channel values
|
||||
CHANNELS_MONITOR_INV_HIDE = NO
|
||||
|
||||
# Use newlib-nano
|
||||
# Values = NO, YES
|
||||
NANO = YES
|
||||
|
||||
#------- END BUILD OPTIONS ---------------------------
|
||||
|
||||
# Define programs and commands.
|
||||
|
@ -1116,6 +1120,12 @@ MATH_LIB = -lm
|
|||
LDFLAGS = -Wl,-Map=$(TARGET).map,--cref
|
||||
LDFLAGS += $(MATH_LIB)
|
||||
|
||||
ifeq ($(NANO), YES)
|
||||
# use newlib-nano for linking
|
||||
NEWLIB_NANO_FLAGS = --specs=nano.specs -u _printf_float
|
||||
CPPDEFS += -DNANO
|
||||
endif
|
||||
|
||||
# Define Messages
|
||||
# English
|
||||
MSG_BEGIN = -------- begin --------
|
||||
|
@ -1324,7 +1334,7 @@ FOXLIB=-L/usr/local/lib \
|
|||
-Wl,-rpath,$(FOXPATH)/src/.libs
|
||||
|
||||
simu: $(LUADEP) stamp_header $(BOARDSRC) $(CPPSRC) Makefile simu.cpp targets/simu/simpgmspace.cpp *.h tra lbm eeprom.bin
|
||||
g++ $(CPPFLAGS) $(INCFLAGS) simu.cpp $(BOARDSRC) $(CPPSRC) $(LUASRC) targets/simu/simpgmspace.cpp -MD -DSIMU -O0 -o simu $(FOXINC) $(FOXLIB) -pthread -fexceptions
|
||||
g++ $(CPPFLAGS) $(INCFLAGS) simu.cpp $(BOARDSRC) $(CPPSRC) $(LUASRC) targets/simu/simpgmspace.cpp -MD -DSIMU -DLUA_USE_APICHECK -O0 -o simu $(FOXINC) $(FOXLIB) -pthread -fexceptions
|
||||
|
||||
eeprom.bin:
|
||||
dd if=/dev/zero of=$@ bs=1 count=2048
|
||||
|
@ -1390,7 +1400,7 @@ OBJS = $(TMP:.s=.o)
|
|||
@echo
|
||||
@echo $(MSG_COMPILING) $@
|
||||
$(CC) $(ARMCPPFLAGS) $< -o allsrc.o
|
||||
$(CC) $(OBJS) allsrc.o -mcpu=cortex-m3 -mthumb -nostartfiles -lm -T$(LDSCRIPT) -Wl,-Map=$(TARGET).map,--cref,--no-warn-mismatch,--gc-sections -o $@
|
||||
$(CC) $(OBJS) allsrc.o -mcpu=cortex-m3 -mthumb -nostartfiles -lm -T$(LDSCRIPT) -Wl,-Map=$(TARGET).map,--cref,--no-warn-mismatch,--gc-sections $(NEWLIB_NANO_FLAGS) -o $@
|
||||
endif
|
||||
|
||||
# Target: clean project.
|
||||
|
|
|
@ -76,6 +76,19 @@ uint16_t maxLuaDuration = 0;
|
|||
#define SCRIPTS_MAX_HEAP 50
|
||||
#define SET_LUA_INSTRUCTIONS_COUNT(x) (instructionsPercent=0, lua_sethook(L, hook, LUA_MASKCOUNT, x))
|
||||
|
||||
struct our_longjmp * global_lj = 0;
|
||||
|
||||
/* custom panic handler */
|
||||
static int custom_lua_atpanic(lua_State *lua)
|
||||
{
|
||||
TRACE("PANIC: unprotected error in call to Lua API (%s)\n", lua_tostring(L, -1));
|
||||
if (global_lj) {
|
||||
longjmp(global_lj->b, 1);
|
||||
/* will never return */
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int instructionsPercent = 0;
|
||||
void hook(lua_State* L, lua_Debug *ar)
|
||||
{
|
||||
|
@ -268,9 +281,10 @@ static int luaPlayFile(lua_State *L)
|
|||
strncpy(str, filename, AUDIO_FILENAME_MAXLEN - (str-file));
|
||||
file[AUDIO_FILENAME_MAXLEN] = 0;
|
||||
PLAY_FILE(file, 0, 0);
|
||||
return 0;
|
||||
}
|
||||
else {
|
||||
PLAY_FILE(filename, 0, 0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1358,14 +1372,29 @@ static const luaL_Reg lcdLib[] = {
|
|||
{ NULL, NULL } /* sentinel */
|
||||
};
|
||||
|
||||
void luaInit()
|
||||
void luaDisable()
|
||||
{
|
||||
POPUP_WARNING("Lua disabled!");
|
||||
luaState = INTERPRETER_PANIC;
|
||||
}
|
||||
|
||||
void luaClose()
|
||||
{
|
||||
if (L) {
|
||||
lua_close(L);
|
||||
PROTECT_LUA() {
|
||||
lua_close(L); // this should not panic, but we make sure anyway
|
||||
}
|
||||
else {
|
||||
// we can only disable Lua for the rest of the session
|
||||
luaDisable();
|
||||
}
|
||||
UNPROTECT_LUA();
|
||||
L = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
L = luaL_newstate();
|
||||
|
||||
void luaRegisterAll()
|
||||
{
|
||||
// Init lua
|
||||
luaL_openlibs(L);
|
||||
|
||||
|
@ -1441,13 +1470,50 @@ void luaInit()
|
|||
lua_registerint(L, "TIMEHOUR", TIMEHOUR);
|
||||
}
|
||||
|
||||
void luaInit()
|
||||
{
|
||||
luaClose();
|
||||
if (luaState != INTERPRETER_PANIC) {
|
||||
L = luaL_newstate();
|
||||
if (L) {
|
||||
// install our panic handler
|
||||
lua_atpanic(L, &custom_lua_atpanic);
|
||||
|
||||
// protect libs and constants registration
|
||||
PROTECT_LUA() {
|
||||
luaRegisterAll();
|
||||
}
|
||||
else {
|
||||
// if we got panic during registration
|
||||
// we disable Lua for this session
|
||||
luaDisable();
|
||||
}
|
||||
UNPROTECT_LUA();
|
||||
}
|
||||
else {
|
||||
/* log error and return */
|
||||
luaDisable();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void luaFree(ScriptInternalData & sid)
|
||||
{
|
||||
PROTECT_LUA() {
|
||||
if (sid.run) {
|
||||
luaL_unref(L, LUA_REGISTRYINDEX, sid.run);
|
||||
sid.run = 0;
|
||||
}
|
||||
if (sid.background) {
|
||||
luaL_unref(L, LUA_REGISTRYINDEX, sid.background);
|
||||
sid.background = 0;
|
||||
}
|
||||
lua_gc(L, LUA_GCCOLLECT, 0);
|
||||
}
|
||||
else {
|
||||
luaDisable();
|
||||
}
|
||||
UNPROTECT_LUA();
|
||||
}
|
||||
|
||||
int luaLoad(const char *filename, ScriptInternalData & sid, ScriptInputsOutputs * sio=NULL)
|
||||
|
@ -1461,6 +1527,7 @@ int luaLoad(const char *filename, ScriptInternalData & sid, ScriptInputsOutputs
|
|||
|
||||
SET_LUA_INSTRUCTIONS_COUNT(MANUAL_SCRIPTS_MAX_INSTRUCTIONS);
|
||||
|
||||
PROTECT_LUA() {
|
||||
if (luaL_loadfile(L, filename) == 0 &&
|
||||
lua_pcall(L, 0, 1, 0) == 0 &&
|
||||
lua_istable(L, -1)) {
|
||||
|
@ -1491,17 +1558,24 @@ int luaLoad(const char *filename, ScriptInternalData & sid, ScriptInputsOutputs
|
|||
|
||||
if (init) {
|
||||
lua_rawgeti(L, LUA_REGISTRYINDEX, init);
|
||||
luaL_unref(L, LUA_REGISTRYINDEX, init);
|
||||
if (lua_pcall(L, 0, 0, 0) != 0) {
|
||||
TRACE("Error in script %s init: %s", filename, lua_tostring(L, -1));
|
||||
sid.state = SCRIPT_SYNTAX_ERROR;
|
||||
}
|
||||
luaL_unref(L, LUA_REGISTRYINDEX, init);
|
||||
lua_gc(L, LUA_GCCOLLECT, 0);
|
||||
}
|
||||
}
|
||||
else {
|
||||
TRACE("Error in script %s: %s", filename, lua_tostring(L, -1));
|
||||
sid.state = SCRIPT_SYNTAX_ERROR;
|
||||
}
|
||||
}
|
||||
else {
|
||||
TRACE("Panic in script %s: %s", filename, lua_tostring(L, -1));
|
||||
sid.state = SCRIPT_PANIC;
|
||||
}
|
||||
UNPROTECT_LUA();
|
||||
|
||||
if (sid.state != SCRIPT_OK) {
|
||||
luaFree(sid);
|
||||
|
@ -1663,6 +1737,9 @@ void luaError(uint8_t error)
|
|||
case SCRIPT_KILLED:
|
||||
msg = "Script killed";
|
||||
break;
|
||||
case SCRIPT_PANIC:
|
||||
msg = "Script panic";
|
||||
break;
|
||||
}
|
||||
POPUP_WARNING(msg);
|
||||
}
|
||||
|
@ -1670,33 +1747,24 @@ void luaError(uint8_t error)
|
|||
|
||||
void luaExec(const char *filename)
|
||||
{
|
||||
LUA_RESET();
|
||||
luaInit();
|
||||
|
||||
standaloneScript.state = SCRIPT_NOFILE;
|
||||
int result = luaLoad(filename, standaloneScript);
|
||||
// TODO the same with run ...
|
||||
if (result == SCRIPT_OK) {
|
||||
luaState = LUASTATE_STANDALONE_SCRIPT_RUNNING;
|
||||
luaState = INTERPRETER_RUNNING_STANDALONE_SCRIPT;
|
||||
}
|
||||
else {
|
||||
luaError(result);
|
||||
luaState = INTERPRETER_RELOAD_PERMANENT_SCRIPTS;
|
||||
}
|
||||
}
|
||||
|
||||
void luaTask(uint8_t evt)
|
||||
void luaDoOneRunStandalone(uint8_t evt)
|
||||
{
|
||||
lcd_locked = false;
|
||||
static uint8_t luaDisplayStatistics = false;
|
||||
|
||||
uint32_t t0 = get_tmr10ms();
|
||||
static uint32_t lastLuaTime = 0;
|
||||
uint16_t interval = (lastLuaTime == 0 ? 0 : (t0 - lastLuaTime));
|
||||
lastLuaTime = t0;
|
||||
if (interval > maxLuaInterval) {
|
||||
maxLuaInterval = interval;
|
||||
}
|
||||
|
||||
if (luaState & LUASTATE_STANDALONE_SCRIPT_RUNNING) {
|
||||
// standalone script
|
||||
if (standaloneScript.state == SCRIPT_OK && standaloneScript.run) {
|
||||
SET_LUA_INSTRUCTIONS_COUNT(MANUAL_SCRIPTS_MAX_INSTRUCTIONS);
|
||||
lua_rawgeti(L, LUA_REGISTRYINDEX, standaloneScript.run);
|
||||
|
@ -1706,7 +1774,7 @@ void luaTask(uint8_t evt)
|
|||
if (instructionsPercent > 100) {
|
||||
TRACE("Script killed");
|
||||
standaloneScript.state = SCRIPT_KILLED;
|
||||
luaState = LUASTATE_RELOAD_MODEL_SCRIPTS;
|
||||
luaState = INTERPRETER_RELOAD_PERMANENT_SCRIPTS;
|
||||
}
|
||||
else if (lua_isstring(L, -1)) {
|
||||
char nextScript[_MAX_LFN+1];
|
||||
|
@ -1717,7 +1785,7 @@ void luaTask(uint8_t evt)
|
|||
else {
|
||||
TRACE("Script error");
|
||||
standaloneScript.state = SCRIPT_SYNTAX_ERROR;
|
||||
luaState = LUASTATE_RELOAD_MODEL_SCRIPTS;
|
||||
luaState = INTERPRETER_RELOAD_PERMANENT_SCRIPTS;
|
||||
}
|
||||
}
|
||||
else {
|
||||
|
@ -1726,13 +1794,12 @@ void luaTask(uint8_t evt)
|
|||
if (scriptResult != 0) {
|
||||
TRACE("Script finished with status %d", scriptResult);
|
||||
standaloneScript.state = SCRIPT_NOFILE;
|
||||
luaState = LUASTATE_RELOAD_MODEL_SCRIPTS;
|
||||
luaState = INTERPRETER_RELOAD_PERMANENT_SCRIPTS;
|
||||
}
|
||||
else if (luaDisplayStatistics) {
|
||||
int gc = 1000*lua_gc(L, LUA_GCCOUNT, 0) + lua_gc(L, LUA_GCCOUNTB, 0);
|
||||
lcd_hline(0, 7*FH-1, lcdLastPos+FW, ERASE);
|
||||
lcd_puts(0, 7*FH, "GV Use: ");
|
||||
lcd_outdezAtt(lcdLastPos, 7*FH, gc, LEFT);
|
||||
lcd_outdezAtt(lcdLastPos, 7*FH, luaGetMemUsed(), LEFT);
|
||||
lcd_putc(lcdLastPos, 7*FH, 'b');
|
||||
lcd_hline(0, 7*FH-2, lcdLastPos+FW, FORCE);
|
||||
lcd_vlineStip(lcdLastPos+FW, 7*FH-2, FH+2, SOLID, FORCE);
|
||||
|
@ -1742,34 +1809,29 @@ void luaTask(uint8_t evt)
|
|||
else {
|
||||
TRACE("Script error: %s", lua_tostring(L, -1));
|
||||
standaloneScript.state = (instructionsPercent > 100 ? SCRIPT_KILLED : SCRIPT_SYNTAX_ERROR);
|
||||
luaState = LUASTATE_RELOAD_MODEL_SCRIPTS;
|
||||
luaState = INTERPRETER_RELOAD_PERMANENT_SCRIPTS;
|
||||
}
|
||||
|
||||
if (standaloneScript.state != SCRIPT_OK) {
|
||||
luaError(standaloneScript.state);
|
||||
luaState = INTERPRETER_RELOAD_PERMANENT_SCRIPTS;
|
||||
}
|
||||
|
||||
if (evt == EVT_KEY_LONG(KEY_EXIT)) {
|
||||
TRACE("Script force exit");
|
||||
killEvents(evt);
|
||||
standaloneScript.state = SCRIPT_NOFILE;
|
||||
luaState = LUASTATE_RELOAD_MODEL_SCRIPTS;
|
||||
luaState = INTERPRETER_RELOAD_PERMANENT_SCRIPTS;
|
||||
}
|
||||
else if (evt == EVT_KEY_LONG(KEY_MENU)) {
|
||||
killEvents(evt);
|
||||
luaDisplayStatistics = !luaDisplayStatistics;
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
// model scripts
|
||||
if (luaState & LUASTATE_RELOAD_MODEL_SCRIPTS) {
|
||||
luaState = 0;
|
||||
LUA_RESET();
|
||||
luaLoadPermanentScripts();
|
||||
}
|
||||
}
|
||||
|
||||
for (int i=0; i<luaScriptsCount; i++) {
|
||||
void luaDoOneRunPermanentScript(uint8_t evt, int i)
|
||||
{
|
||||
ScriptInternalData & sid = scriptInternalData[i];
|
||||
if (sid.state == SCRIPT_OK) {
|
||||
SET_LUA_INSTRUCTIONS_COUNT(PERMANENT_SCRIPTS_MAX_INSTRUCTIONS);
|
||||
|
@ -1796,7 +1858,7 @@ void luaTask(uint8_t evt)
|
|||
else if (sid.reference >= SCRIPT_FUNC_FIRST && sid.reference <= SCRIPT_FUNC_LAST) {
|
||||
CustomFnData & fn = g_model.funcSw[sid.reference-SCRIPT_FUNC_FIRST];
|
||||
if (!getSwitch(fn.swtch)) {
|
||||
continue;
|
||||
return;
|
||||
}
|
||||
#if defined(SIMU) || defined(DEBUG)
|
||||
filename = fn.play.name;
|
||||
|
@ -1816,7 +1878,7 @@ void luaTask(uint8_t evt)
|
|||
lua_rawgeti(L, LUA_REGISTRYINDEX, sid.background);
|
||||
}
|
||||
else {
|
||||
continue;
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (lua_pcall(L, inputsCount, sio ? sio->outputsCount : 0, 0) == 0) {
|
||||
|
@ -1852,11 +1914,12 @@ void luaTask(uint8_t evt)
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
lua_gc(L, LUA_GCCOLLECT, 0);
|
||||
}
|
||||
|
||||
void luaDoGc()
|
||||
{
|
||||
PROTECT_LUA() {
|
||||
lua_gc(L, LUA_GCSTEP /*LUA_GCCOLLECT*/, 0); // LUA_GCSTEP is enough
|
||||
#if defined(SIMU) || defined(DEBUG)
|
||||
static int lastgc = 0;
|
||||
int gc = luaGetMemUsed();
|
||||
|
@ -1865,6 +1928,60 @@ void luaTask(uint8_t evt)
|
|||
TRACE("GC Use: %dbytes", gc);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else {
|
||||
// we disable Lua for the rest of the session
|
||||
luaDisable();
|
||||
}
|
||||
UNPROTECT_LUA();
|
||||
}
|
||||
|
||||
void luaTask(uint8_t evt)
|
||||
{
|
||||
lcd_locked = false;
|
||||
|
||||
uint32_t t0 = get_tmr10ms();
|
||||
static uint32_t lastLuaTime = 0;
|
||||
uint16_t interval = (lastLuaTime == 0 ? 0 : (t0 - lastLuaTime));
|
||||
lastLuaTime = t0;
|
||||
if (interval > maxLuaInterval) {
|
||||
maxLuaInterval = interval;
|
||||
}
|
||||
|
||||
if (luaState & INTERPRETER_RUNNING_STANDALONE_SCRIPT) {
|
||||
PROTECT_LUA() {
|
||||
luaDoOneRunStandalone(evt);
|
||||
}
|
||||
else {
|
||||
POPUP_WARNING("Script Panic!");
|
||||
luaState = INTERPRETER_RELOAD_PERMANENT_SCRIPTS;
|
||||
}
|
||||
UNPROTECT_LUA();
|
||||
}
|
||||
else {
|
||||
// model scripts
|
||||
if (luaState & INTERPRETER_RELOAD_PERMANENT_SCRIPTS) {
|
||||
luaState = 0;
|
||||
luaInit();
|
||||
if (!L) return;
|
||||
luaLoadPermanentScripts();
|
||||
}
|
||||
|
||||
for (int i=0; i<luaScriptsCount; i++) {
|
||||
PROTECT_LUA() {
|
||||
luaDoOneRunPermanentScript(evt, i);
|
||||
}
|
||||
else {
|
||||
// we disable this script for the rest of the session
|
||||
ScriptInternalData & sid = scriptInternalData[i];
|
||||
sid.state = SCRIPT_PANIC;
|
||||
luaFree(sid);
|
||||
}
|
||||
UNPROTECT_LUA();
|
||||
}
|
||||
}
|
||||
|
||||
luaDoGc();
|
||||
|
||||
t0 = get_tmr10ms() - t0;
|
||||
if (t0 > maxLuaDuration) {
|
||||
|
@ -1874,5 +1991,5 @@ void luaTask(uint8_t evt)
|
|||
|
||||
int luaGetMemUsed()
|
||||
{
|
||||
return 1000*lua_gc(L, LUA_GCCOUNT, 0) + lua_gc(L, LUA_GCCOUNTB, 0);
|
||||
return (lua_gc(L, LUA_GCCOUNT, 0) << 10) + lua_gc(L, LUA_GCCOUNTB, 0);
|
||||
}
|
||||
|
|
|
@ -2505,6 +2505,10 @@ void opentxClose()
|
|||
// TODO needed? telemetryEnd();
|
||||
#endif
|
||||
|
||||
#if defined(LUA)
|
||||
luaClose();
|
||||
#endif
|
||||
|
||||
#if defined(SDCARD)
|
||||
closeLogs();
|
||||
sdDone();
|
||||
|
@ -3352,8 +3356,6 @@ void opentxInit(OPENTX_INIT_ARGS)
|
|||
rtcInit();
|
||||
#endif
|
||||
|
||||
LUA_INIT();
|
||||
|
||||
if (g_eeGeneral.backlightMode != e_backlight_mode_off) backlightOn(); // on Tx start turn the light on
|
||||
|
||||
if (UNEXPECTED_SHUTDOWN()) {
|
||||
|
|
|
@ -1475,7 +1475,8 @@ enum AUDIO_SOUNDS {
|
|||
SCRIPT_OK,
|
||||
SCRIPT_NOFILE,
|
||||
SCRIPT_SYNTAX_ERROR,
|
||||
SCRIPT_KILLED
|
||||
SCRIPT_PANIC,
|
||||
SCRIPT_KILLED,
|
||||
};
|
||||
enum ScriptReference {
|
||||
SCRIPT_MIX_FIRST,
|
||||
|
@ -1498,13 +1499,18 @@ enum AUDIO_SOUNDS {
|
|||
uint8_t outputsCount;
|
||||
ScriptOutput outputs[MAX_SCRIPT_OUTPUTS];
|
||||
};
|
||||
#define LUASTATE_STANDALONE_SCRIPT_RUNNING 1
|
||||
#define LUASTATE_RELOAD_MODEL_SCRIPTS 2
|
||||
enum InterpreterState {
|
||||
INTERPRETER_RUNNING_PERMANENT_SCRIPTS,
|
||||
INTERPRETER_RUNNING_STANDALONE_SCRIPT,
|
||||
INTERPRETER_RELOAD_PERMANENT_SCRIPTS,
|
||||
INTERPRETER_PANIC,
|
||||
};
|
||||
extern uint8_t luaState;
|
||||
extern uint8_t luaScriptsCount;
|
||||
extern ScriptInternalData standaloneScript;
|
||||
extern ScriptInternalData scriptInternalData[MAX_SCRIPTS];
|
||||
extern ScriptInputsOutputs scriptInputsOutputs[MAX_SCRIPTS];
|
||||
void luaClose();
|
||||
void luaInit();
|
||||
void luaTask(uint8_t evt);
|
||||
void luaExec(const char *filename);
|
||||
|
@ -1513,13 +1519,23 @@ enum AUDIO_SOUNDS {
|
|||
int luaGetMemUsed();
|
||||
#define luaGetCpuUsed(idx) scriptInternalData[idx].instructions
|
||||
bool isTelemetryScriptAvailable(uint8_t index);
|
||||
#define LUA_INIT()
|
||||
#define LUA_RESET() luaInit()
|
||||
#define LUA_LOAD_MODEL_SCRIPTS() luaState |= LUASTATE_RELOAD_MODEL_SCRIPTS
|
||||
#define LUA_LOAD_MODEL_SCRIPT(idx) luaState |= LUASTATE_RELOAD_MODEL_SCRIPTS
|
||||
#define LUA_LOAD_MODEL_SCRIPTS() luaState |= INTERPRETER_RELOAD_PERMANENT_SCRIPTS
|
||||
#define LUA_LOAD_MODEL_SCRIPT(idx) luaState |= INTERPRETER_RELOAD_PERMANENT_SCRIPTS
|
||||
|
||||
// Lua PROTECT/UNPROTECT
|
||||
#include <setjmp.h>
|
||||
struct our_longjmp {
|
||||
struct our_longjmp *previous;
|
||||
jmp_buf b;
|
||||
volatile int status; /* error code */
|
||||
};
|
||||
extern struct our_longjmp * global_lj;
|
||||
#define PROTECT_LUA() { struct our_longjmp lj; \
|
||||
lj.previous = global_lj; /* chain new error handler */ \
|
||||
global_lj = &lj; \
|
||||
if (setjmp(lj.b) == 0)
|
||||
#define UNPROTECT_LUA() global_lj = lj.previous; } /* restore old error handler */
|
||||
#else
|
||||
#define LUA_INIT()
|
||||
#define LUA_RESET()
|
||||
#define LUA_LOAD_MODEL_SCRIPTS()
|
||||
#define LUA_LOAD_MODEL_SCRIPT(idx)
|
||||
#endif
|
||||
|
|
|
@ -309,8 +309,6 @@ void *main_thread(void *)
|
|||
|
||||
if (g_eeGeneral.backlightMode != e_backlight_mode_off) backlightOn(); // on Tx start turn the light on
|
||||
|
||||
LUA_INIT();
|
||||
|
||||
if (main_thread_running == 1) {
|
||||
opentxStart();
|
||||
}
|
||||
|
|
|
@ -99,6 +99,13 @@ uint32_t stack_free(uint32_t tid)
|
|||
stack = audioStack;
|
||||
size = AUDIO_STACK_SIZE;
|
||||
break;
|
||||
#if defined(PCBTARANIS)
|
||||
case 255:
|
||||
// main stack
|
||||
stack = (OS_STK *)&_main_stack_start;
|
||||
size = ((unsigned char *)&_estack - (unsigned char *)&_main_stack_start) / 4;
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
|
@ -107,7 +114,7 @@ uint32_t stack_free(uint32_t tid)
|
|||
for (; i<size; i++)
|
||||
if (stack[i] != 0x55555555)
|
||||
break;
|
||||
return i;
|
||||
return i*4;
|
||||
}
|
||||
|
||||
void mixerTask(void * pdata)
|
||||
|
|
|
@ -183,7 +183,6 @@ int main(int argc, char **argv)
|
|||
StartEepromThread(NULL);
|
||||
g_menuStackPtr = 0;
|
||||
g_menuStack[0] = menuMainView;
|
||||
LUA_RESET();
|
||||
::testing::InitGoogleTest(&argc, argv);
|
||||
return RUN_ALL_TESTS();
|
||||
}
|
||||
|
|
|
@ -52,6 +52,8 @@ extern const char * zchar2string(const char * zstring, int size);
|
|||
void luaExecStr(const char * str)
|
||||
{
|
||||
extern lua_State * L;
|
||||
if (!L) luaInit();
|
||||
if (!L) FAIL() << "No Lua state!";
|
||||
if (luaL_dostring(L, str)) {
|
||||
FAIL() << "lua error: " << lua_tostring(L, -1);
|
||||
}
|
||||
|
@ -98,4 +100,51 @@ TEST(Lua, testSetTelemetryChannel)
|
|||
|
||||
}
|
||||
|
||||
TEST(Lua, testPanicProtection)
|
||||
{
|
||||
bool passed = false;
|
||||
PROTECT_LUA() {
|
||||
PROTECT_LUA() {
|
||||
//simulate panic
|
||||
longjmp(global_lj->b, 1);
|
||||
}
|
||||
else {
|
||||
//we should come here
|
||||
passed = true;
|
||||
}
|
||||
UNPROTECT_LUA();
|
||||
}
|
||||
else {
|
||||
// an not here
|
||||
// TRACE("testLuaProtection: test 1 FAILED");
|
||||
FAIL() << "Failed test 1";
|
||||
}
|
||||
UNPROTECT_LUA()
|
||||
|
||||
EXPECT_EQ(passed, true);
|
||||
|
||||
passed = false;
|
||||
|
||||
PROTECT_LUA() {
|
||||
PROTECT_LUA() {
|
||||
int a = 5;
|
||||
a = a; // avoids the warning
|
||||
}
|
||||
else {
|
||||
//we should not come here
|
||||
// TRACE("testLuaProtection: test 2 FAILED");
|
||||
FAIL() << "Failed test 2";
|
||||
}
|
||||
UNPROTECT_LUA()
|
||||
//simulate panic
|
||||
longjmp(global_lj->b, 1);
|
||||
}
|
||||
else {
|
||||
// we should come here
|
||||
passed = true;
|
||||
}
|
||||
UNPROTECT_LUA()
|
||||
|
||||
EXPECT_EQ(passed, true);
|
||||
}
|
||||
#endif
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue