mirror of
https://github.com/ThePhD/sol2.git
synced 2024-03-22 13:10:44 +08:00
Preparing for overload support
Preparing to benchmarking of several different lua frameworks
This commit is contained in:
parent
540438baec
commit
9372b54b02
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -43,3 +43,4 @@ main2.cpp
|
|||
lua-5.3.2/
|
||||
lua-5.2.4/
|
||||
bench/
|
||||
*.props
|
||||
|
|
|
@ -50,7 +50,7 @@ args = parser.parse_args()
|
|||
# general variables
|
||||
include = [ '.', os.path.join('Catch', 'include')]
|
||||
depends = []
|
||||
cxxflags = [ '-Wall', '-Wextra', '-pedantic', '-pedantic-errors', '-std=c++11', '-Wno-unused-variable' ]
|
||||
cxxflags = [ '-Wall', '-Wextra', '-pedantic', '-pedantic-errors', '-std=c++14', '-Wno-unused-variable' ]
|
||||
ldflags = []
|
||||
script_dir = os.path.dirname(os.path.realpath(sys.argv[0]))
|
||||
sol_dir = os.path.join(script_dir, 'sol')
|
||||
|
|
|
@ -226,7 +226,7 @@ struct pusher<function_sig<Sigs...>> {
|
|||
|
||||
template<typename R, typename... Args, typename Fx, typename = std::result_of_t<Fx(Args...)>>
|
||||
static void set_memfx(types<R(Args...)> t, lua_State* L, Fx&& fx) {
|
||||
typedef Decay<Unwrap<Unqualified<Fx>>> raw_fx_t;
|
||||
typedef std::decay_t<Unwrapped<Unqualified<Fx>>> raw_fx_t;
|
||||
typedef R(* fx_ptr_t)(Args...);
|
||||
typedef std::is_convertible<raw_fx_t, fx_ptr_t> is_convertible;
|
||||
set_isconvertible_fx(is_convertible(), t, L, std::forward<Fx>(fx));
|
||||
|
@ -234,7 +234,7 @@ struct pusher<function_sig<Sigs...>> {
|
|||
|
||||
template<typename Fx>
|
||||
static void set_memfx(types<>, lua_State* L, Fx&& fx) {
|
||||
typedef Unwrap<Unqualified<Fx>> fx_t;
|
||||
typedef Unwrapped<Unqualified<Fx>> fx_t;
|
||||
typedef decltype(&fx_t::operator()) Sig;
|
||||
set_memfx(types<function_signature_t<Sig>>(), L, std::forward<Fx>(fx));
|
||||
}
|
||||
|
@ -269,13 +269,13 @@ struct pusher<function_sig<Sigs...>> {
|
|||
template<typename Fx, typename R, typename... Args>
|
||||
static void set_isconvertible_fx(std::true_type, types<R(Args...)>, lua_State* L, Fx&& fx) {
|
||||
typedef R(* fx_ptr_t)(Args...);
|
||||
fx_ptr_t fxptr = unwrapper(std::forward<Fx>(fx));
|
||||
fx_ptr_t fxptr = unwrap(std::forward<Fx>(fx));
|
||||
set(L, fxptr);
|
||||
}
|
||||
|
||||
template<typename Fx, typename R, typename... Args>
|
||||
static void set_isconvertible_fx(std::false_type, types<R(Args...)>, lua_State* L, Fx&& fx) {
|
||||
typedef Unwrap<Decay<Fx>> fx_t;
|
||||
typedef Unwrapped<std::decay_t<Fx>> fx_t;
|
||||
std::unique_ptr<base_function> sptr(new functor_function<fx_t>(std::forward<Fx>(fx)));
|
||||
set_fx<Fx>(L, std::move(sptr));
|
||||
}
|
||||
|
@ -287,7 +287,7 @@ struct pusher<function_sig<Sigs...>> {
|
|||
|
||||
template<typename Fx, typename T>
|
||||
static void set_reference_fx(std::false_type, lua_State* L, Fx&& fx, T&& obj) {
|
||||
typedef std::remove_pointer_t<Decay<Fx>> clean_fx;
|
||||
typedef std::remove_pointer_t<std::decay_t<Fx>> clean_fx;
|
||||
std::unique_ptr<base_function> sptr(new member_function<clean_fx, Unqualified<T>>(std::forward<T>(obj), std::forward<Fx>(fx)));
|
||||
return set_fx<Fx>(L, std::move(sptr));
|
||||
}
|
||||
|
@ -299,12 +299,12 @@ struct pusher<function_sig<Sigs...>> {
|
|||
// idx n + 1: is the object's void pointer
|
||||
// We don't need to store the size, because the other side is templated
|
||||
// with the same member function pointer type
|
||||
typedef Decay<Fx> dFx;
|
||||
typedef std::decay_t<Fx> dFx;
|
||||
typedef Unqualified<Fx> uFx;
|
||||
dFx memfxptr(std::forward<Fx>(fx));
|
||||
auto userptr = sol::detail::get_ptr(obj);
|
||||
void* userobjdata = static_cast<void*>(userptr);
|
||||
lua_CFunction freefunc = &static_member_function<Decay<decltype(*userptr)>, uFx>::call;
|
||||
lua_CFunction freefunc = &static_member_function<std::decay_t<decltype(*userptr)>, uFx>::call;
|
||||
|
||||
int upvalues = stack::detail::push_as_upvalues(L, memfxptr);
|
||||
upvalues += stack::push(L, userobjdata);
|
||||
|
@ -314,7 +314,7 @@ struct pusher<function_sig<Sigs...>> {
|
|||
|
||||
template<typename Fx>
|
||||
static void set_fx(std::false_type, lua_State* L, Fx&& fx) {
|
||||
Decay<Fx> target(std::forward<Fx>(fx));
|
||||
std::decay_t<Fx> target(std::forward<Fx>(fx));
|
||||
lua_CFunction freefunc = &static_function<Fx>::call;
|
||||
|
||||
int upvalues = stack::detail::push_as_upvalues(L, target);
|
||||
|
|
|
@ -28,12 +28,19 @@
|
|||
|
||||
namespace sol {
|
||||
namespace detail {
|
||||
struct ref_call_t {
|
||||
ref_call_t() {}
|
||||
struct ref_call_t {} const ref_call = ref_call_t{};
|
||||
template <typename T>
|
||||
struct implicit_wrapper {
|
||||
T& item;
|
||||
implicit_wrapper(T& item) : item(item) {}
|
||||
operator T& () {
|
||||
return item;
|
||||
}
|
||||
operator T* () {
|
||||
return std::addressof(item);
|
||||
}
|
||||
};
|
||||
|
||||
const auto ref_call = ref_call_t{};
|
||||
|
||||
template <typename Sig, typename... Args>
|
||||
struct function_packer : std::tuple<Args...> { using std::tuple<Args...>::tuple; };
|
||||
|
||||
|
@ -51,8 +58,8 @@ struct functor {
|
|||
T* item;
|
||||
Func invocation;
|
||||
|
||||
template<typename... FxArgs>
|
||||
functor(FxArgs&&... fxargs): item(nullptr), invocation(std::forward<FxArgs>(fxargs)...) {}
|
||||
template<typename... Args>
|
||||
functor(Args&&... args): item(nullptr), invocation(std::forward<Args>(args)...) {}
|
||||
|
||||
bool check () const {
|
||||
return invocation != nullptr;
|
||||
|
@ -71,7 +78,7 @@ struct functor {
|
|||
}
|
||||
|
||||
template<typename... Args>
|
||||
auto operator()(Args&&... args) -> decltype(std::declval<functor>().call(types<return_type>{}, std::forward<Args>(args)...)) {
|
||||
decltype(auto) operator()(Args&&... args) {
|
||||
return this->call(types<return_type>{}, std::forward<Args>(args)...);
|
||||
}
|
||||
};
|
||||
|
@ -138,13 +145,13 @@ public:
|
|||
template<typename... Args>
|
||||
void call(types<void>, Args&&... args) {
|
||||
T& member = *item;
|
||||
invocation(member, std::forward<Args>(args)...);
|
||||
invocation(implicit_wrapper<T>(member), std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename Ret, typename... Args>
|
||||
Ret call(types<Ret>, Args&&... args) {
|
||||
T& member = *item;
|
||||
return invocation(member, std::forward<Args>(args)...);
|
||||
return invocation(implicit_wrapper<T>(member), std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
|
@ -154,7 +161,6 @@ public:
|
|||
};
|
||||
} // detail
|
||||
|
||||
|
||||
template<typename Function>
|
||||
struct static_function {
|
||||
typedef std::remove_pointer_t<std::decay_t<Function>> function_type;
|
||||
|
@ -168,16 +174,10 @@ struct static_function {
|
|||
return 0;
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
static int typed_call(types<>, types<Args...> t, function_type* fx, lua_State* L) {
|
||||
return typed_call(types<void>(), t, fx, L);
|
||||
}
|
||||
|
||||
template<typename... Ret, typename... Args>
|
||||
static int typed_call(types<Ret...>, types<Args...> ta, function_type* fx, lua_State* L) {
|
||||
typedef return_type_t<Ret...> return_type;
|
||||
typedef decltype(stack::call(L, 0, types<return_type>(), ta, fx)) ret_t;
|
||||
ret_t r = stack::call(L, 0, types<return_type>(), ta, fx);
|
||||
decltype(auto) r = stack::call(L, 0, types<return_type>(), ta, fx);
|
||||
int nargs = static_cast<int>(sizeof...(Args));
|
||||
lua_pop(L, nargs);
|
||||
return stack::push(L, std::forward<decltype(r)>(r));
|
||||
|
@ -209,19 +209,13 @@ struct static_member_function {
|
|||
return 0;
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
static int typed_call(types<>, types<Args...> t, T& item, function_type& ifx, lua_State* L) {
|
||||
return typed_call(types<void>(), t, item, ifx, L);
|
||||
}
|
||||
|
||||
template<typename... Ret, typename... Args>
|
||||
static int typed_call(types<Ret...> tr, types<Args...> ta, T& item, function_type& ifx, lua_State* L) {
|
||||
typedef return_type_t<Ret...> return_type;
|
||||
auto fx = [&item, &ifx](Args&&... args) -> return_type { return (item.*ifx)(std::forward<Args>(args)...); };
|
||||
return_type r = stack::call(L, 0, tr, ta, fx);
|
||||
decltype(auto) r = stack::call(L, 0, tr, ta, fx);
|
||||
int nargs = static_cast<int>(sizeof...(Args));
|
||||
lua_pop(L, nargs);
|
||||
return stack::push(L, std::forward<return_type>(r));
|
||||
return stack::push(L, std::forward<decltype(r)>(r));
|
||||
}
|
||||
|
||||
static int call(lua_State* L) {
|
||||
|
@ -311,7 +305,7 @@ struct base_function {
|
|||
}
|
||||
|
||||
static int gc(lua_State* L) {
|
||||
func_gc<I>(std::integral_constant<bool, (I < 1)>(), L);
|
||||
func_gc<I>(Bool<(I < 1)>(), L);
|
||||
return 0;
|
||||
}
|
||||
};
|
||||
|
@ -334,8 +328,8 @@ struct functor_function : public base_function {
|
|||
typedef function_args_t<function_type> args_type;
|
||||
Function fx;
|
||||
|
||||
template<typename... FxArgs>
|
||||
functor_function(FxArgs&&... fxargs): fx(std::forward<FxArgs>(fxargs)...) {}
|
||||
template<typename... Args>
|
||||
functor_function(Args&&... args): fx(std::forward<Args>(args)...) {}
|
||||
|
||||
template<typename... Args>
|
||||
int operator()(types<void> r, types<Args...> t, lua_State* L) {
|
||||
|
@ -345,11 +339,6 @@ struct functor_function : public base_function {
|
|||
return 0;
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
int operator()(types<>, types<Args...> t, lua_State* L) {
|
||||
return (*this)(types<void>(), t, L);
|
||||
}
|
||||
|
||||
template<typename... Ret, typename... Args>
|
||||
int operator()(types<Ret...> tr, types<Args...> ta, lua_State* L) {
|
||||
return_type r = stack::call(L, 0, tr, ta, fx);
|
||||
|
@ -376,18 +365,18 @@ struct member_function : public base_function {
|
|||
T member;
|
||||
function_type invocation;
|
||||
|
||||
template<typename Tm, typename... FxArgs>
|
||||
functor(Tm&& m, FxArgs&&... fxargs): member(std::forward<Tm>(m)), invocation(std::forward<FxArgs>(fxargs)...) {}
|
||||
template<typename Tm, typename... Args>
|
||||
functor(Tm&& m, Args&&... args): member(std::forward<Tm>(m)), invocation(std::forward<Args>(args)...) {}
|
||||
|
||||
template<typename... Args>
|
||||
return_type operator()(Args&&... args) {
|
||||
auto& mem = unwrapper(unref(member));
|
||||
auto& mem = unwrap(deref(member));
|
||||
return (mem.*invocation)(std::forward<Args>(args)...);
|
||||
}
|
||||
} fx;
|
||||
|
||||
template<typename Tm, typename... FxArgs>
|
||||
member_function(Tm&& m, FxArgs&&... fxargs): fx(std::forward<Tm>(m), std::forward<FxArgs>(fxargs)...) {}
|
||||
template<typename Tm, typename... Args>
|
||||
member_function(Tm&& m, Args&&... args): fx(std::forward<Tm>(m), std::forward<Args>(args)...) {}
|
||||
|
||||
template<typename... Args>
|
||||
int operator()(types<void> tr, types<Args...> ta, lua_State* L) {
|
||||
|
@ -395,15 +384,9 @@ struct member_function : public base_function {
|
|||
return 0;
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
int operator()(types<>, types<Args...> t, lua_State* L) {
|
||||
return (*this)(types<void>(), t, L);
|
||||
}
|
||||
|
||||
template<typename... Ret, typename... Args>
|
||||
int operator()(types<Ret...> tr, types<Args...> ta, lua_State* L) {
|
||||
typedef decltype(stack::call(L, 0, tr, ta, fx)) ret_t;
|
||||
ret_t r = stack::call(L, 0, tr, ta, fx);
|
||||
decltype(auto) r = stack::call(L, 0, tr, ta, fx);
|
||||
int nargs = static_cast<int>(sizeof...(Args));
|
||||
lua_pop(L, nargs);
|
||||
return stack::push(L, std::forward<decltype(r)>(r));
|
||||
|
@ -429,12 +412,12 @@ struct usertype_function_core : public base_function {
|
|||
|
||||
fx_t fx;
|
||||
|
||||
template<typename... FxArgs>
|
||||
usertype_function_core(FxArgs&&... fxargs): fx(std::forward<FxArgs>(fxargs)...) {}
|
||||
template<typename... Args>
|
||||
usertype_function_core(Args&&... args): fx(std::forward<Args>(args)...) {}
|
||||
|
||||
template<typename Return, typename Raw = Unqualified<Return>>
|
||||
std::enable_if_t<std::is_same<T, Raw>::value, int> push(lua_State* L, Return&& r) {
|
||||
if(detail::get_ptr(r) == fx.item) {
|
||||
if(ptr(unwrap(r)) == fx.item) {
|
||||
// push nothing
|
||||
// note that pushing nothing with the ':'
|
||||
// syntax means we leave the instance of what
|
||||
|
@ -454,33 +437,22 @@ struct usertype_function_core : public base_function {
|
|||
}
|
||||
|
||||
template<typename... Args>
|
||||
int call(types<void> r, types<Args...> t, lua_State* L) {
|
||||
int operator()(types<void> tr, types<Args...> ta, lua_State* L) {
|
||||
//static const std::size_t skew = static_cast<std::size_t>(std::is_member_object_pointer<function_type>::value);
|
||||
stack::call(L, 0, r, t, fx);
|
||||
stack::call(L, 0, tr, ta, fx);
|
||||
int nargs = static_cast<int>(sizeof...(Args));
|
||||
lua_pop(L, nargs);
|
||||
return 0;
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
int call(types<>, types<Args...> t, lua_State* L) {
|
||||
return this->call(types<void>(), t, L);
|
||||
}
|
||||
|
||||
template<typename... Ret, typename... Args>
|
||||
int call(types<Ret...> tr, types<Args...> ta, lua_State* L) {
|
||||
typedef decltype(stack::call(L, 0, tr, ta, fx)) ret_t;
|
||||
ret_t r = stack::call(L, 0, tr, ta, fx);
|
||||
int operator()(types<Ret...> tr, types<Args...> ta, lua_State* L) {
|
||||
decltype(auto) r = stack::call(L, 0, tr, ta, fx);
|
||||
int nargs = static_cast<int>(sizeof...(Args));
|
||||
lua_pop(L, nargs);
|
||||
int pushcount = push(L, std::forward<decltype(r)>(r));
|
||||
return pushcount;
|
||||
}
|
||||
|
||||
template<typename... Ret, typename... Args>
|
||||
int operator()(types<Ret...> r, types<Args...> t, lua_State* L) {
|
||||
return this->call(r, t, L);
|
||||
}
|
||||
};
|
||||
|
||||
template<typename Function, typename Tp>
|
||||
|
@ -494,9 +466,8 @@ struct usertype_function : public usertype_function_core<Function, Tp> {
|
|||
template<typename... FxArgs>
|
||||
usertype_function(FxArgs&&... fxargs): base_t(std::forward<FxArgs>(fxargs)...) {}
|
||||
|
||||
template<typename Tx>
|
||||
int fx_call(lua_State* L) {
|
||||
this->fx.item = detail::get_ptr(stack::get<Tx>(L, 1));
|
||||
int prelude(lua_State* L) {
|
||||
this->fx.item = ptr(stack::get<T>(L, 1));
|
||||
if(this->fx.item == nullptr) {
|
||||
throw error("userdata for function call is null: are you using the wrong syntax? (use item:function/variable(...) syntax)");
|
||||
}
|
||||
|
@ -504,11 +475,11 @@ struct usertype_function : public usertype_function_core<Function, Tp> {
|
|||
}
|
||||
|
||||
virtual int operator()(lua_State* L) override {
|
||||
return fx_call<T>(L);
|
||||
return prelude(L);
|
||||
}
|
||||
|
||||
virtual int operator()(lua_State* L, detail::ref_call_t) override {
|
||||
return fx_call<T*>(L);
|
||||
return prelude(L);
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -523,9 +494,8 @@ struct usertype_variable_function : public usertype_function_core<Function, Tp>
|
|||
template<typename... FxArgs>
|
||||
usertype_variable_function(FxArgs&&... fxargs): base_t(std::forward<FxArgs>(fxargs)...) {}
|
||||
|
||||
template<typename Tx>
|
||||
int fx_call(lua_State* L) {
|
||||
this->fx.item = detail::get_ptr(stack::get<Tx>(L, 1));
|
||||
int prelude(lua_State* L) {
|
||||
this->fx.item = ptr(stack::get<T>(L, 1));
|
||||
if(this->fx.item == nullptr) {
|
||||
throw error("userdata for member variable is null");
|
||||
}
|
||||
|
@ -543,11 +513,11 @@ struct usertype_variable_function : public usertype_function_core<Function, Tp>
|
|||
}
|
||||
|
||||
virtual int operator()(lua_State* L) override {
|
||||
return fx_call<T>(L);
|
||||
return prelude(L);
|
||||
}
|
||||
|
||||
virtual int operator()(lua_State* L, detail::ref_call_t) override {
|
||||
return fx_call<T*>(L);
|
||||
return prelude(L);
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -565,41 +535,30 @@ struct usertype_indexing_function : public usertype_function_core<Function, Tp>
|
|||
template<typename... FxArgs>
|
||||
usertype_indexing_function(std::string name, FxArgs&&... fxargs): base_t(std::forward<FxArgs>(fxargs)...), name(std::move(name)) {}
|
||||
|
||||
template<typename Tx>
|
||||
int fx_call(lua_State* L) {
|
||||
int prelude(lua_State* L) {
|
||||
std::string accessor = stack::get<std::string>(L, 1 - lua_gettop(L));
|
||||
auto function = functions.find(accessor);
|
||||
if(function != functions.end()) {
|
||||
if(function->second.second) {
|
||||
stack::push<upvalue>(L, function->second.first.get());
|
||||
if(std::is_same<T*, Tx>::value) {
|
||||
stack::push(L, &base_function::usertype<0>::ref_call, 1);
|
||||
}
|
||||
else {
|
||||
stack::push(L, &base_function::usertype<0>::call, 1);
|
||||
}
|
||||
stack::push(L, &base_function::usertype<0>::ref_call, 1);
|
||||
return 1;
|
||||
}
|
||||
else if(std::is_same<T*, Tx>::value) {
|
||||
return (*function->second.first)(L, detail::ref_call);
|
||||
}
|
||||
else {
|
||||
return (*function->second.first)(L);
|
||||
}
|
||||
return (*function->second.first)(L, detail::ref_call);
|
||||
}
|
||||
if (!this->fx.check()) {
|
||||
throw error("invalid indexing \"" + accessor + "\" on type: " + name);
|
||||
}
|
||||
this->fx.item = detail::get_ptr(stack::get<Tx>(L, 1));
|
||||
this->fx.item = ptr(stack::get<T>(L, 1));
|
||||
return static_cast<base_t&>(*this)(tuple_types<return_type>(), args_type(), L);
|
||||
}
|
||||
|
||||
virtual int operator()(lua_State* L) override {
|
||||
return fx_call<T>(L);
|
||||
return prelude(L);
|
||||
}
|
||||
|
||||
virtual int operator()(lua_State* L, detail::ref_call_t) override {
|
||||
return fx_call<T*>(L);
|
||||
return prelude(L);
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -86,22 +86,22 @@ public:
|
|||
|
||||
template<typename Table, typename Key, typename T>
|
||||
inline bool operator==(T&& left, const proxy<Table, Key>& right) {
|
||||
return left == right.template get<Decay<T>>();
|
||||
return left == right.template get<std::decay_t<T>>();
|
||||
}
|
||||
|
||||
template<typename Table, typename Key, typename T>
|
||||
inline bool operator==(const proxy<Table, Key>& right, T&& left) {
|
||||
return right.template get<Decay<T>>() == left;
|
||||
return right.template get<std::decay_t<T>>() == left;
|
||||
}
|
||||
|
||||
template<typename Table, typename Key, typename T>
|
||||
inline bool operator!=(T&& left, const proxy<Table, Key>& right) {
|
||||
return right.template get<Decay<T>>() != left;
|
||||
return right.template get<std::decay_t<T>>() != left;
|
||||
}
|
||||
|
||||
template<typename Table, typename Key, typename T>
|
||||
inline bool operator!=(const proxy<Table, Key>& right, T&& left) {
|
||||
return right.template get<Decay<T>>() != left;
|
||||
return right.template get<std::decay_t<T>>() != left;
|
||||
}
|
||||
} // sol
|
||||
|
||||
|
|
|
@ -33,23 +33,6 @@
|
|||
#include <functional>
|
||||
|
||||
namespace sol {
|
||||
namespace detail {
|
||||
template<typename T>
|
||||
inline T* get_ptr(T& val) {
|
||||
return std::addressof(val);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline T* get_ptr(std::reference_wrapper<T> val) {
|
||||
return std::addressof(val.get());
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline T* get_ptr(T* val) {
|
||||
return val;
|
||||
}
|
||||
} // detail
|
||||
|
||||
namespace stack {
|
||||
|
||||
template<typename T, typename = void>
|
||||
|
@ -137,10 +120,10 @@ template <typename T>
|
|||
struct userdata_pusher {
|
||||
template <typename Key, typename... Args>
|
||||
static void push (lua_State* L, Key&& metatablekey, Args&&... args) {
|
||||
// Basically, we store all data like this:
|
||||
// If it's a new value (no std::ref(x)), then we store the pointer to the new
|
||||
// Basically, we store all user0data like this:
|
||||
// If it's a movable/copyable value (no std::ref(x)), then we store the pointer to the new
|
||||
// data in the first sizeof(T*) bytes, and then however many bytes it takes to
|
||||
// do the actual object. Things that are just references/pointers are stored as
|
||||
// do the actual object. Things that are std::ref or plain T* are stored as
|
||||
// just the sizeof(T*), and nothing else.
|
||||
T** pdatum = static_cast<T**>(lua_newuserdata(L, sizeof(T*) + sizeof(T)));
|
||||
T** referencepointer = pdatum;
|
||||
|
@ -624,12 +607,12 @@ inline void remove( lua_State* L, int index, int count ) {
|
|||
}
|
||||
}
|
||||
|
||||
template <bool checkargs = detail::default_check_arguments, typename R, typename... Args, typename Fx, typename... FxArgs, typename = typename std::enable_if<!std::is_void<R>::value>::type>
|
||||
template <bool checkargs = detail::default_check_arguments, typename R, typename... Args, typename Fx, typename... FxArgs, typename = std::enable_if_t<!std::is_void<R>::value>>
|
||||
inline R call(lua_State* L, int start, types<R> tr, types<Args...> ta, Fx&& fx, FxArgs&&... args) {
|
||||
return detail::call<checkargs>(L, start, ta, tr, ta, std::forward<Fx>(fx), std::forward<FxArgs>(args)...);
|
||||
}
|
||||
|
||||
template <bool checkargs = detail::default_check_arguments, typename R, typename... Args, typename Fx, typename... FxArgs, typename = typename std::enable_if<!std::is_void<R>::value>::type>
|
||||
template <bool checkargs = detail::default_check_arguments, typename R, typename... Args, typename Fx, typename... FxArgs, typename = std::enable_if_t<!std::is_void<R>::value>>
|
||||
inline R call(lua_State* L, types<R> tr, types<Args...> ta, Fx&& fx, FxArgs&&... args) {
|
||||
return call<checkargs>(L, 0, ta, tr, ta, std::forward<Fx>(fx), std::forward<FxArgs>(args)...);
|
||||
}
|
||||
|
|
|
@ -150,9 +150,9 @@ public:
|
|||
return globals.get<Args...>(std::forward<Keys>(keys)...);
|
||||
}
|
||||
|
||||
template<typename... Tn>
|
||||
state_view& set(Tn&&... argn) {
|
||||
globals.set(std::forward<Tn>(argn)...);
|
||||
template<typename... Args>
|
||||
state_view& set(Args&&... args) {
|
||||
globals.set(std::forward<Args>(args)...);
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
@ -214,11 +214,11 @@ public:
|
|||
return result;
|
||||
}
|
||||
|
||||
template <typename... Tn>
|
||||
table create_table(int narr = 0, int nrec = sizeof...(Tn), Tn&&... argn) {
|
||||
template <typename... Args>
|
||||
table create_table(int narr = 0, int nrec = sizeof...(Args), Args&&... args) {
|
||||
lua_createtable(L, narr, nrec);
|
||||
table result(L);
|
||||
result.set(std::forward<Tn>(argn)...);
|
||||
result.set(std::forward<Args>(args)...);
|
||||
lua_pop(L, 1);
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -114,9 +114,9 @@ public:
|
|||
return tuple_get( types<Ret...>( ), build_indices<sizeof...( Ret )>( ), std::forward_as_tuple(std::forward<Keys>(keys)...));
|
||||
}
|
||||
|
||||
template<typename... Tn>
|
||||
table_core& set( Tn&&... argn ) {
|
||||
tuple_set(build_indices<sizeof...(Tn) / 2>(), std::forward_as_tuple(std::forward<Tn>(argn)...));
|
||||
template<typename... Args>
|
||||
table_core& set( Args&&... args ) {
|
||||
tuple_set(build_indices<sizeof...(Args) / 2>(), std::forward_as_tuple(std::forward<Args>(args)...));
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
@ -214,7 +214,7 @@ private:
|
|||
|
||||
template<typename Fx, typename Key>
|
||||
void set_fx( types<>, Key&& key, Fx&& fx ) {
|
||||
typedef Unqualified<Unwrap<Fx>> fx_t;
|
||||
typedef Unwrapped<Unqualified<Fx>> fx_t;
|
||||
typedef decltype( &fx_t::operator() ) Sig;
|
||||
set_fx( types<function_signature_t<Sig>>( ), std::forward<Key>( key ), std::forward<Fx>( fx ) );
|
||||
}
|
||||
|
|
|
@ -31,6 +31,9 @@ namespace sol {
|
|||
template<typename T>
|
||||
struct identity { typedef T type; };
|
||||
|
||||
template<typename T>
|
||||
using identity_t = typename identity<T>::type;
|
||||
|
||||
template<typename... Args>
|
||||
struct is_tuple : std::false_type{ };
|
||||
|
||||
|
@ -38,12 +41,12 @@ template<typename... Args>
|
|||
struct is_tuple<std::tuple<Args...>> : std::true_type{ };
|
||||
|
||||
template<typename T>
|
||||
struct unwrap {
|
||||
struct unwrapped {
|
||||
typedef T type;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
struct unwrap<std::reference_wrapper<T>> {
|
||||
struct unwrapped<std::reference_wrapper<T>> {
|
||||
typedef T type;
|
||||
};
|
||||
|
||||
|
@ -55,6 +58,14 @@ struct remove_member_pointer<R T::*> {
|
|||
typedef R type;
|
||||
};
|
||||
|
||||
template<typename R, typename T>
|
||||
struct remove_member_pointer<R T::* const> {
|
||||
typedef R type;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
using remove_member_pointer_t = remove_member_pointer<T>;
|
||||
|
||||
template<typename T, template<typename...> class Templ>
|
||||
struct is_specialization_of : std::false_type { };
|
||||
template<typename... T, template<typename...> class Templ>
|
||||
|
@ -100,13 +111,10 @@ template<typename... Args>
|
|||
using DisableIf = typename std::enable_if<Not<And<Args...>>::value, int>::type;
|
||||
|
||||
template<typename T>
|
||||
using Unqualified = typename std::remove_cv<typename std::remove_reference<T>::type>::type;
|
||||
using Unqualified = std::remove_cv_t<std::remove_reference_t<T>>;
|
||||
|
||||
template<typename T>
|
||||
using Decay = typename std::decay<T>::type;
|
||||
|
||||
template<typename T>
|
||||
using Unwrap = typename unwrap<T>::type;
|
||||
using Unwrapped = typename unwrapped<T>::type;
|
||||
|
||||
template<typename... Args>
|
||||
struct return_type {
|
||||
|
@ -126,16 +134,16 @@ struct return_type<> {
|
|||
template <typename... Args>
|
||||
using return_type_t = typename return_type<Args...>::type;
|
||||
|
||||
template <typename Empty, typename... Tn>
|
||||
using ReturnTypeOr = typename std::conditional<(sizeof...(Tn) < 1), Empty, typename return_type<Tn...>::type>::type;
|
||||
template <typename Empty, typename... Args>
|
||||
using ReturnTypeOr = typename std::conditional<(sizeof...(Args) < 1), Empty, typename return_type<Args...>::type>::type;
|
||||
|
||||
template <typename... Tn>
|
||||
using ReturnType = ReturnTypeOr<void, Tn...>;
|
||||
template <typename... Args>
|
||||
using ReturnType = ReturnTypeOr<void, Args...>;
|
||||
|
||||
namespace detail {
|
||||
|
||||
template<typename T, bool isclass = std::is_class<Unqualified<T>>::value>
|
||||
struct is_function_impl : std::is_function<typename std::remove_pointer<T>::type> {};
|
||||
struct is_function_impl : std::is_function<std::remove_pointer_t<T>> {};
|
||||
|
||||
template<typename T>
|
||||
struct is_function_impl<T, true> {
|
||||
|
@ -192,12 +200,12 @@ struct fx_traits<R(T::*)(Args...), false> {
|
|||
typedef std::tuple<Args...> arg_tuple_type;
|
||||
typedef types<Args...> args_type;
|
||||
typedef R(T::* function_pointer_type)(Args...);
|
||||
typedef typename std::remove_pointer<function_pointer_type>::type function_type;
|
||||
typedef std::remove_pointer_t<function_pointer_type> function_type;
|
||||
typedef R(*free_function_pointer_type)(Args...);
|
||||
typedef R return_type;
|
||||
typedef typename std::remove_pointer<free_function_pointer_type>::type signature_type;
|
||||
typedef std::remove_pointer_t<free_function_pointer_type> signature_type;
|
||||
template<std::size_t i>
|
||||
using arg = typename std::tuple_element<i, arg_tuple_type>::type;
|
||||
using arg = std::tuple_element_t<i, arg_tuple_type>;
|
||||
};
|
||||
|
||||
template<typename T, typename R, typename... Args>
|
||||
|
@ -207,12 +215,12 @@ struct fx_traits<R(T::*)(Args...) const, false> {
|
|||
typedef std::tuple<Args...> arg_tuple_type;
|
||||
typedef types<Args...> args_type;
|
||||
typedef R(T::* function_pointer_type)(Args...);
|
||||
typedef typename std::remove_pointer<function_pointer_type>::type function_type;
|
||||
typedef std::remove_pointer_t<function_pointer_type> function_type;
|
||||
typedef R(*free_function_pointer_type)(Args...);
|
||||
typedef R return_type;
|
||||
typedef typename std::remove_pointer<free_function_pointer_type>::type signature_type;
|
||||
typedef std::remove_pointer_t<free_function_pointer_type> signature_type;
|
||||
template<std::size_t i>
|
||||
using arg = typename std::tuple_element<i, arg_tuple_type>::type;
|
||||
using arg = std::tuple_element_t<i, arg_tuple_type>;
|
||||
};
|
||||
|
||||
template<typename R, typename... Args>
|
||||
|
@ -225,9 +233,9 @@ struct fx_traits<R(Args...), false> {
|
|||
typedef R(*function_pointer_type)(Args...);
|
||||
typedef R(*free_function_pointer_type)(Args...);
|
||||
typedef R return_type;
|
||||
typedef typename std::remove_pointer<free_function_pointer_type>::type signature_type;
|
||||
typedef std::remove_pointer_t<free_function_pointer_type> signature_type;
|
||||
template<std::size_t i>
|
||||
using arg = typename std::tuple_element<i, arg_tuple_type>::type;
|
||||
using arg = std::tuple_element_t<i, arg_tuple_type>;
|
||||
};
|
||||
|
||||
template<typename R, typename... Args>
|
||||
|
@ -240,9 +248,9 @@ struct fx_traits<R(*)(Args...), false> {
|
|||
typedef R(*function_pointer_type)(Args...);
|
||||
typedef R(*free_function_pointer_type)(Args...);
|
||||
typedef R return_type;
|
||||
typedef typename std::remove_pointer<free_function_pointer_type>::type signature_type;
|
||||
typedef std::remove_pointer_t<free_function_pointer_type> signature_type;
|
||||
template<std::size_t i>
|
||||
using arg = typename std::tuple_element<i, arg_tuple_type>::type;
|
||||
using arg = std::tuple_element_t<i, arg_tuple_type>;
|
||||
};
|
||||
|
||||
} // detail
|
||||
|
@ -279,7 +287,7 @@ struct member_traits<Signature, true> {
|
|||
typedef R(*function_pointer_type)(Arg);
|
||||
typedef R(*free_function_pointer_type)(Arg);
|
||||
template<std::size_t i>
|
||||
using arg = typename std::tuple_element<i, arg_tuple_type>::type;
|
||||
using arg = std::tuple_element_t<i, arg_tuple_type>;
|
||||
};
|
||||
} // detail
|
||||
|
||||
|
@ -322,43 +330,58 @@ template <typename T>
|
|||
using is_c_str = Or<std::is_same<std::decay_t<Unqualified<T>>, char*>, std::is_same<Unqualified<T>, std::string>>;
|
||||
|
||||
template<typename T>
|
||||
auto unwrapper(T&& item) -> decltype(std::forward<T>(item)) {
|
||||
auto unwrap(T&& item) -> decltype(std::forward<T>(item)) {
|
||||
return std::forward<T>(item);
|
||||
}
|
||||
|
||||
template<typename Arg>
|
||||
Arg& unwrapper(std::reference_wrapper<Arg> arg) {
|
||||
template<typename T>
|
||||
T& unwrap(std::reference_wrapper<T> arg) {
|
||||
return arg.get();
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T& unref(T& item) {
|
||||
T& deref(T& item) {
|
||||
return item;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T& unref(T* item) {
|
||||
T& deref(T* item) {
|
||||
return *item;
|
||||
}
|
||||
|
||||
template<typename T, typename Dx>
|
||||
decltype(auto) deref(std::unique_ptr<T, Dx>& item) {
|
||||
return *item;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T& unref(std::unique_ptr<T>& item) {
|
||||
T& deref(std::shared_ptr<T>& item) {
|
||||
return *item;
|
||||
}
|
||||
|
||||
template<typename T, typename Dx>
|
||||
decltype(auto) deref(const std::unique_ptr<T, Dx>& item) {
|
||||
return *item;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T& unref(std::shared_ptr<T>& item) {
|
||||
T& deref(const std::shared_ptr<T>& item) {
|
||||
return *item;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T& unref(const std::unique_ptr<T>& item) {
|
||||
return *item;
|
||||
inline T* ptr(T& val) {
|
||||
return std::addressof(val);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T& unref(const std::shared_ptr<T>& item) {
|
||||
return *item;
|
||||
inline T* ptr(std::reference_wrapper<T> val) {
|
||||
return std::addressof(val.get());
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline T* ptr(T* val) {
|
||||
return val;
|
||||
}
|
||||
} // sol
|
||||
|
||||
|
|
|
@ -29,6 +29,9 @@ namespace sol {
|
|||
template<typename... Ts>
|
||||
struct reverse_tuple;
|
||||
|
||||
template<typename... Ts>
|
||||
using reverse_tuple_t = typename reverse_tuple<Ts...>::type;
|
||||
|
||||
template<>
|
||||
struct reverse_tuple<std::tuple<>> {
|
||||
using type = std::tuple<>;
|
||||
|
@ -57,7 +60,7 @@ template<size_t... Ns>
|
|||
struct build_reverse_indices<0, Ns...> : indices<Ns...> {};
|
||||
|
||||
template<typename... Args>
|
||||
struct types : build_indices<sizeof...(Args)> { typedef types type; };
|
||||
struct types : build_indices<sizeof...(Args)> { typedef types type; static constexpr std::size_t size() { return sizeof...(Args); } };
|
||||
|
||||
namespace detail {
|
||||
template<class Acc, class... Args>
|
||||
|
@ -91,8 +94,8 @@ using tuple_types_t = typename tuple_types<Args...>::type;
|
|||
template<typename Arg>
|
||||
struct remove_one_type : detail::chop_one<Arg> {};
|
||||
|
||||
template<typename... Tn>
|
||||
struct constructors {};
|
||||
template<typename... Args>
|
||||
using constructors = sol::types<Args...>;
|
||||
|
||||
const auto default_constructor = constructors<types<>>{};
|
||||
|
||||
|
|
|
@ -25,7 +25,6 @@
|
|||
#include "compatibility.hpp"
|
||||
#include "traits.hpp"
|
||||
#include <string>
|
||||
#include "traits.hpp"
|
||||
|
||||
namespace sol {
|
||||
struct nil_t {};
|
||||
|
@ -172,7 +171,7 @@ template <typename T>
|
|||
struct lua_type_of<T*> : std::integral_constant<type, type::userdata> {};
|
||||
|
||||
template <typename T>
|
||||
struct lua_type_of<T, typename std::enable_if<std::is_arithmetic<T>::value>::type> : std::integral_constant<type, type::number> {};
|
||||
struct lua_type_of<T, std::enable_if_t<std::is_arithmetic<T>::value>> : std::integral_constant<type, type::number> {};
|
||||
|
||||
template<typename T>
|
||||
inline type type_of() {
|
||||
|
@ -186,7 +185,7 @@ inline type type_of(lua_State* L, int index) {
|
|||
// All enumerations are given and taken from lua
|
||||
// as numbers as well
|
||||
template <typename T>
|
||||
struct lua_type_of<T, typename std::enable_if<std::is_enum<T>::value>::type> : std::integral_constant<type, type::number> {
|
||||
struct lua_type_of<T, std::enable_if_t<std::is_enum<T>::value>> : std::integral_constant<type, type::number> {
|
||||
|
||||
};
|
||||
|
||||
|
@ -199,8 +198,8 @@ struct is_proxy_primitive : is_lua_primitive<T> { };
|
|||
template <typename T>
|
||||
struct is_proxy_primitive<std::reference_wrapper<T>> : std::true_type { };
|
||||
|
||||
template <typename... Tn>
|
||||
struct is_proxy_primitive<std::tuple<Tn...>> : std::true_type { };
|
||||
template <typename... Args>
|
||||
struct is_proxy_primitive<std::tuple<Args...>> : std::true_type { };
|
||||
} // sol
|
||||
|
||||
#endif // SOL_TYPES_HPP
|
||||
|
|
|
@ -129,7 +129,7 @@ private:
|
|||
T*& referencereference = *referencepointer;
|
||||
T* obj = reinterpret_cast<T*>(referencepointer + 1);
|
||||
referencereference = obj;
|
||||
match_constructor(L, obj, syntax, argcount - static_cast<int>(syntax), typename identity<TTypes>::type()...);
|
||||
match_constructor(L, obj, syntax, argcount - static_cast<int>(syntax), identity_t<TTypes>()...);
|
||||
|
||||
if(luaL_newmetatable(L, std::addressof(meta[0])) == 1) {
|
||||
lua_pop(L, 1);
|
||||
|
@ -143,17 +143,16 @@ private:
|
|||
}
|
||||
};
|
||||
|
||||
struct destructor {
|
||||
static int destruct(lua_State* L) {
|
||||
userdata udata = stack::get<userdata>(L, 1);
|
||||
// The first sizeof(T*) bytes are the reference: the rest is
|
||||
// the actual data itself
|
||||
T* obj = static_cast<T*>(static_cast<void*>(reinterpret_cast<char*>(udata.value) + sizeof(T*)));
|
||||
std::allocator<T> alloc{};
|
||||
alloc.destroy(obj);
|
||||
return 0;
|
||||
}
|
||||
};
|
||||
static int destruct(lua_State* L) {
|
||||
userdata udata = stack::get<userdata>(L, 1);
|
||||
// The first sizeof(T*) bytes are the reference: the rest is
|
||||
// the actual data itself (if there is a reference at all)
|
||||
T** pobj = reinterpret_cast<T**>(udata.value);
|
||||
T*& obj = *pobj;
|
||||
std::allocator<T> alloc{};
|
||||
alloc.destroy(obj);
|
||||
return 0;
|
||||
}
|
||||
|
||||
template<std::size_t N>
|
||||
void build_cleanup() {
|
||||
|
@ -218,7 +217,7 @@ private:
|
|||
template<std::size_t N, typename Base, typename Ret>
|
||||
bool build_function(std::true_type, function_map_t*&, function_map_t*&, std::string funcname, Ret Base::* func) {
|
||||
static_assert(std::is_base_of<Base, T>::value, "Any registered function must be part of the class");
|
||||
typedef typename std::decay<decltype(func)>::type function_type;
|
||||
typedef std::decay_t<decltype(func)> function_type;
|
||||
indexmetafunctions.emplace(funcname, std::make_pair(detail::make_unique<usertype_variable_function<function_type, T>>(func), false));
|
||||
newindexmetafunctions.emplace(funcname, std::make_pair(detail::make_unique<usertype_variable_function<function_type, T>>(func), false));
|
||||
return false;
|
||||
|
@ -228,43 +227,43 @@ private:
|
|||
std::unique_ptr<base_function> make_function(const std::string&, Ret(*func)(Arg, Args...)) {
|
||||
typedef Unqualified<Arg> Argu;
|
||||
static_assert(std::is_base_of<Argu, T>::value, "Any non-member-function must have a first argument which is covariant with the desired userdata type.");
|
||||
typedef typename std::decay<decltype(func)>::type function_type;
|
||||
return detail::make_unique<usertype_function<function_type, T>>(func);
|
||||
typedef std::decay_t<decltype(func)> function_type;
|
||||
return std::make_unique<usertype_function<function_type, T>>(func);
|
||||
}
|
||||
|
||||
template<typename Base, typename Ret>
|
||||
std::unique_ptr<base_function> make_variable_function(std::true_type, const std::string&, Ret Base::* func) {
|
||||
static_assert(std::is_base_of<Base, T>::value, "Any registered function must be part of the class");
|
||||
typedef typename std::decay<decltype(func)>::type function_type;
|
||||
return detail::make_unique<usertype_variable_function<function_type, T>>(func);
|
||||
typedef std::decay_t<decltype(func)> function_type;
|
||||
return std::make_unique<usertype_variable_function<function_type, T>>(func);
|
||||
}
|
||||
|
||||
template<typename Base, typename Ret>
|
||||
std::unique_ptr<base_function> make_variable_function(std::false_type, const std::string&, Ret Base::* func) {
|
||||
static_assert(std::is_base_of<Base, T>::value, "Any registered function must be part of the class");
|
||||
typedef typename std::decay<decltype(func)>::type function_type;
|
||||
return detail::make_unique<usertype_function<function_type, T>>(func);
|
||||
typedef std::decay_t<decltype(func)> function_type;
|
||||
return std::make_unique<usertype_function<function_type, T>>(func);
|
||||
}
|
||||
|
||||
template<typename Base, typename Ret>
|
||||
std::unique_ptr<base_function> make_function(const std::string& name, Ret Base::* func) {
|
||||
typedef typename std::decay<decltype(func)>::type function_type;
|
||||
typedef std::decay_t<decltype(func)> function_type;
|
||||
return make_variable_function(std::is_member_object_pointer<function_type>(), name, func);
|
||||
}
|
||||
|
||||
template<typename Fx>
|
||||
std::unique_ptr<base_function> make_function(const std::string&, Fx&& func) {
|
||||
typedef Unqualified<Fx> Fxu;
|
||||
typedef typename std::tuple_element<0, typename function_traits<Fxu>::arg_tuple_type>::type TArg;
|
||||
typedef Unqualified<TArg> TArgu;
|
||||
static_assert(std::is_base_of<TArgu, T>::value, "Any non-member-function must have a first argument which is covariant with the desired userdata type.");
|
||||
typedef typename std::decay<decltype(func)>::type function_type;
|
||||
return detail::make_unique<usertype_function<function_type, T>>(func);
|
||||
typedef std::tuple_element_t<0, typename function_traits<Fxu>::arg_tuple_type> Arg;
|
||||
typedef Unqualified<Arg> Argu;
|
||||
static_assert(std::is_base_of<Argu, T>::value, "Any non-member-function must have a first argument which is covariant with the desired usertype.");
|
||||
typedef std::decay_t<Fxu> function_type;
|
||||
return std::make_unique<usertype_function<function_type, T>>(func);
|
||||
}
|
||||
|
||||
template<std::size_t N, typename Fx>
|
||||
bool build_function(std::false_type, function_map_t*& index, function_map_t*& newindex, std::string funcname, Fx&& func) {
|
||||
typedef typename std::decay<Fx>::type function_type;
|
||||
typedef std::decay_t<Fx> function_type;
|
||||
auto metamethod = std::find(meta_function_names.begin(), meta_function_names.end(), funcname);
|
||||
if(metamethod != meta_function_names.end()) {
|
||||
functionnames.push_back(std::move(funcname));
|
||||
|
@ -300,7 +299,7 @@ private:
|
|||
|
||||
template<std::size_t N, typename Fx, typename... Args>
|
||||
void build_function_tables(function_map_t*& index, function_map_t*& newindex, std::string funcname, Fx&& func, Args&&... args) {
|
||||
typedef typename std::is_member_object_pointer<Unqualified<Fx>>::type is_variable;
|
||||
typedef std::is_member_object_pointer<Unqualified<Fx>> is_variable;
|
||||
static const std::size_t V = static_cast<std::size_t>(!is_variable::value);
|
||||
if(build_function<N>(is_variable(), index, newindex, std::move(funcname), std::forward<Fx>(func))) {
|
||||
build_function_tables<N + V>(index, newindex, std::forward<Args>(args)...);
|
||||
|
@ -347,7 +346,7 @@ public:
|
|||
functionnames.push_back("new");
|
||||
metafunctiontable.push_back({ functionnames.back().c_str(), &constructor<CArgs...>::construct });
|
||||
functionnames.push_back("__gc");
|
||||
metafunctiontable.push_back({ functionnames.back().c_str(), &destructor::destruct });
|
||||
metafunctiontable.push_back({ functionnames.back().c_str(), destruct });
|
||||
// ptr_functions does not participate in garbage collection/new,
|
||||
// as all pointered types are considered
|
||||
// to be references. This makes returns of
|
||||
|
@ -384,7 +383,7 @@ private:
|
|||
|
||||
void set_global_deleter(lua_State* L) {
|
||||
// Automatic deleter table -- stays alive until lua VM dies
|
||||
// even if the user calls collectgarbage()
|
||||
// even if the user calls collectgarbage(), weirdly enough
|
||||
lua_createtable(L, 0, 0);
|
||||
lua_createtable(L, 0, 1);
|
||||
int up = push_upvalues<true>(L, metafunctions);
|
||||
|
|
Loading…
Reference in New Issue
Block a user