[Date Prev][Date Next][Thread Prev][Thread Next]
[Date Index]
[Thread Index]
- Subject: Re: Problems with lifecycle of states
- From: "Peter Cawley" <lua@...>
- Date: Wed, 31 Oct 2007 15:50:25 +0000
I've commented each line of the code you provided with the state of
the stack after the call:
state.m_state = lua_newthread(hostLuaState); // m_state < top
// Prevent the new thread from being garbage collected
lua_pushvalue(hostLuaState, -1); // m_state m_state < top
// Add to our list of registered states, keeping a reference to the
state so we can remove it later on
m_RegisteredStates.push_back(ThreadRef(&state, hostLuaState,
luaL_ref(hostLuaState, LUA_REGISTRYINDEX))); // m_state < top
// Retrieve our lookup table from the global index table
lua_pushstring(m_MainState, "lookup"); // m_state "lookup" < top
lua_gettable(m_MainState, LUA_GLOBALSINDEX); // m_state lookup < top
// Set lookup[state.m_state] = &state
lua_pushlightuserdata(m_MainState, state.m_state); // m_state lookup
m_state_ptr < top
lua_pushlightuserdata(m_MainState, &state); // m_state lookup
m_state_ptr state_ptr < top
lua_settable(m_MainState, -3); // m_state lookup < top
// Remove the table from the stack
lua_pop(m_MainState, 1); // m_state < top
Assuming the ThreadRef constructor doesn't pop anything off the stack,
then you are left with the thread still sitting on the stack. So
unless you are popping it off somewhere, it will remain there and
prevent garbage collection.
On 31/10/2007, Tom Miles <Tom@creative-assembly.co.uk> wrote:
> Hello, and thanks for your reply.
>
> Point 2 was catching me out. I am storing the state as a key in lookup
> table. I'ld set the table up to be weak, but set __mode to "v", not
> "k", so it was weak over value, not key. However changing this hasn't
> solved my issues. I've checked the host states stack after the creation
> of the sub state, and it is empty, so I'm pretty confident that the only
> references to my created states are the explicit lua_ref(), and the weak
> reference in my lookup. Therefore, when I use lua_unref(), it SHOULD be
> applicable for garbage collection. However, the memory allocated for the
> state is only freed when I call lua_close() on my main state at shut
> down.
>
> I think I'm missing something obvious, but I don't know what.
>
> > -----Original Message-----
> > From: lua-bounces@bazar2.conectiva.com.br
> > [mailto:lua-bounces@bazar2.conectiva.com.br] On Behalf Of Peter Cawley
> > Sent: 30 October 2007 18:06
> > To: Lua list
> > Subject: Re: Problems with lifecycle of states
> >
> > The comment on the second line might explain why they are not
> > garbage collected:
> > lua_pushvalue(hostLuaState, -1); // Prevent the new thread from
> > being garbage collected
> >
> > If a lua object (in this case a thread) is in a stack, being
> > a key in a table or being a value in a table, then it will
> > not be garbage collected. If you want it garbage collected:
> > 1) Make sure it isn't on the stack anywhere (the stack of the
> > main state, or the stack of any threads)
> > 2) Make sure it isn't the key or value of a key/value pair in a table
> >
> > Removing a key from a table is the same as removing a
> > key/value pair; "x.y = nil" removes the "y" key and the
> > associated value from "x".
> >
> > Weak tables
> > (http://www.lua.org/manual/5.1/manual.html#2.10.2) are an
> > exception to this rule, in that a table can be defined so
> > that the keys or values in the table are not counted as
> > references to objects.
> > When a key or value of a key/value pair is garbage collected,
> > then the entire key/value pair is removed from the table
> > automatically.
> >
> > On 30/10/2007, Tom Miles <Tom@creative-assembly.co.uk> wrote:
> > > Hi,
> > >
> > > Having just started using Decda to debug my lua project
> > I've noticed
> > > that my threads are never getting garbage collected. I've searched
> > > the archives about this, and found some vaguely relevant posts, but
> > > none which can address my situation, so apologies if I've
> > missed something.
> > >
> > > The states are set up thusly:
> > >
> > > state.m_state = lua_newthread(hostLuaState);
> > > lua_pushvalue(hostLuaState, -1); // Prevent the new
> > thread from
> > > being garbage collected
> > >
> > > // Add to our list of registered states, keeping a reference to the
> > > state so we can remove it later on
> > > m_RegisteredStates.push_back(ThreadRef(&state, hostLuaState,
> > > luaL_ref(hostLuaState, LUA_REGISTRYINDEX)));
> > >
> > > // Retrieve our lookup table from the global index table
> > > lua_pushstring(m_MainState, "lookup"); lua_gettable(m_MainState,
> > > LUA_GLOBALSINDEX);
> > >
> > > // Set lookup[state.m_state] = &state
> > > lua_pushlightuserdata(m_MainState, state.m_state);
> > > lua_pushlightuserdata(m_MainState, &state);
> > >
> > > lua_settable(m_MainState, -3);
> > > // Remove the table from the stack
> > > lua_pop(m_MainState, 1);
> > >
> > >
> > > And "freed":
> > >
> > > CA_STD::LIST<ThreadRef>::iterator iter =
> > > std::find_if(m_RegisteredStates.begin(), m_RegisteredStates.end(),
> > > Finder(&state)); if (iter != m_RegisteredStates.end())
> > > luaL_unref((*iter).host, LUA_REGISTRYINDEX, (*iter).ref);
> > >
> > > This has been working for ages, but I realised I still used
> > the lookup
> > > table, so I added:
> > >
> > > // Remove the state from the lookup table by setting
> > > lookup[state.m_state] = nil lua_pushstring(m_MainState, "lookup");
> > > lua_gettable(m_MainState, LUA_GLOBALSINDEX);
> > > lua_pushlightuserdata(m_MainState, state.m_state);
> > > lua_pushnil(m_MainState); lua_settable(m_MainState, -3);
> > >
> > > Which has added lots of random lockups and crashes within
> > lua, usually
> > > during garbage colled. It would seem that if I remove the
> > value from
> > > my lookup table then states are being pulled from under my
> > feet. Or
> > > the lookup table removal code is corrupting the state somehow.
> > >
> > > So, a couple of questions:
> > > 1. What am I doing wrong?
> > > 2. If I use the state as a key in a table, does that count as a
> > > reference to the object as far as the GC is concerned? If
> > so, how do
> > > I remove a key from the table?
> > >
> > > Any help would be very greatfully recieved.
> > >
> > > Tom
> > >
> > >
> > >
> > > Tom Miles
> > > creative assembly
> > --------------------------------------------------------------
> > --------------
> > > DISCLAIMER
> > > This email is sent by The Creative Assembly Limited company
> > No. 03425917, registered in England &Wales registered office
> > 27 Great West Road, Middlesex, TW8 9BW, England. The contents
> > of this e-mail and any attachments are confidential to the
> > intended recipient and may also be legally privileged. Unless
> > you are the named addressee (or authorised to receive for the
> > addressee) of this email you may not copy, disclose or
> > distribute it to anyone else. If you have received this email
> > in error, please notify us immediately by e-mail on
> > postmaster@creative-assembly.co.uk and then delete the email
> > and any copies. The Creative Assembly Limited have made all
> > reasonable efforts to ensure that this e-mail and any
> > attached documents or software are free from software
> > viruses, but it is the recipient's responsibility to confirm this.
> > >
> > >
> >
>
>
>
> Tom Miles
> creative assembly ----------------------------------------------------------------------------
> DISCLAIMER
> This email is sent by The Creative Assembly Limited company No. 03425917, registered in England &Wales registered office 27 Great West Road, Middlesex, TW8 9BW, England. The contents of this e-mail and any attachments are confidential to the intended recipient and may also be legally privileged. Unless you are the named addressee (or authorised to receive for the addressee) of this email you may not copy, disclose or distribute it to anyone else. If you have received this email in error, please notify us immediately by e-mail on postmaster@creative-assembly.co.uk and then delete the email and any copies. The Creative Assembly Limited have made all reasonable efforts to ensure that this e-mail and any attached documents or software are free from software viruses, but it is the recipient's responsibility to confirm this.
>
>