lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


Hello all,

I'm trying to avoid a potential denial of service situation with the execution of Lua code where a user can enter code that takes a long time to run, thereby hanging the interpreter. Proving to be more difficult than it seems.

My solution registers a hook function that executes based on the count hook. It checks the current time and if execution has timed out, it does a longjmp out of the interpreter and back into the host application. Something like the code below. It works fine, with the exception that this only ever works once on a given lua_State because if the call ever times out, the lua_State will no longer call hooks on subsequent execution (because L->activehook is set to 0 and never gets set back to 1 because my longjmp bypasses that code). Lua hides the activehook variable from the host so I can't reset it.

Are there any good solutions to this, or alternatives to implementing the same functionality?

Thanks,
Gerald.


static void my_hook(lua_State *L, lua_Debug *ar) {
    /* ... get lctx containing timeout values */
    if (time(NULL) >= lctx->timeout) {
	    longjmp(lctx->timeout_jmp, 1);
    }
}

static void timed_lua(lua_State *L) {
/* ... Set up lctx containing jmp_buf for longjmp and timeout values */
    lua_sethook(L, my_hook, LUA_MASKCOUNT, 1024);
    if (setjmp(lctx->timeout_jmp) == 0) {
	lctx->timeout = time(NULL) + timeout;
	rv = luaL_dostring(L, "...");	
	/* Didn't time out */
    } else {
	/* Timed out */
    }
}