diff --git a/libs/lua/LuaBridge/detail/CFunctions.h b/libs/lua/LuaBridge/detail/CFunctions.h index ce376545db..1154edd3c9 100644 --- a/libs/lua/LuaBridge/detail/CFunctions.h +++ b/libs/lua/LuaBridge/detail/CFunctions.h @@ -355,6 +355,28 @@ struct CFunc } }; + template ::ReturnType> + struct CallMemberCPtr + { + typedef typename FuncTraits ::Params Params; + + static int f (lua_State* L) + { + assert (isfulluserdata (L, lua_upvalueindex (1))); + std::shared_ptr* const t = Userdata::get > (L, 1, true); + T* const tt = const_cast (t->get()); + if (!tt) { + return luaL_error (L, "shared_ptr is nil"); + } + MemFnPtr const& fnptr = *static_cast (lua_touserdata (L, lua_upvalueindex (1))); + assert (fnptr != 0); + ArgList args (L); + Stack ::push (L, FuncTraits ::call (tt, fnptr, args)); + return 1; + } + }; + template struct CastMemberPtr { @@ -636,6 +658,31 @@ struct CFunc } }; + template ::ReturnType> + struct CallMemberRefCPtr + { + typedef typename FuncTraits ::Params Params; + + static int f (lua_State* L) + { + assert (isfulluserdata (L, lua_upvalueindex (1))); + std::shared_ptr* const t = Userdata::get > (L, 1, true); + T* const tt = const_cast (t->get()); + if (!tt) { + return luaL_error (L, "shared_ptr is nil"); + } + MemFnPtr const& fnptr = *static_cast (lua_touserdata (L, lua_upvalueindex (1))); + assert (fnptr != 0); + ArgList args (L); + Stack ::push (L, FuncTraits ::call (tt, fnptr, args)); + LuaRef v (newTable (L)); + FuncArgs ::refs (v, args); + v.push(L); + return 2; + } + }; + template ::ReturnType> struct CallMemberRefWPtr @@ -726,6 +773,24 @@ struct CFunc } }; + template + struct CallMemberCPtr + { + typedef typename FuncTraits ::Params Params; + + static int f (lua_State* L) + { + assert (isfulluserdata (L, lua_upvalueindex (1))); + std::shared_ptr* const t = Userdata::get > (L, 1, true); + T* const tt = const_cast (t->get()); + MemFnPtr const& fnptr = *static_cast (lua_touserdata (L, lua_upvalueindex (1))); + assert (fnptr != 0); + ArgList args (L); + FuncTraits ::call (tt, fnptr, args); + return 0; + } + }; + template struct CallMemberWPtr { @@ -817,6 +882,30 @@ struct CFunc } }; + template + struct CallMemberRefCPtr + { + typedef typename FuncTraits ::Params Params; + + static int f (lua_State* L) + { + assert (isfulluserdata (L, lua_upvalueindex (1))); + std::shared_ptr* const t = Userdata::get > (L, 1, true); + T* const tt = const_cast (t->get()); + if (!tt) { + return luaL_error (L, "shared_ptr is nil"); + } + MemFnPtr const& fnptr = *static_cast (lua_touserdata (L, lua_upvalueindex (1))); + assert (fnptr != 0); + ArgList args (L); + FuncTraits ::call (tt, fnptr, args); + LuaRef v (newTable (L)); + FuncArgs ::refs (v, args); + v.push(L); + return 1; + } + }; + template struct CallMemberRefWPtr { @@ -932,6 +1021,30 @@ struct CFunc } }; + template + struct CallMemberCPtrFunctionHelper + { + typedef typename FuncTraits ::ClassType T; + static void add (lua_State* L, char const* name, MemFnPtr mf) + { + new (lua_newuserdata (L, sizeof (MemFnPtr))) MemFnPtr (mf); + lua_pushcclosure (L, &CallMemberCPtr ::f, 1); + rawsetfield (L, -3, name); // class table + } + }; + + template + struct CallMemberRefCPtrFunctionHelper + { + typedef typename FuncTraits ::ClassType T; + static void add (lua_State* L, char const* name, MemFnPtr mf) + { + new (lua_newuserdata (L, sizeof (MemFnPtr))) MemFnPtr (mf); + lua_pushcclosure (L, &CallMemberRefCPtr ::f, 1); + rawsetfield (L, -3, name); // class table + } + }; + template struct CallMemberWPtrFunctionHelper { diff --git a/libs/lua/LuaBridge/detail/Namespace.h b/libs/lua/LuaBridge/detail/Namespace.h index a9092cde1e..24d037ecde 100644 --- a/libs/lua/LuaBridge/detail/Namespace.h +++ b/libs/lua/LuaBridge/detail/Namespace.h @@ -28,13 +28,14 @@ */ //============================================================================== +#include + #ifdef LUABINDINGDOC #include #include #include #include #include -#include #include #include @@ -1275,6 +1276,7 @@ private: WSPtrClass (char const* name, Namespace const* parent) : ClassBase (parent->L) , shared (name, parent) + , shared_const (name, parent) , weak (name, parent) { #ifdef LUABINDINGDOC @@ -1285,13 +1287,14 @@ private: parent->_name + name, std::string(), type_name ()) m_stackSize = shared.m_stackSize; - parent->m_stackSize = weak.m_stackSize = shared.m_stackSize = 0; - lua_pop (L, 3); + parent->m_stackSize = weak.m_stackSize = shared.m_stackSize = shared_const.m_stackSize = 0; + lua_pop (L, 6); } - WSPtrClass (char const* name, Namespace const* parent, void const* const sharedkey, void const* const weakkey) + WSPtrClass (char const* name, Namespace const* parent, void const* const sharedkey, void const* const sharedconstkey, void const* const weakkey) : ClassBase (parent->L) , shared (name, parent, sharedkey) + , shared_const (name, parent, sharedconstkey) , weak (name, parent, weakkey) { #ifdef LUABINDINGDOC @@ -1299,8 +1302,8 @@ private: _name = parent->_name + name + ":"; #endif m_stackSize = shared.m_stackSize; - parent->m_stackSize = weak.m_stackSize = shared.m_stackSize = 0; - lua_pop (L, 3); + parent->m_stackSize = weak.m_stackSize = shared.m_stackSize = shared_const.m_stackSize = 0; + lua_pop (L, 6); } template @@ -1310,6 +1313,9 @@ private: set_shared_class (); CFunc::CallMemberPtrFunctionHelper ::add (L, name, mf); + set_const_shared_class (); + CFunc::CallMemberCPtrFunctionHelper ::add (L, name, mf); + set_weak_class (); CFunc::CallMemberWPtrFunctionHelper ::add (L, name, mf); return *this; @@ -1322,6 +1328,9 @@ private: set_shared_class (); CFunc::CallMemberRefPtrFunctionHelper ::add (L, name, mf); + set_const_shared_class (); + CFunc::CallMemberRefCPtrFunctionHelper ::add (L, name, mf); + set_weak_class (); CFunc::CallMemberRefWPtrFunctionHelper ::add (L, name, mf); return *this; @@ -1336,6 +1345,11 @@ private: &shared. template ctorPtrPlacementProxy ::Params, std::shared_ptr, T >, 0); rawsetfield(L, -2, "__call"); + set_const_shared_class (); + lua_pushcclosure (L, + &shared_const. template ctorPtrPlacementProxy ::Params, std::shared_ptr, T >, 0); + rawsetfield(L, -2, "__call"); + set_weak_class (); // NOTE: this constructs an empty weak-ptr, // ideally we'd construct a weak-ptr from a referenced shared-ptr @@ -1359,6 +1373,11 @@ private: lua_pushcclosure (L, &CFunc::Call ::f, 1); rawsetfield (L, -2, name); + set_const_shared_class (); + new (lua_newuserdata (L, sizeof (fp))) FP (fp); + lua_pushcclosure (L, &CFunc::Call ::f, 1); + rawsetfield (L, -2, name); + set_weak_class (); new (lua_newuserdata (L, sizeof (fp))) FP (fp); lua_pushcclosure (L, &CFunc::Call ::f, 1); @@ -1374,6 +1393,11 @@ private: &shared. template ctorNilPtrPlacementProxy >, 0); rawsetfield(L, -2, "__call"); + set_const_shared_class (); + lua_pushcclosure (L, + &shared_const. template ctorNilPtrPlacementProxy >, 0); + rawsetfield(L, -2, "__call"); + set_weak_class (); // NOTE: this constructs an empty weak-ptr, // ideally we'd construct a weak-ptr from a referenced shared-ptr @@ -1394,6 +1418,13 @@ private: rawsetfield (L, -5, name); // const table rawsetfield (L, -3, name); // class table + set_const_shared_class (); + assert (lua_istable (L, -1)); + lua_pushcclosure (L, fp, 0); + lua_pushvalue (L, -1); + rawsetfield (L, -5, name); // const table + rawsetfield (L, -3, name); // class table + set_weak_class (); assert (lua_istable (L, -1)); lua_pushcclosure (L, fp, 0); @@ -1416,6 +1447,12 @@ private: assert (lua_istable (L, -1)); lua_pushcclosure (L, &CFunc::CastMemberPtr ::f, 0); rawsetfield (L, -3, name); // class table + + set_const_shared_class (); + assert (lua_istable (L, -1)); + lua_pushcclosure (L, &CFunc::CastMemberPtr ::f, 0); + rawsetfield (L, -3, name); // class table + return *this; } @@ -1427,6 +1464,11 @@ private: lua_pushcclosure (L, &CFunc::PtrNullCheck ::f, 0); rawsetfield (L, -3, "isnil"); // class table + set_const_shared_class (); + assert (lua_istable (L, -1)); + lua_pushcclosure (L, &CFunc::PtrNullCheck ::f, 0); + rawsetfield (L, -3, "isnil"); // class table + set_weak_class (); assert (lua_istable (L, -1)); lua_pushcclosure (L, &CFunc::WPtrNullCheck ::f, 0); @@ -1442,6 +1484,11 @@ private: lua_pushcclosure (L, &CFunc::PtrEqualCheck ::f, 0); rawsetfield (L, -3, "sameinstance"); // class table + set_const_shared_class (); + assert (lua_istable (L, -1)); + lua_pushcclosure (L, &CFunc::PtrEqualCheck ::f, 0); + rawsetfield (L, -3, "sameinstance"); // class table + set_weak_class (); assert (lua_istable (L, -1)); lua_pushcclosure (L, &CFunc::WPtrEqualCheck ::f, 0); @@ -1481,6 +1528,20 @@ private: lua_pop (L, 1); } + set_const_shared_class (); + assert (lua_istable (L, -1)); + // Add to __propget in class and const tables. + { + rawgetfield (L, -2, "__propget"); + rawgetfield (L, -4, "__propget"); + new (lua_newuserdata (L, sizeof (mp_t))) mp_t (mp); + lua_pushcclosure (L, &CFunc::getPtrProperty , 1); + lua_pushvalue (L, -1); + rawsetfield (L, -4, name); + rawsetfield (L, -2, name); + lua_pop (L, 2); + } + set_shared_class (); assert (lua_istable (L, -1)); // Add to __propget in class and const tables. @@ -1532,7 +1593,17 @@ private: lua_insert (L, -3); lua_insert (L, -2); } + void set_const_shared_class () { + lua_pop (L, 3); + lua_rawgetp (L, LUA_REGISTRYINDEX, ClassInfo >::getStaticKey ()); + rawgetfield (L, -1, "__class"); + rawgetfield (L, -1, "__const"); + lua_insert (L, -3); + lua_insert (L, -2); + } + Class > shared; + Class > shared_const; Class > weak; }; @@ -2122,6 +2193,7 @@ public: CLASSDOC ("[C] Derived Pointer Class", _name << name, type_name (), type_name ()) return WSPtrClass (name, this, ClassInfo >::getStaticKey (), + ClassInfo >::getStaticKey (), ClassInfo >::getStaticKey ()) .addNullCheck() .addEqualCheck();