Thanks Mike for confirmation! It helped me to find the problem. My FFI CDEF
generator produced one struct 16-bytes shorter than C expected, which
caused the memory overwrite.
On Mon, May 3, 2021 at 12:17 AM Mike Pall <mikelj-2105@xxxxxxx> wrote:
Martin Cohen wrote:
void lj_debug_shortname(char *out, GCstr *str)not
{
const char *src = strdata(str);
if (*src == '=') {
strncpy(out, src+1, LUA_IDSIZE); /* Remove first char. */
out[LUA_IDSIZE-1] = '\0'; /* Ensures null termination. */
} else if (*src == '@') { /* Output "source", or "...source". */
size_t len = str->len-1;
src++; /* Skip the `@' */
if (len >= LUA_IDSIZE) {
src += len-(LUA_IDSIZE-4); /* Get last part of file name. */
*out++ = '.'; *out++ = '.'; *out++ = '.';
}
strcpy(out, src);
Error occurs on last line pasted (strcpy) and is caused by `src` starting
with `@` but `str->len` being 0. That causes it to enter the `*src == '@'
branch, but by that time `src` already points to invalid memory that is
0 terminated.
This can't happen there, since all interned strings (GCstr) are
zero-terminated beyond their given length:
"": str->len == 0, src[0] == '\0' (valid memory, not '@')
"@": str->len == 1, src[0] == '@', src[1] == '\0' (valid memory)
Maybe you've modified the memory of some const char * string
returned by lua_tostring() or similar? Also check your usage of
the chunkname argument for any lua_load* or luaL_load* call.
--Mike