lua-users home
lua-l archive

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


I have a reproducible situation where luai_userstatefree is called on a thread that never had luai_userstatethread called on it. This looks like a bug in Lua, and it can cause heap corruption.


The problem occurs if the allocator returns NULL in a call to lua_newthread. If the second allocation inside lua_newthread fails, then the thread is kept around in a non-initialized state. When you shutdown with lua_close, then luai_userstatefree is called on this thread, even though luai_userstatethread was never called!


Below are the steps to reproduce the bug on a stock 5.1.4 source. All it does is open a state, attempt to create a thread, and then close the state:




#include "stdio.h"

#define luai_userstateopen(L)       ((void)L)

#define luai_userstateclose(L)            ((void)L)

#define luai_userstatethread(L,L1)      (fprintf(stderr,"luai_userstatethread\n"))

#define luai_userstatefree(L)       (fprintf(stderr,"luai_userstatefree\n"))

#define luai_userstateresume(L,n)   ((void)L)

#define luai_userstateyield(L,n)    ((void)L)






#define lua_c


#include "lua.h"


static int trigger = 0;


// A simple override of l_alloc

static void *allocator (void *ud, void *ptr, size_t osize, size_t nsize) {



  if (nsize == 0) {


    return NULL;


  else if (nsize>osize && (--trigger==0))


        // Simulate an out-of-memory condition

        return 0;



    return realloc(ptr, nsize);



static int pmain (lua_State *L) {


  // setting trigger to 2 will cause the 2nd allocation to fail.

  // setting trigger to 0 will cause no memory error,

  // and you will see the correct behavior.

  trigger = 2;         




  return 0;



int main (int argc, char **argv) {

  lua_State *L = lua_newstate(allocator, NULL);

  lua_cpcall(L, &pmain, 0);




  // At this point the console will display how many times

  // luai_userstatethread and luai_userstatefree where called

  return 0;