sachin varshney
unread,Apr 9, 2025, 5:46:29 AM4/9/25Sign in to reply to author
Sign in to forward
You do not have permission to delete messages in this group
Either email addresses are anonymous for this group or you need the view member email addresses permission to view the original message
to lua-l
Hi Lua Team,
Recently we upgraded lua library from lua-5.0.2 to lua-5.4.6, we've observed what may be an unexpected behavior when
using assert() within Lua code that's executed via lua_pcall() from the C host application.
Summary ;
==========
We run this Lua snippet through load() and pcall():
local func, err = load("assert(false, 'my error')")
local success, result = pcall(func)
When executed from C using lua_pcall(), we observe the following:
lua_pcall() returns 0, which indicates success,
The Lua stack is empty (lua_gettop(L) == 0),
There is no error message or return values on the stack.
This makes it impossible to tell from the C side that an assert() failure occurred — which is highly misleading, as no error is propagated.
Test Setup (C Code) :
lua_getglobal(L, "dobuffer");
lua_pushstring(L, "assert(false, 'fail message')");
int ret = lua_pcall(L, 1, 2, 0);
int top = lua_gettop(L);
printf("lua_pcall returned: %d, stack top = %d\n", ret, top);
if (ret != 0) {
printf("Lua Error: %s\n", lua_tostring(L, -1));
} else if (top == 0) {
printf("Unexpected: lua_pcall returned success, but stack is empty.\n");
}
Additional Logs from Lua Internals :
=====================================
luaB_assert invoked
luaD_rawrunprotected invoked 1: 2
luaD_closeprotected for loop ret = 2
luaD_rawrunprotected invoked 1: 0
Result output displayed = 0
From this, it appears an error (ret = 2) was caught and suppressed internally, leaving the C API (lua_pcall) unaware that an error happened.
❗ Why This Matters
This breaks the expected contract between Lua and host C code. From the C side, we rely on lua_pcall() to return non-zero on error — if the stack is empty and ret == 0, we assume everything went fine.
❓ Request for Clarification
Is this behavior expected? Should assert(false, "msg") inside load() always be considered recoverable?
If so, what is the recommended way to raise a Lua error from within such a loaded string so that C can detect it?
If this behavior isn't intended, could it possibly be related to the luaB_assert or luaD_rawrunprotected logic?
We're happy to share more details or context from our side if it helps clarify the issue
Thanks and best regards,
Varshney Sachin