public static int MetaRefManGc(IntPtr l)
        {
            using (var lr = new LuaStateRecover(l))
            {
                var oldtop = l.gettop();
                if (oldtop < 1)
                {
                    return(0);
                }

                if (l.isuserdata(1) && !l.islightuserdata(1))
                {
                    IntPtr   pud    = l.touserdata(1);
                    IntPtr   hval   = Marshal.ReadIntPtr(pud);
                    GCHandle handle = (GCHandle)hval;

                    LuaThreadRefMan ud = null;
                    try
                    {
                        ud = handle.Target as LuaThreadRefMan;
                    }
                    catch { }
                    if (!object.ReferenceEquals(ud, null))
                    {
                        ud.Close();
                    }

                    handle.Free();
                }
            }
            return(0);
        }
        public static LuaThreadRefMan PrepareRefMan(this IntPtr l)
        {
            if (l != IntPtr.Zero)
            {
                using (var lr = new LuaStateRecover(l))
                {
                    l.GetField(lua.LUA_REGISTRYINDEX, "___thdreg");
                    IntPtr   pud = l.touserdata(-1);
                    GCHandle handle;
                    if (pud != IntPtr.Zero)
                    {
                        IntPtr hval = Marshal.ReadIntPtr(pud);
                        handle = (GCHandle)hval;
                        LuaThreadRefMan ud = null;
                        try
                        {
                            ud = handle.Target as LuaThreadRefMan;
                        }
                        catch { }
                        if (ud != null)
                        {
                            return(ud);
                        }
                    }
                    l.pop(1);

                    l.newtable();                  // meta
                    l.pushcfunction(FuncRefManGc); // meta, func
                    l.SetField(-2, "__gc");        // meta

                    LuaThreadRefMan man = new LuaThreadRefMan();
                    pud    = l.newuserdata(new IntPtr(Marshal.SizeOf(typeof(IntPtr)))); // meta, man
                    handle = GCHandle.Alloc(man);
                    Marshal.WriteIntPtr(pud, (IntPtr)handle);

                    l.insert(-2);                                   // man, meta
                    l.setmetatable(-2);                             // man
                    l.SetField(lua.LUA_REGISTRYINDEX, "___thdreg"); // (empty)
                    return(man);
                }
            }
            return(null);
        }
Exemplo n.º 3
0
 public static LuaThreadRefMan GetOrCreateRefMan(this IntPtr l)
 {
     l.checkstack(1);
     l.pushlightuserdata(LuaConst.LRKEY_REF_MAN); // #man
     l.gettable(lua.LUA_REGISTRYINDEX);           // man
     if (l.isuserdata(-1))
     {
         LuaThreadRefMan man = null;
         try
         {
             IntPtr pud = l.touserdata(-1);
             if (pud != IntPtr.Zero)
             {
                 IntPtr   hval   = Marshal.ReadIntPtr(pud);
                 GCHandle handle = (GCHandle)hval;
                 man = handle.Target as LuaThreadRefMan;
             }
         }
         catch { }
         l.pop(1); // X
         return(man);
     }
     else
     {
         l.checkstack(5);
         l.pop(1);                                        // X
         l.pushlightuserdata(LuaConst.LRKEY_REF_MAN);     // #man
         LuaThreadRefMan man = new LuaThreadRefMan();
         var             h   = l.PushLuaRawObject(man);   // #man man
         l.PushCommonMetaTable();                         // #man man meta
         l.setmetatable(-2);                              // #man man
         l.newtable();                                    // #man man env
         l.pushlightuserdata(LuaConst.LRKEY_OBJ_META_EX); // #man man env #meta
         l.pushlightuserdata(h);                          // #man man env #meta meta
         l.settable(-3);                                  // #man man env
         l.setfenv(-2);                                   // #man man
         l.settable(lua.LUA_REGISTRYINDEX);               // X
         return(man);
     }
 }
 public static LuaThreadRefMan GetRefMan(this IntPtr l)
 {
     if (l != IntPtr.Zero)
     {
         using (var lr = new LuaStateRecover(l))
         {
             l.GetField(lua.LUA_REGISTRYINDEX, "___thdreg");
             IntPtr pud = l.touserdata(-1);
             if (pud != IntPtr.Zero)
             {
                 IntPtr          hval   = Marshal.ReadIntPtr(pud);
                 GCHandle        handle = (GCHandle)hval;
                 LuaThreadRefMan ud     = null;
                 try
                 {
                     ud = handle.Target as LuaThreadRefMan;
                 }
                 catch { }
                 return(ud);
             }
         }
     }
     return(null);
 }