大改
This commit is contained in:
62
csgo2/LuaBridge/luaBridge/Array.h
Normal file
62
csgo2/LuaBridge/luaBridge/Array.h
Normal file
@@ -0,0 +1,62 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
//
|
||||
// Copyright 2020, Dmitry Tarakanov
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
|
||||
#include <array>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
template<class T, std::size_t s>
|
||||
struct Stack<std::array<T, s>>
|
||||
{
|
||||
static void push(lua_State* L, std::array<T, s> const& array)
|
||||
{
|
||||
lua_createtable(L, static_cast<int>(s), 0);
|
||||
for (std::size_t i = 0; i < s; ++i)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(i + 1));
|
||||
Stack<T>::push(L, array[i]);
|
||||
lua_settable(L, -3);
|
||||
}
|
||||
}
|
||||
|
||||
static std::array<T, s> get(lua_State* L, int index)
|
||||
{
|
||||
if (!lua_istable(L, index))
|
||||
{
|
||||
luaL_error(L, "#%d argument must be table", index);
|
||||
}
|
||||
|
||||
std::size_t const tableSize = static_cast<std::size_t>(get_length(L, index));
|
||||
|
||||
if (tableSize != s)
|
||||
{
|
||||
luaL_error(L, "array size must be %d ", s);
|
||||
}
|
||||
|
||||
std::array<T, s> array;
|
||||
|
||||
int const absindex = lua_absindex(L, index);
|
||||
lua_pushnil(L);
|
||||
int arrayIndex = 0;
|
||||
while (lua_next(L, absindex) != 0)
|
||||
{
|
||||
array[arrayIndex] = Stack<T>::get(L, -1);
|
||||
lua_pop(L, 1);
|
||||
++arrayIndex;
|
||||
}
|
||||
return array;
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index)
|
||||
{
|
||||
return lua_istable(L, index) && get_length(L, index) == s;
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace luabridge
|
||||
51
csgo2/LuaBridge/luaBridge/List.h
Normal file
51
csgo2/LuaBridge/luaBridge/List.h
Normal file
@@ -0,0 +1,51 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2020, Dmitry Tarakanov
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
|
||||
#include <list>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
template<class T>
|
||||
struct Stack<std::list<T>>
|
||||
{
|
||||
static void push(lua_State* L, std::list<T> const& list)
|
||||
{
|
||||
lua_createtable(L, static_cast<int>(list.size()), 0);
|
||||
typename std::list<T>::const_iterator item = list.begin();
|
||||
for (std::size_t i = 1; i <= list.size(); ++i)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(i));
|
||||
Stack<T>::push(L, *item);
|
||||
lua_settable(L, -3);
|
||||
++item;
|
||||
}
|
||||
}
|
||||
|
||||
static std::list<T> get(lua_State* L, int index)
|
||||
{
|
||||
if (!lua_istable(L, index))
|
||||
{
|
||||
luaL_error(L, "#%d argument must be a table", index);
|
||||
}
|
||||
|
||||
std::list<T> list;
|
||||
|
||||
int const absindex = lua_absindex(L, index);
|
||||
lua_pushnil(L);
|
||||
while (lua_next(L, absindex) != 0)
|
||||
{
|
||||
list.push_back(Stack<T>::get(L, -1));
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
return list;
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_istable(L, index); }
|
||||
};
|
||||
|
||||
} // namespace luabridge
|
||||
34
csgo2/LuaBridge/luaBridge/LuaBridge.h
Normal file
34
csgo2/LuaBridge/luaBridge/LuaBridge.h
Normal file
@@ -0,0 +1,34 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2020, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2007, Nathan Reed
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
// All #include dependencies are listed here
|
||||
// instead of in the individual header files.
|
||||
//
|
||||
|
||||
#define LUABRIDGE_MAJOR_VERSION 2
|
||||
#define LUABRIDGE_MINOR_VERSION 7
|
||||
#define LUABRIDGE_VERSION 207
|
||||
|
||||
#ifndef LUA_VERSION_NUM
|
||||
#error "Lua headers must be included prior to LuaBridge ones"
|
||||
#endif
|
||||
|
||||
#include <LuaBridge/detail/CFunctions.h>
|
||||
#include <LuaBridge/detail/ClassInfo.h>
|
||||
#include <LuaBridge/detail/Constructor.h>
|
||||
#include <LuaBridge/detail/FuncTraits.h>
|
||||
#include <LuaBridge/detail/Iterator.h>
|
||||
#include <LuaBridge/detail/LuaException.h>
|
||||
#include <LuaBridge/detail/LuaHelpers.h>
|
||||
#include <LuaBridge/detail/LuaRef.h>
|
||||
#include <LuaBridge/detail/Namespace.h>
|
||||
#include <LuaBridge/detail/Security.h>
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
#include <LuaBridge/detail/TypeList.h>
|
||||
#include <LuaBridge/detail/TypeTraits.h>
|
||||
#include <LuaBridge/detail/Userdata.h>
|
||||
52
csgo2/LuaBridge/luaBridge/Map.h
Normal file
52
csgo2/LuaBridge/luaBridge/Map.h
Normal file
@@ -0,0 +1,52 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2018, Dmitry Tarakanov
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
#include <LuaBridge/detail/dump.h>
|
||||
|
||||
#include <map>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
template<class K, class V>
|
||||
struct Stack<std::map<K, V>>
|
||||
{
|
||||
typedef std::map<K, V> Map;
|
||||
|
||||
static void push(lua_State* L, const Map& map)
|
||||
{
|
||||
lua_createtable(L, 0, static_cast<int>(map.size()));
|
||||
typedef typename Map::const_iterator ConstIter;
|
||||
for (ConstIter i = map.begin(); i != map.end(); ++i)
|
||||
{
|
||||
Stack<K>::push(L, i->first);
|
||||
Stack<V>::push(L, i->second);
|
||||
lua_settable(L, -3);
|
||||
}
|
||||
}
|
||||
|
||||
static Map get(lua_State* L, int index)
|
||||
{
|
||||
if (!lua_istable(L, index))
|
||||
{
|
||||
luaL_error(L, "#%d argument must be a table", index);
|
||||
}
|
||||
|
||||
Map map;
|
||||
int const absindex = lua_absindex(L, index);
|
||||
lua_pushnil(L);
|
||||
while (lua_next(L, absindex) != 0)
|
||||
{
|
||||
map.emplace(Stack<K>::get(L, -2), Stack<V>::get(L, -1));
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
return map;
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_istable(L, index); }
|
||||
};
|
||||
|
||||
} // namespace luabridge
|
||||
46
csgo2/LuaBridge/luaBridge/Optional.h
Normal file
46
csgo2/LuaBridge/luaBridge/Optional.h
Normal file
@@ -0,0 +1,46 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2021, Stefan Frings
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
|
||||
#include <optional>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
template<class T>
|
||||
struct Stack<std::optional<T>>
|
||||
{
|
||||
static void push(lua_State* L, std::optional<T> const& optional)
|
||||
{
|
||||
if (optional)
|
||||
{
|
||||
Stack<T>::push(L, *optional);
|
||||
}
|
||||
else
|
||||
{
|
||||
lua_pushnil(L);
|
||||
}
|
||||
}
|
||||
|
||||
static std::optional<T> get(lua_State* L, int index)
|
||||
{
|
||||
if (lua_isnil(L, index))
|
||||
{
|
||||
lua_pop(L, 1);
|
||||
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
return Stack<T>::get(L, index);
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index)
|
||||
{
|
||||
return lua_isnil(L, index) || Stack<T>::isInstance(L, index);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace luabridge
|
||||
77
csgo2/LuaBridge/luaBridge/Pair.h
Normal file
77
csgo2/LuaBridge/luaBridge/Pair.h
Normal file
@@ -0,0 +1,77 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2022, Stefan Frings
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
|
||||
#include <cassert>
|
||||
#include <utility>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
template<class T1, class T2>
|
||||
struct Stack<std::pair<T1, T2>>
|
||||
{
|
||||
static void push(lua_State* L, std::pair<T1, T2> const& pair)
|
||||
{
|
||||
lua_createtable(L, 2, 0);
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(1));
|
||||
Stack<T1>::push(L, pair.first);
|
||||
lua_settable(L, -3);
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(2));
|
||||
Stack<T2>::push(L, pair.second);
|
||||
lua_settable(L, -3);
|
||||
}
|
||||
|
||||
static std::pair<T1, T2> get(lua_State* L, int index)
|
||||
{
|
||||
if (!lua_istable(L, index))
|
||||
{
|
||||
luaL_error(L, "#%d argument must be a table", index);
|
||||
}
|
||||
|
||||
std::size_t const tableSize = static_cast<std::size_t>(get_length(L, index));
|
||||
|
||||
if (tableSize != 2)
|
||||
{
|
||||
luaL_error(L, "pair size must be 2");
|
||||
}
|
||||
|
||||
std::pair<T1, T2> pair;
|
||||
|
||||
int const absindex = lua_absindex(L, index);
|
||||
lua_pushnil(L);
|
||||
|
||||
{
|
||||
int const next = lua_next(L, absindex);
|
||||
assert(next != 0);
|
||||
|
||||
pair.first = Stack<T1>::get(L, -1);
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
|
||||
{
|
||||
int const next = lua_next(L, absindex);
|
||||
assert(next != 0);
|
||||
|
||||
pair.second = Stack<T2>::get(L, -1);
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
|
||||
{
|
||||
int const next = lua_next(L, absindex);
|
||||
assert(next == 0);
|
||||
}
|
||||
|
||||
return pair;
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index)
|
||||
{
|
||||
return lua_istable(L, index) && get_length(L, index) == 2;
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace luabridge
|
||||
317
csgo2/LuaBridge/luaBridge/RefCountedObject.h
Normal file
317
csgo2/LuaBridge/luaBridge/RefCountedObject.h
Normal file
@@ -0,0 +1,317 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2004-11 by Raw Material Software Ltd.
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
//==============================================================================
|
||||
/*
|
||||
This is a derivative work used by permission from part of
|
||||
JUCE, available at http://www.rawaterialsoftware.com
|
||||
|
||||
License: The MIT License (http://www.opensource.org/licenses/mit-license.php)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
|
||||
This file incorporates work covered by the following copyright and
|
||||
permission notice:
|
||||
|
||||
This file is part of the JUCE library - "Jules' Utility Class Extensions"
|
||||
Copyright 2004-11 by Raw Material Software Ltd.
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <cassert>
|
||||
#include <utility>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
Adds reference-counting to an object.
|
||||
|
||||
To add reference-counting to a class, derive it from this class, and
|
||||
use the RefCountedObjectPtr class to point to it.
|
||||
|
||||
e.g. @code
|
||||
class MyClass : public RefCountedObjectType
|
||||
{
|
||||
void foo();
|
||||
|
||||
// This is a neat way of declaring a typedef for a pointer class,
|
||||
// rather than typing out the full templated name each time..
|
||||
typedef RefCountedObjectPtr<MyClass> Ptr;
|
||||
};
|
||||
|
||||
MyClass::Ptr p = new MyClass();
|
||||
MyClass::Ptr p2 = p;
|
||||
p = 0;
|
||||
p2->foo();
|
||||
@endcode
|
||||
|
||||
Once a new RefCountedObjectType has been assigned to a pointer, be
|
||||
careful not to delete the object manually.
|
||||
*/
|
||||
template<class CounterType>
|
||||
class RefCountedObjectType
|
||||
{
|
||||
public:
|
||||
//==============================================================================
|
||||
/** Increments the object's reference count.
|
||||
|
||||
This is done automatically by the smart pointer, but is public just
|
||||
in case it's needed for nefarious purposes.
|
||||
*/
|
||||
void incReferenceCount() const { ++refCount; }
|
||||
|
||||
/** Decreases the object's reference count.
|
||||
|
||||
If the count gets to zero, the object will be deleted.
|
||||
*/
|
||||
void decReferenceCount() const
|
||||
{
|
||||
assert(getReferenceCount() > 0);
|
||||
|
||||
if (--refCount == 0)
|
||||
delete this;
|
||||
}
|
||||
|
||||
/** Returns the object's current reference count.
|
||||
* @returns The reference count.
|
||||
*/
|
||||
int getReferenceCount() const { return static_cast<int>(refCount); }
|
||||
|
||||
protected:
|
||||
//==============================================================================
|
||||
/** Creates the reference-counted object (with an initial ref count of zero). */
|
||||
RefCountedObjectType() : refCount() {}
|
||||
|
||||
/** Destructor. */
|
||||
virtual ~RefCountedObjectType()
|
||||
{
|
||||
// it's dangerous to delete an object that's still referenced by something else!
|
||||
assert(getReferenceCount() == 0);
|
||||
}
|
||||
|
||||
private:
|
||||
//==============================================================================
|
||||
CounterType mutable refCount;
|
||||
};
|
||||
|
||||
//==============================================================================
|
||||
|
||||
/** Non thread-safe reference counted object.
|
||||
|
||||
This creates a RefCountedObjectType that uses a non-atomic integer
|
||||
as the counter.
|
||||
*/
|
||||
typedef RefCountedObjectType<int> RefCountedObject;
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
A smart-pointer class which points to a reference-counted object.
|
||||
|
||||
The template parameter specifies the class of the object you want to point
|
||||
to - the easiest way to make a class reference-countable is to simply make
|
||||
it inherit from RefCountedObjectType, but if you need to, you could roll
|
||||
your own reference-countable class by implementing a pair of methods called
|
||||
incReferenceCount() and decReferenceCount().
|
||||
|
||||
When using this class, you'll probably want to create a typedef to
|
||||
abbreviate the full templated name - e.g.
|
||||
|
||||
@code
|
||||
|
||||
typedef RefCountedObjectPtr <MyClass> MyClassPtr;
|
||||
|
||||
@endcode
|
||||
*/
|
||||
template<class ReferenceCountedObjectClass>
|
||||
class RefCountedObjectPtr
|
||||
{
|
||||
public:
|
||||
/** The class being referenced by this pointer. */
|
||||
typedef ReferenceCountedObjectClass ReferencedType;
|
||||
|
||||
//==============================================================================
|
||||
/** Creates a pointer to a null object. */
|
||||
RefCountedObjectPtr() : referencedObject(nullptr) {}
|
||||
|
||||
/** Creates a pointer to an object.
|
||||
This will increment the object's reference-count if it is non-null.
|
||||
|
||||
@param refCountedObject A reference counted object to own.
|
||||
*/
|
||||
RefCountedObjectPtr(ReferenceCountedObjectClass* const refCountedObject)
|
||||
: referencedObject(refCountedObject)
|
||||
{
|
||||
if (refCountedObject != nullptr)
|
||||
refCountedObject->incReferenceCount();
|
||||
}
|
||||
|
||||
/** Copies another pointer.
|
||||
This will increment the object's reference-count (if it is non-null).
|
||||
|
||||
@param other Another pointer.
|
||||
*/
|
||||
RefCountedObjectPtr(const RefCountedObjectPtr& other) : referencedObject(other.referencedObject)
|
||||
{
|
||||
if (referencedObject != nullptr)
|
||||
referencedObject->incReferenceCount();
|
||||
}
|
||||
|
||||
/**
|
||||
Takes-over the object from another pointer.
|
||||
|
||||
@param other Another pointer.
|
||||
*/
|
||||
RefCountedObjectPtr(RefCountedObjectPtr&& other) : referencedObject(other.referencedObject)
|
||||
{
|
||||
other.referencedObject = nullptr;
|
||||
}
|
||||
|
||||
/** Copies another pointer.
|
||||
This will increment the object's reference-count (if it is non-null).
|
||||
|
||||
@param other Another pointer.
|
||||
*/
|
||||
template<class DerivedClass>
|
||||
RefCountedObjectPtr(const RefCountedObjectPtr<DerivedClass>& other)
|
||||
: referencedObject(static_cast<ReferenceCountedObjectClass*>(other.getObject()))
|
||||
{
|
||||
if (referencedObject != nullptr)
|
||||
referencedObject->incReferenceCount();
|
||||
}
|
||||
|
||||
/** Changes this pointer to point at a different object.
|
||||
|
||||
The reference count of the old object is decremented, and it might be
|
||||
deleted if it hits zero. The new object's count is incremented.
|
||||
|
||||
@param other A pointer to assign from.
|
||||
@returns This pointer.
|
||||
*/
|
||||
RefCountedObjectPtr& operator=(const RefCountedObjectPtr& other)
|
||||
{
|
||||
return operator=(other.referencedObject);
|
||||
}
|
||||
|
||||
/** Changes this pointer to point at a different object.
|
||||
The reference count of the old object is decremented, and it might be
|
||||
deleted if it hits zero. The new object's count is incremented.
|
||||
|
||||
@param other A pointer to assign from.
|
||||
@returns This pointer.
|
||||
*/
|
||||
template<class DerivedClass>
|
||||
RefCountedObjectPtr& operator=(const RefCountedObjectPtr<DerivedClass>& other)
|
||||
{
|
||||
return operator=(static_cast<ReferenceCountedObjectClass*>(other.getObject()));
|
||||
}
|
||||
|
||||
/**
|
||||
Takes-over the object from another pointer.
|
||||
|
||||
@param other A pointer to assign from.
|
||||
@returns This pointer.
|
||||
*/
|
||||
RefCountedObjectPtr& operator=(RefCountedObjectPtr&& other)
|
||||
{
|
||||
std::swap(referencedObject, other.referencedObject);
|
||||
return *this;
|
||||
}
|
||||
|
||||
/** Changes this pointer to point at a different object.
|
||||
The reference count of the old object is decremented, and it might be
|
||||
deleted if it hits zero. The new object's count is incremented.
|
||||
|
||||
@param newObject A reference counted object to own.
|
||||
@returns This pointer.
|
||||
*/
|
||||
RefCountedObjectPtr& operator=(ReferenceCountedObjectClass* const newObject)
|
||||
{
|
||||
if (referencedObject != newObject)
|
||||
{
|
||||
if (newObject != nullptr)
|
||||
newObject->incReferenceCount();
|
||||
|
||||
ReferenceCountedObjectClass* const oldObject = referencedObject;
|
||||
referencedObject = newObject;
|
||||
|
||||
if (oldObject != nullptr)
|
||||
oldObject->decReferenceCount();
|
||||
}
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
/** Destructor.
|
||||
This will decrement the object's reference-count, and may delete it if it
|
||||
gets to zero.
|
||||
*/
|
||||
~RefCountedObjectPtr()
|
||||
{
|
||||
if (referencedObject != nullptr)
|
||||
referencedObject->decReferenceCount();
|
||||
}
|
||||
|
||||
/** Returns the object that this pointer references.
|
||||
The returned pointer may be null.
|
||||
|
||||
@returns The pointee.
|
||||
*/
|
||||
operator ReferenceCountedObjectClass*() const { return referencedObject; }
|
||||
|
||||
/** Returns the object that this pointer references.
|
||||
The returned pointer may be null.
|
||||
|
||||
@returns The pointee.
|
||||
*/
|
||||
ReferenceCountedObjectClass* operator->() const { return referencedObject; }
|
||||
|
||||
/** Returns the object that this pointer references.
|
||||
The returned pointer may be null.
|
||||
|
||||
@returns The pointee.
|
||||
*/
|
||||
ReferenceCountedObjectClass* getObject() const { return referencedObject; }
|
||||
|
||||
private:
|
||||
//==============================================================================
|
||||
ReferenceCountedObjectClass* referencedObject;
|
||||
};
|
||||
|
||||
//==============================================================================
|
||||
|
||||
// forward declaration
|
||||
template<class T>
|
||||
struct ContainerTraits;
|
||||
|
||||
template<class T>
|
||||
struct ContainerTraits<RefCountedObjectPtr<T>>
|
||||
{
|
||||
typedef T Type;
|
||||
|
||||
static T* get(RefCountedObjectPtr<T> const& c) { return c.getObject(); }
|
||||
};
|
||||
|
||||
//==============================================================================
|
||||
|
||||
} // namespace luabridge
|
||||
226
csgo2/LuaBridge/luaBridge/RefCountedPtr.h
Normal file
226
csgo2/LuaBridge/luaBridge/RefCountedPtr.h
Normal file
@@ -0,0 +1,226 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2021, Stefan Frings
|
||||
// Copyright 2019, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2007, Nathan Reed
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <cassert>
|
||||
#include <unordered_map>
|
||||
#include <utility>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
namespace detail {
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
Support for our RefCountedPtr.
|
||||
*/
|
||||
struct RefCountedPtrBase
|
||||
{
|
||||
// Declaration of container for the refcounts
|
||||
typedef std::unordered_map<const void*, int> RefCountsType;
|
||||
|
||||
protected:
|
||||
RefCountsType& getRefCounts() const
|
||||
{
|
||||
static RefCountsType refcounts;
|
||||
return refcounts;
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
A reference counted smart pointer.
|
||||
|
||||
The api is compatible with boost::RefCountedPtr and std::RefCountedPtr, in the
|
||||
sense that it implements a strict subset of the functionality.
|
||||
|
||||
This implementation uses a hash table to look up the reference count
|
||||
associated with a particular pointer.
|
||||
|
||||
@tparam T The class type.
|
||||
|
||||
@todo Decompose RefCountedPtr using a policy. At a minimum, the underlying
|
||||
reference count should be policy based (to support atomic operations)
|
||||
and the delete behavior should be policy based (to support custom
|
||||
disposal methods).
|
||||
|
||||
@todo Provide an intrusive version of RefCountedPtr.
|
||||
*/
|
||||
template<class T>
|
||||
class RefCountedPtr : private detail::RefCountedPtrBase
|
||||
{
|
||||
public:
|
||||
template<typename Other>
|
||||
struct rebind
|
||||
{
|
||||
typedef RefCountedPtr<Other> other;
|
||||
};
|
||||
|
||||
/** Construct as nullptr or from existing pointer to T.
|
||||
|
||||
@param p The optional, existing pointer to assign from.
|
||||
*/
|
||||
RefCountedPtr(T* const p = nullptr) : m_p(p)
|
||||
{
|
||||
if (m_p)
|
||||
{
|
||||
++getRefCounts()[m_p];
|
||||
}
|
||||
}
|
||||
|
||||
/** Construct from another RefCountedPtr.
|
||||
|
||||
@param rhs The RefCountedPtr to assign from.
|
||||
*/
|
||||
RefCountedPtr(RefCountedPtr<T> const& rhs) : RefCountedPtr(rhs.get()) {}
|
||||
|
||||
/** Construct from a RefCountedPtr of a different type.
|
||||
|
||||
@invariant A pointer to U must be convertible to a pointer to T.
|
||||
|
||||
@tparam U The other object type.
|
||||
@param rhs The RefCountedPtr to assign from.
|
||||
*/
|
||||
template<typename U>
|
||||
RefCountedPtr(RefCountedPtr<U> const& rhs) : RefCountedPtr(rhs.get())
|
||||
{
|
||||
}
|
||||
|
||||
/** Release the object.
|
||||
|
||||
If there are no more references then the object is deleted.
|
||||
*/
|
||||
~RefCountedPtr() { reset(); }
|
||||
|
||||
/** Assign from another RefCountedPtr.
|
||||
|
||||
@param rhs The RefCountedPtr to assign from.
|
||||
@returns A reference to the RefCountedPtr.
|
||||
*/
|
||||
RefCountedPtr<T>& operator=(RefCountedPtr<T> const& rhs)
|
||||
{
|
||||
// NOTE Self assignment is handled gracefully
|
||||
*this = rhs.get();
|
||||
return *this;
|
||||
}
|
||||
|
||||
/** Assign from another RefCountedPtr of a different type.
|
||||
|
||||
@note A pointer to U must be convertible to a pointer to T.
|
||||
|
||||
@tparam U The other object type.
|
||||
@param rhs The other RefCountedPtr to assign from.
|
||||
@returns A reference to the RefCountedPtr.
|
||||
*/
|
||||
template<typename U>
|
||||
RefCountedPtr<T>& operator=(RefCountedPtr<U> const& rhs)
|
||||
{
|
||||
// NOTE Self assignment is handled gracefully
|
||||
*this = rhs.get();
|
||||
return *this;
|
||||
}
|
||||
|
||||
RefCountedPtr<T>& operator=(T* const p)
|
||||
{
|
||||
if (p != m_p)
|
||||
{
|
||||
RefCountedPtr<T> tmp(p);
|
||||
std::swap(m_p, tmp.m_p);
|
||||
}
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
/** Retrieve the raw pointer.
|
||||
|
||||
@returns A pointer to the object.
|
||||
*/
|
||||
T* get() const { return m_p; }
|
||||
|
||||
/** Retrieve the raw pointer by conversion.
|
||||
|
||||
@returns A pointer to the object.
|
||||
*/
|
||||
operator T*() const { return m_p; }
|
||||
|
||||
/** Retrieve the raw pointer.
|
||||
|
||||
@returns A pointer to the object.
|
||||
*/
|
||||
T* operator*() const { return m_p; }
|
||||
|
||||
/** Retrieve the raw pointer.
|
||||
|
||||
@returns A pointer to the object.
|
||||
*/
|
||||
T* operator->() const { return m_p; }
|
||||
|
||||
/** Determine the number of references.
|
||||
|
||||
@note This is not thread-safe.
|
||||
|
||||
@returns The number of active references.
|
||||
*/
|
||||
RefCountsType::mapped_type use_count() const
|
||||
{
|
||||
if (!m_p)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
const auto itCounter = getRefCounts().find(m_p);
|
||||
assert(itCounter != getRefCounts().end());
|
||||
assert(itCounter->second > 0);
|
||||
|
||||
return itCounter->second;
|
||||
}
|
||||
|
||||
/** Release the pointer.
|
||||
|
||||
The reference count is decremented. If the reference count reaches
|
||||
zero, the object is deleted.
|
||||
*/
|
||||
void reset()
|
||||
{
|
||||
if (m_p)
|
||||
{
|
||||
const auto itCounter = getRefCounts().find(m_p);
|
||||
assert(itCounter != getRefCounts().end());
|
||||
assert(itCounter->second > 0);
|
||||
|
||||
if (--itCounter->second == 0)
|
||||
{
|
||||
delete m_p;
|
||||
getRefCounts().erase(itCounter);
|
||||
}
|
||||
|
||||
m_p = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
T* m_p;
|
||||
};
|
||||
|
||||
//==============================================================================
|
||||
|
||||
// forward declaration
|
||||
template<class T>
|
||||
struct ContainerTraits;
|
||||
|
||||
template<class T>
|
||||
struct ContainerTraits<RefCountedPtr<T>>
|
||||
{
|
||||
typedef T Type;
|
||||
|
||||
static T* get(RefCountedPtr<T> const& c) { return c.get(); }
|
||||
};
|
||||
|
||||
} // namespace luabridge
|
||||
51
csgo2/LuaBridge/luaBridge/UnorderedMap.h
Normal file
51
csgo2/LuaBridge/luaBridge/UnorderedMap.h
Normal file
@@ -0,0 +1,51 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2019, Dmitry Tarakanov
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
|
||||
#include <unordered_map>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
template<class K, class V>
|
||||
struct Stack<std::unordered_map<K, V>>
|
||||
{
|
||||
typedef std::unordered_map<K, V> Map;
|
||||
|
||||
static void push(lua_State* L, const Map& map)
|
||||
{
|
||||
lua_createtable(L, 0, static_cast<int>(map.size()));
|
||||
typedef typename Map::const_iterator ConstIter;
|
||||
for (ConstIter i = map.begin(); i != map.end(); ++i)
|
||||
{
|
||||
Stack<K>::push(L, i->first);
|
||||
Stack<V>::push(L, i->second);
|
||||
lua_settable(L, -3);
|
||||
}
|
||||
}
|
||||
|
||||
static Map get(lua_State* L, int index)
|
||||
{
|
||||
if (!lua_istable(L, index))
|
||||
{
|
||||
luaL_error(L, "#%d argument must be a table", index);
|
||||
}
|
||||
|
||||
Map map;
|
||||
int const absindex = lua_absindex(L, index);
|
||||
lua_pushnil(L);
|
||||
while (lua_next(L, absindex) != 0)
|
||||
{
|
||||
map.emplace(Stack<K>::get(L, -2), Stack<V>::get(L, -1));
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
return map;
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_istable(L, index); }
|
||||
};
|
||||
|
||||
} // namespace luabridge
|
||||
50
csgo2/LuaBridge/luaBridge/Vector.h
Normal file
50
csgo2/LuaBridge/luaBridge/Vector.h
Normal file
@@ -0,0 +1,50 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2018, Dmitry Tarakanov
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
|
||||
#include <vector>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
template<class T>
|
||||
struct Stack<std::vector<T>>
|
||||
{
|
||||
static void push(lua_State* L, std::vector<T> const& vector)
|
||||
{
|
||||
lua_createtable(L, static_cast<int>(vector.size()), 0);
|
||||
for (std::size_t i = 0; i < vector.size(); ++i)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(i + 1));
|
||||
Stack<T>::push(L, vector[i]);
|
||||
lua_settable(L, -3);
|
||||
}
|
||||
}
|
||||
|
||||
static std::vector<T> get(lua_State* L, int index)
|
||||
{
|
||||
if (!lua_istable(L, index))
|
||||
{
|
||||
luaL_error(L, "#%d argument must be a table", index);
|
||||
}
|
||||
|
||||
std::vector<T> vector;
|
||||
vector.reserve(static_cast<std::size_t>(get_length(L, index)));
|
||||
|
||||
int const absindex = lua_absindex(L, index);
|
||||
lua_pushnil(L);
|
||||
while (lua_next(L, absindex) != 0)
|
||||
{
|
||||
vector.push_back(Stack<T>::get(L, -1));
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
return vector;
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_istable(L, index); }
|
||||
};
|
||||
|
||||
} // namespace luabridge
|
||||
470
csgo2/LuaBridge/luaBridge/detail/CFunctions.h
Normal file
470
csgo2/LuaBridge/luaBridge/detail/CFunctions.h
Normal file
@@ -0,0 +1,470 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2019, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Config.h>
|
||||
#include <LuaBridge/detail/FuncTraits.h>
|
||||
|
||||
#include <string>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
namespace detail {
|
||||
|
||||
// We use a structure so we can define everything in the header.
|
||||
//
|
||||
struct CFunc
|
||||
{
|
||||
static void addGetter(lua_State* L, const char* name, int tableIndex)
|
||||
{
|
||||
assert(lua_istable(L, tableIndex));
|
||||
assert(lua_iscfunction(L, -1)); // Stack: getter
|
||||
|
||||
lua_rawgetp(L, tableIndex, getPropgetKey()); // Stack: getter, propget table (pg)
|
||||
lua_pushvalue(L, -2); // Stack: getter, pg, getter
|
||||
rawsetfield(L, -2, name); // Stack: getter, pg
|
||||
lua_pop(L, 2); // Stack: -
|
||||
}
|
||||
|
||||
static void addSetter(lua_State* L, const char* name, int tableIndex)
|
||||
{
|
||||
assert(lua_istable(L, tableIndex));
|
||||
assert(lua_iscfunction(L, -1)); // Stack: setter
|
||||
|
||||
lua_rawgetp(L, tableIndex, getPropsetKey()); // Stack: setter, propset table (ps)
|
||||
lua_pushvalue(L, -2); // Stack: setter, ps, setter
|
||||
rawsetfield(L, -2, name); // Stack: setter, ps
|
||||
lua_pop(L, 2); // Stack: -
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
__index metamethod for a namespace or class static and non-static members.
|
||||
Retrieves functions from metatables and properties from propget tables.
|
||||
Looks through the class hierarchy if inheritance is present.
|
||||
*/
|
||||
static int indexMetaMethod(lua_State* L)
|
||||
{
|
||||
assert(lua_istable(L, 1) ||
|
||||
lua_isuserdata(L, 1)); // Stack (further not shown): table | userdata, name
|
||||
|
||||
lua_getmetatable(L, 1); // Stack: class/const table (mt)
|
||||
assert(lua_istable(L, -1));
|
||||
|
||||
for (;;)
|
||||
{
|
||||
lua_pushvalue(L, 2); // Stack: mt, field name
|
||||
lua_rawget(L, -2); // Stack: mt, field | nil
|
||||
|
||||
if (lua_iscfunction(L, -1)) // Stack: mt, field
|
||||
{
|
||||
lua_remove(L, -2); // Stack: field
|
||||
return 1;
|
||||
}
|
||||
|
||||
assert(lua_isnil(L, -1)); // Stack: mt, nil
|
||||
lua_pop(L, 1); // Stack: mt
|
||||
|
||||
lua_rawgetp(L, -1, getPropgetKey()); // Stack: mt, propget table (pg)
|
||||
assert(lua_istable(L, -1));
|
||||
|
||||
lua_pushvalue(L, 2); // Stack: mt, pg, field name
|
||||
lua_rawget(L, -2); // Stack: mt, pg, getter | nil
|
||||
lua_remove(L, -2); // Stack: mt, getter | nil
|
||||
|
||||
if (lua_iscfunction(L, -1)) // Stack: mt, getter
|
||||
{
|
||||
lua_remove(L, -2); // Stack: getter
|
||||
lua_pushvalue(L, 1); // Stack: getter, table | userdata
|
||||
lua_call(L, 1, 1); // Stack: value
|
||||
return 1;
|
||||
}
|
||||
|
||||
assert(lua_isnil(L, -1)); // Stack: mt, nil
|
||||
lua_pop(L, 1); // Stack: mt
|
||||
|
||||
// It may mean that the field may be in const table and it's constness violation.
|
||||
// Don't check that, just return nil
|
||||
|
||||
// Repeat the lookup in the parent metafield,
|
||||
// or return nil if the field doesn't exist.
|
||||
lua_rawgetp(L, -1, getParentKey()); // Stack: mt, parent mt | nil
|
||||
|
||||
if (lua_isnil(L, -1)) // Stack: mt, nil
|
||||
{
|
||||
lua_remove(L, -2); // Stack: nil
|
||||
return 1;
|
||||
}
|
||||
|
||||
// Removethe metatable and repeat the search in the parent one.
|
||||
assert(lua_istable(L, -1)); // Stack: mt, parent mt
|
||||
lua_remove(L, -2); // Stack: parent mt
|
||||
}
|
||||
|
||||
// no return
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
__newindex metamethod for namespace or class static members.
|
||||
Retrieves properties from propset tables.
|
||||
*/
|
||||
static int newindexStaticMetaMethod(lua_State* L) { return newindexMetaMethod(L, false); }
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
__newindex metamethod for non-static members.
|
||||
Retrieves properties from propset tables.
|
||||
*/
|
||||
static int newindexObjectMetaMethod(lua_State* L) { return newindexMetaMethod(L, true); }
|
||||
|
||||
static int newindexMetaMethod(lua_State* L, bool pushSelf)
|
||||
{
|
||||
assert(
|
||||
lua_istable(L, 1) ||
|
||||
lua_isuserdata(L, 1)); // Stack (further not shown): table | userdata, name, new value
|
||||
|
||||
lua_getmetatable(L, 1); // Stack: metatable (mt)
|
||||
assert(lua_istable(L, -1));
|
||||
|
||||
for (;;)
|
||||
{
|
||||
lua_rawgetp(L, -1, getPropsetKey()); // Stack: mt, propset table (ps) | nil
|
||||
|
||||
if (lua_isnil(L, -1)) // Stack: mt, nil
|
||||
{
|
||||
lua_pop(L, 2); // Stack: -
|
||||
return luaL_error(L, "No member named '%s'", lua_tostring(L, 2));
|
||||
}
|
||||
|
||||
assert(lua_istable(L, -1));
|
||||
|
||||
lua_pushvalue(L, 2); // Stack: mt, ps, field name
|
||||
lua_rawget(L, -2); // Stack: mt, ps, setter | nil
|
||||
lua_remove(L, -2); // Stack: mt, setter | nil
|
||||
|
||||
if (lua_iscfunction(L, -1)) // Stack: mt, setter
|
||||
{
|
||||
lua_remove(L, -2); // Stack: setter
|
||||
if (pushSelf)
|
||||
{
|
||||
lua_pushvalue(L, 1); // Stack: setter, table | userdata
|
||||
}
|
||||
lua_pushvalue(L, 3); // Stack: setter, table | userdata, new value
|
||||
lua_call(L, pushSelf ? 2 : 1, 0); // Stack: -
|
||||
return 0;
|
||||
}
|
||||
|
||||
assert(lua_isnil(L, -1)); // Stack: mt, nil
|
||||
lua_pop(L, 1); // Stack: mt
|
||||
|
||||
lua_rawgetp(L, -1, getParentKey()); // Stack: mt, parent mt | nil
|
||||
|
||||
if (lua_isnil(L, -1)) // Stack: mt, nil
|
||||
{
|
||||
lua_pop(L, 1); // Stack: -
|
||||
return luaL_error(L, "No writable member '%s'", lua_tostring(L, 2));
|
||||
}
|
||||
|
||||
assert(lua_istable(L, -1)); // Stack: mt, parent mt
|
||||
lua_remove(L, -2); // Stack: parent mt
|
||||
// Repeat the search in the parent
|
||||
}
|
||||
|
||||
// no return
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to report an error writing to a read-only value.
|
||||
|
||||
The name of the variable is in the first upvalue.
|
||||
*/
|
||||
static int readOnlyError(lua_State* L)
|
||||
{
|
||||
std::string s;
|
||||
|
||||
s = s + "'" + lua_tostring(L, lua_upvalueindex(1)) + "' is read-only";
|
||||
|
||||
return luaL_error(L, s.c_str());
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to get a variable.
|
||||
|
||||
This is used for global variables or class static data members.
|
||||
|
||||
The pointer to the data is in the first upvalue.
|
||||
*/
|
||||
template<class T>
|
||||
static int getVariable(lua_State* L)
|
||||
{
|
||||
assert(lua_islightuserdata(L, lua_upvalueindex(1)));
|
||||
T const* ptr = static_cast<T const*>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
assert(ptr != 0);
|
||||
Stack<T>::push(L, *ptr);
|
||||
return 1;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to set a variable.
|
||||
|
||||
This is used for global variables or class static data members.
|
||||
|
||||
The pointer to the data is in the first upvalue.
|
||||
*/
|
||||
template<class T>
|
||||
static int setVariable(lua_State* L)
|
||||
{
|
||||
assert(lua_islightuserdata(L, lua_upvalueindex(1)));
|
||||
T* ptr = static_cast<T*>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
assert(ptr != 0);
|
||||
*ptr = Stack<T>::get(L, 1);
|
||||
return 0;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to call a function with a return value.
|
||||
|
||||
This is used for global functions, global properties, class static methods,
|
||||
and class static properties.
|
||||
|
||||
The function pointer (lightuserdata) in the first upvalue.
|
||||
*/
|
||||
template<class FnPtr>
|
||||
struct Call
|
||||
{
|
||||
typedef typename FuncTraits<FnPtr>::Params Params;
|
||||
typedef typename FuncTraits<FnPtr>::ReturnType ReturnType;
|
||||
|
||||
static int f(lua_State* L)
|
||||
{
|
||||
assert(lua_islightuserdata(L, lua_upvalueindex(1)));
|
||||
FnPtr fnptr = reinterpret_cast<FnPtr>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
assert(fnptr != 0);
|
||||
return Invoke<ReturnType, Params, 1>::run(L, fnptr);
|
||||
}
|
||||
};
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to call a class member function with a return value.
|
||||
|
||||
The member function pointer is in the first upvalue.
|
||||
The class userdata object is at the top of the Lua stack.
|
||||
*/
|
||||
template<class MemFnPtr>
|
||||
struct CallMember
|
||||
{
|
||||
typedef typename FuncTraits<MemFnPtr>::ClassType T;
|
||||
typedef typename FuncTraits<MemFnPtr>::Params Params;
|
||||
typedef typename FuncTraits<MemFnPtr>::ReturnType ReturnType;
|
||||
|
||||
static int f(lua_State* L)
|
||||
{
|
||||
assert(isfulluserdata(L, lua_upvalueindex(1)));
|
||||
T* const t = Userdata::get<T>(L, 1, false);
|
||||
MemFnPtr const& fnptr =
|
||||
*static_cast<MemFnPtr const*>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
assert(fnptr != 0);
|
||||
return Invoke<ReturnType, Params, 2>::run(L, t, fnptr);
|
||||
}
|
||||
};
|
||||
|
||||
template<class MemFnPtr>
|
||||
struct CallConstMember
|
||||
{
|
||||
typedef typename FuncTraits<MemFnPtr>::ClassType T;
|
||||
typedef typename FuncTraits<MemFnPtr>::Params Params;
|
||||
typedef typename FuncTraits<MemFnPtr>::ReturnType ReturnType;
|
||||
|
||||
static int f(lua_State* L)
|
||||
{
|
||||
assert(isfulluserdata(L, lua_upvalueindex(1)));
|
||||
T const* const t = Userdata::get<T>(L, 1, true);
|
||||
MemFnPtr const& fnptr =
|
||||
*static_cast<MemFnPtr const*>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
assert(fnptr != 0);
|
||||
return Invoke<ReturnType, Params, 2>::run(L, t, fnptr);
|
||||
}
|
||||
};
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to call a class member lua_CFunction.
|
||||
|
||||
The member function pointer is in the first upvalue.
|
||||
The object userdata ('this') value is at top ot the Lua stack.
|
||||
*/
|
||||
template<class T>
|
||||
struct CallMemberCFunction
|
||||
{
|
||||
static int f(lua_State* L)
|
||||
{
|
||||
assert(isfulluserdata(L, lua_upvalueindex(1)));
|
||||
typedef int (T::*MFP)(lua_State * L);
|
||||
T* const t = Userdata::get<T>(L, 1, false);
|
||||
MFP const& fnptr = *static_cast<MFP const*>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
assert(fnptr != 0);
|
||||
return (t->*fnptr)(L);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct CallConstMemberCFunction
|
||||
{
|
||||
static int f(lua_State* L)
|
||||
{
|
||||
assert(isfulluserdata(L, lua_upvalueindex(1)));
|
||||
typedef int (T::*MFP)(lua_State * L);
|
||||
T const* const t = Userdata::get<T>(L, 1, true);
|
||||
MFP const& fnptr = *static_cast<MFP const*>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
assert(fnptr != 0);
|
||||
return (t->*fnptr)(L);
|
||||
}
|
||||
};
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to call on a object.
|
||||
|
||||
The proxy function pointer (lightuserdata) is in the first upvalue.
|
||||
The class userdata object is at the top of the Lua stack.
|
||||
*/
|
||||
template<class FnPtr>
|
||||
struct CallProxyFunction
|
||||
{
|
||||
using Params = typename FuncTraits<FnPtr>::Params;
|
||||
using ReturnType = typename FuncTraits<FnPtr>::ReturnType;
|
||||
|
||||
static int f(lua_State* L)
|
||||
{
|
||||
assert(lua_islightuserdata(L, lua_upvalueindex(1)));
|
||||
auto fnptr = reinterpret_cast<FnPtr>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
assert(fnptr != 0);
|
||||
return Invoke<ReturnType, Params, 1>::run(L, fnptr);
|
||||
}
|
||||
};
|
||||
|
||||
template<class Functor>
|
||||
struct CallProxyFunctor
|
||||
{
|
||||
using Params = typename FuncTraits<Functor>::Params;
|
||||
using ReturnType = typename FuncTraits<Functor>::ReturnType;
|
||||
|
||||
static int f(lua_State* L)
|
||||
{
|
||||
assert(isfulluserdata(L, lua_upvalueindex(1)));
|
||||
Functor& fn = *static_cast<Functor*>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
return Invoke<ReturnType, Params, 1>::run(L, fn);
|
||||
}
|
||||
};
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
|
||||
// SFINAE Helpers
|
||||
|
||||
template<class MemFnPtr, bool isConst>
|
||||
struct CallMemberFunctionHelper
|
||||
{
|
||||
static void add(lua_State* L, char const* name, MemFnPtr mf)
|
||||
{
|
||||
new (lua_newuserdata(L, sizeof(MemFnPtr))) MemFnPtr(mf);
|
||||
lua_pushcclosure(L, &CallConstMember<MemFnPtr>::f, 1);
|
||||
lua_pushvalue(L, -1);
|
||||
rawsetfield(L, -5, name); // const table
|
||||
rawsetfield(L, -3, name); // class table
|
||||
}
|
||||
};
|
||||
|
||||
template<class MemFnPtr>
|
||||
struct CallMemberFunctionHelper<MemFnPtr, false>
|
||||
{
|
||||
static void add(lua_State* L, char const* name, MemFnPtr mf)
|
||||
{
|
||||
new (lua_newuserdata(L, sizeof(MemFnPtr))) MemFnPtr(mf);
|
||||
lua_pushcclosure(L, &CallMember<MemFnPtr>::f, 1);
|
||||
rawsetfield(L, -3, name); // class table
|
||||
}
|
||||
};
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
__gc metamethod for a class.
|
||||
*/
|
||||
template<class C>
|
||||
static int gcMetaMethod(lua_State* L)
|
||||
{
|
||||
Userdata* const ud = Userdata::getExact<C>(L, 1);
|
||||
ud->~Userdata();
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
__gc metamethod for an arbitrary class.
|
||||
*/
|
||||
template<class T>
|
||||
static int gcMetaMethodAny(lua_State* L)
|
||||
{
|
||||
assert(isfulluserdata(L, 1));
|
||||
T* t = static_cast<T*>(lua_touserdata(L, 1));
|
||||
t->~T();
|
||||
return 0;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to get a class data member.
|
||||
|
||||
The pointer-to-member is in the first upvalue.
|
||||
The class userdata object is at the top of the Lua stack.
|
||||
*/
|
||||
template<class C, typename T>
|
||||
static int getProperty(lua_State* L)
|
||||
{
|
||||
C* const c = Userdata::get<C>(L, 1, true);
|
||||
T C::** mp = static_cast<T C::**>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
try
|
||||
{
|
||||
Stack<T&>::push(L, c->**mp);
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
luaL_error(L, e.what());
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
lua_CFunction to set a class data member.
|
||||
|
||||
The pointer-to-member is in the first upvalue.
|
||||
The class userdata object is at the top of the Lua stack.
|
||||
*/
|
||||
template<class C, typename T>
|
||||
static int setProperty(lua_State* L)
|
||||
{
|
||||
C* const c = Userdata::get<C>(L, 1, false);
|
||||
T C::** mp = static_cast<T C::**>(lua_touserdata(L, lua_upvalueindex(1)));
|
||||
try
|
||||
{
|
||||
c->** mp = Stack<T>::get(L, 2);
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
luaL_error(L, e.what());
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
} // namespace luabridge
|
||||
140
csgo2/LuaBridge/luaBridge/detail/ClassInfo.h
Normal file
140
csgo2/LuaBridge/luaBridge/detail/ClassInfo.h
Normal file
@@ -0,0 +1,140 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2020, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
namespace detail {
|
||||
|
||||
/**
|
||||
* A unique key for a type name in a metatable.
|
||||
*/
|
||||
inline const void* getTypeKey()
|
||||
{
|
||||
#ifdef _NDEBUG
|
||||
static char value;
|
||||
return &value;
|
||||
#else
|
||||
return reinterpret_cast<void*>(0x71);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* The key of a const table in another metatable.
|
||||
*/
|
||||
inline const void* getConstKey()
|
||||
{
|
||||
#ifdef _NDEBUG
|
||||
static char value;
|
||||
return &value;
|
||||
#else
|
||||
return reinterpret_cast<void*>(0xc07);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* The key of a class table in another metatable.
|
||||
*/
|
||||
inline const void* getClassKey()
|
||||
{
|
||||
#ifdef _NDEBUG
|
||||
static char value;
|
||||
return &value;
|
||||
#else
|
||||
return reinterpret_cast<void*>(0xc1a);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* The key of a propget table in another metatable.
|
||||
*/
|
||||
inline const void* getPropgetKey()
|
||||
{
|
||||
#ifdef _NDEBUG
|
||||
static char value;
|
||||
return &value;
|
||||
#else
|
||||
return reinterpret_cast<void*>(0x6e7);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* The key of a propset table in another metatable.
|
||||
*/
|
||||
inline const void* getPropsetKey()
|
||||
{
|
||||
#ifdef _NDEBUG
|
||||
static char value;
|
||||
return &value;
|
||||
#else
|
||||
return reinterpret_cast<void*>(0x5e7);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* The key of a static table in another metatable.
|
||||
*/
|
||||
inline const void* getStaticKey()
|
||||
{
|
||||
#ifdef _NDEBUG
|
||||
static char value;
|
||||
return &value;
|
||||
#else
|
||||
return reinterpret_cast<void*>(0x57a);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* The key of a parent table in another metatable.
|
||||
*/
|
||||
inline const void* getParentKey()
|
||||
{
|
||||
#ifdef _NDEBUG
|
||||
static char value;
|
||||
return &value;
|
||||
#else
|
||||
return reinterpret_cast<void*>(0xdad);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
Get the key for the static table in the Lua registry.
|
||||
The static table holds the static data members, static properties, and
|
||||
static member functions for a class.
|
||||
*/
|
||||
template<class T>
|
||||
void const* getStaticRegistryKey()
|
||||
{
|
||||
static char value;
|
||||
return &value;
|
||||
}
|
||||
|
||||
/** Get the key for the class table in the Lua registry.
|
||||
The class table holds the data members, properties, and member functions
|
||||
of a class. Read-only data and properties, and const member functions are
|
||||
also placed here (to save a lookup in the const table).
|
||||
*/
|
||||
template<class T>
|
||||
void const* getClassRegistryKey()
|
||||
{
|
||||
static char value;
|
||||
return &value;
|
||||
}
|
||||
|
||||
/** Get the key for the const table in the Lua registry.
|
||||
The const table holds read-only data members and properties, and const
|
||||
member functions of a class.
|
||||
*/
|
||||
template<class T>
|
||||
void const* getConstRegistryKey()
|
||||
{
|
||||
static char value;
|
||||
return &value;
|
||||
}
|
||||
|
||||
} // namespace detail
|
||||
|
||||
} // namespace luabridge
|
||||
7
csgo2/LuaBridge/luaBridge/detail/Config.h
Normal file
7
csgo2/LuaBridge/luaBridge/detail/Config.h
Normal file
@@ -0,0 +1,7 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2020, Dmitry Tarakanov
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
// Empty file
|
||||
225
csgo2/LuaBridge/luaBridge/detail/Constructor.h
Normal file
225
csgo2/LuaBridge/luaBridge/detail/Constructor.h
Normal file
@@ -0,0 +1,225 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2007, Nathan Reed
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
namespace detail {
|
||||
|
||||
/*
|
||||
* Constructor generators. These templates allow you to call operator new and
|
||||
* pass the contents of a type/value list to the Constructor. Like the
|
||||
* function pointer containers, these are only defined up to 8 parameters.
|
||||
*/
|
||||
|
||||
/** Constructor generators.
|
||||
|
||||
These templates call operator new with the contents of a type/value
|
||||
list passed to the Constructor with up to 8 parameters. Two versions
|
||||
of call() are provided. One performs a regular new, the other performs
|
||||
a placement new.
|
||||
*/
|
||||
template<class T, typename List>
|
||||
struct Constructor
|
||||
{
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct Constructor<T, None>
|
||||
{
|
||||
static T* call(TypeListValues<None> const&) { return new T; }
|
||||
static T* call(void* mem, TypeListValues<None> const&) { return new (mem) T; }
|
||||
};
|
||||
|
||||
template<class T, class P1>
|
||||
struct Constructor<T, TypeList<P1>>
|
||||
{
|
||||
static T* call(const TypeListValues<TypeList<P1>>& tvl) { return new T(tvl.hd); }
|
||||
static T* call(void* mem, const TypeListValues<TypeList<P1>>& tvl)
|
||||
{
|
||||
return new (mem) T(tvl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T, class P1, class P2>
|
||||
struct Constructor<T, TypeList<P1, TypeList<P2>>>
|
||||
{
|
||||
static T* call(const TypeListValues<TypeList<P1, TypeList<P2>>>& tvl)
|
||||
{
|
||||
return new T(tvl.hd, tvl.tl.hd);
|
||||
}
|
||||
static T* call(void* mem, const TypeListValues<TypeList<P1, TypeList<P2>>>& tvl)
|
||||
{
|
||||
return new (mem) T(tvl.hd, tvl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T, class P1, class P2, class P3>
|
||||
struct Constructor<T, TypeList<P1, TypeList<P2, TypeList<P3>>>>
|
||||
{
|
||||
static T* call(const TypeListValues<TypeList<P1, TypeList<P2, TypeList<P3>>>>& tvl)
|
||||
{
|
||||
return new T(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd);
|
||||
}
|
||||
static T* call(void* mem, const TypeListValues<TypeList<P1, TypeList<P2, TypeList<P3>>>>& tvl)
|
||||
{
|
||||
return new (mem) T(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T, class P1, class P2, class P3, class P4>
|
||||
struct Constructor<T, TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4>>>>>
|
||||
{
|
||||
static T*
|
||||
call(const TypeListValues<TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4>>>>>& tvl)
|
||||
{
|
||||
return new T(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd, tvl.tl.tl.tl.hd);
|
||||
}
|
||||
static T*
|
||||
call(void* mem,
|
||||
const TypeListValues<TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4>>>>>& tvl)
|
||||
{
|
||||
return new (mem) T(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd, tvl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T, class P1, class P2, class P3, class P4, class P5>
|
||||
struct Constructor<T, TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5>>>>>>
|
||||
{
|
||||
static T*
|
||||
call(const TypeListValues<TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5>>>>>>&
|
||||
tvl)
|
||||
{
|
||||
return new T(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd, tvl.tl.tl.tl.hd, tvl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
static T*
|
||||
call(void* mem,
|
||||
const TypeListValues<TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5>>>>>>&
|
||||
tvl)
|
||||
{
|
||||
return new (mem) T(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd, tvl.tl.tl.tl.hd, tvl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T, class P1, class P2, class P3, class P4, class P5, class P6>
|
||||
struct Constructor<
|
||||
T,
|
||||
TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5, TypeList<P6>>>>>>>
|
||||
{
|
||||
static T*
|
||||
call(const TypeListValues<
|
||||
TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5, TypeList<P6>>>>>>>& tvl)
|
||||
{
|
||||
return new T(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
static T*
|
||||
call(void* mem,
|
||||
const TypeListValues<
|
||||
TypeList<P1, TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5, TypeList<P6>>>>>>>&
|
||||
tvl)
|
||||
{
|
||||
return new (mem) T(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T, class P1, class P2, class P3, class P4, class P5, class P6, class P7>
|
||||
struct Constructor<
|
||||
T,
|
||||
TypeList<P1,
|
||||
TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5, TypeList<P6, TypeList<P7>>>>>>>>
|
||||
{
|
||||
static T*
|
||||
call(const TypeListValues<TypeList<
|
||||
P1,
|
||||
TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5, TypeList<P6, TypeList<P7>>>>>>>>&
|
||||
tvl)
|
||||
{
|
||||
return new T(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
static T*
|
||||
call(void* mem,
|
||||
const TypeListValues<TypeList<
|
||||
P1,
|
||||
TypeList<P2, TypeList<P3, TypeList<P4, TypeList<P5, TypeList<P6, TypeList<P7>>>>>>>>&
|
||||
tvl)
|
||||
{
|
||||
return new (mem) T(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T, class P1, class P2, class P3, class P4, class P5, class P6, class P7, class P8>
|
||||
struct Constructor<
|
||||
T,
|
||||
TypeList<
|
||||
P1,
|
||||
TypeList<
|
||||
P2,
|
||||
TypeList<P3, TypeList<P4, TypeList<P5, TypeList<P6, TypeList<P7, TypeList<P8>>>>>>>>>
|
||||
{
|
||||
static T*
|
||||
call(const TypeListValues<TypeList<
|
||||
P1,
|
||||
TypeList<
|
||||
P2,
|
||||
TypeList<P3,
|
||||
TypeList<P4, TypeList<P5, TypeList<P6, TypeList<P7, TypeList<P8>>>>>>>>>&
|
||||
tvl)
|
||||
{
|
||||
return new T(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
static T*
|
||||
call(void* mem,
|
||||
const TypeListValues<TypeList<
|
||||
P1,
|
||||
TypeList<
|
||||
P2,
|
||||
TypeList<P3,
|
||||
TypeList<P4, TypeList<P5, TypeList<P6, TypeList<P7, TypeList<P8>>>>>>>>>&
|
||||
tvl)
|
||||
{
|
||||
return new (mem) T(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
} // namespace luabridge
|
||||
435
csgo2/LuaBridge/luaBridge/detail/FuncTraits.h
Normal file
435
csgo2/LuaBridge/luaBridge/detail/FuncTraits.h
Normal file
@@ -0,0 +1,435 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2020, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Config.h>
|
||||
#include <LuaBridge/detail/TypeList.h>
|
||||
|
||||
#include <functional>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
namespace detail {
|
||||
|
||||
/**
|
||||
Since the throw specification is part of a function signature, the FuncTraits
|
||||
family of templates needs to be specialized for both types. The
|
||||
LUABRIDGE_THROWSPEC macro controls whether we use the 'throw ()' form, or
|
||||
'noexcept' (if C++11 is available) to distinguish the functions.
|
||||
*/
|
||||
#if defined(__APPLE_CPP__) || defined(__APPLE_CC__) || defined(__clang__) || defined(__GNUC__) || \
|
||||
(defined(_MSC_VER) && (_MSC_VER >= 1700))
|
||||
// Do not define LUABRIDGE_THROWSPEC since the Xcode and gcc compilers do not
|
||||
// distinguish the throw specification in the function signature.
|
||||
#define LUABRIDGE_THROWSPEC
|
||||
#else
|
||||
// Visual Studio 10 and earlier pay too much mind to useless throw () spec.
|
||||
//
|
||||
#define LUABRIDGE_THROWSPEC throw()
|
||||
#endif
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
* Traits class for unrolling the type list values into function arguments.
|
||||
*/
|
||||
template<class ReturnType, size_t NUM_PARAMS>
|
||||
struct Caller;
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 0>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>&)
|
||||
{
|
||||
return fn();
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>&)
|
||||
{
|
||||
return (obj->*fn)();
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 1>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 2>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd, tvl.tl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd, tvl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 3>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 4>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd, tvl.tl.tl.tl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd, tvl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 5>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd, tvl.tl.tl.tl.hd, tvl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd, tvl.tl.hd, tvl.tl.tl.hd, tvl.tl.tl.tl.hd, tvl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 6>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 7>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 8>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType>
|
||||
struct Caller<ReturnType, 9>
|
||||
{
|
||||
template<class Fn, class Params>
|
||||
static ReturnType f(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return fn(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
|
||||
template<class T, class MemFn, class Params>
|
||||
static ReturnType f(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return (obj->*fn)(tvl.hd,
|
||||
tvl.tl.hd,
|
||||
tvl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.tl.hd,
|
||||
tvl.tl.tl.tl.tl.tl.tl.tl.tl.hd);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType, class Fn, class Params>
|
||||
ReturnType doCall(Fn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return Caller<ReturnType, TypeListSize<Params>::value>::f(fn, tvl);
|
||||
}
|
||||
|
||||
template<class ReturnType, class T, class MemFn, class Params>
|
||||
ReturnType doCall(T* obj, MemFn& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return Caller<ReturnType, TypeListSize<Params>::value>::f(obj, fn, tvl);
|
||||
}
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
Traits for function pointers.
|
||||
|
||||
There are three types of functions: global, non-const member, and const
|
||||
member. These templates determine the type of function, which class type it
|
||||
belongs to if it is a class member, the const-ness if it is a member
|
||||
function, and the type information for the return value and argument list.
|
||||
|
||||
Expansions are provided for functions with up to 8 parameters. This can be
|
||||
manually extended, or expanded to an arbitrary amount using C++11 features.
|
||||
*/
|
||||
template<class MemFn, class D = MemFn>
|
||||
struct FuncTraits
|
||||
{
|
||||
};
|
||||
|
||||
/* Ordinary function pointers. */
|
||||
|
||||
template<class R, class... ParamList>
|
||||
struct FuncTraits<R (*)(ParamList...)>
|
||||
{
|
||||
static bool const isMemberFunction = false;
|
||||
using DeclType = R (*)(ParamList...);
|
||||
using ReturnType = R;
|
||||
using Params = typename MakeTypeList<ParamList...>::Result;
|
||||
|
||||
static R call(const DeclType& fp, TypeListValues<Params>& tvl) { return doCall<R>(fp, tvl); }
|
||||
};
|
||||
|
||||
/* Windows: WINAPI (a.k.a. __stdcall) function pointers. */
|
||||
|
||||
#ifdef _M_IX86 // Windows 32bit only
|
||||
|
||||
template<class R, class... ParamList>
|
||||
struct FuncTraits<R(__stdcall*)(ParamList...)>
|
||||
{
|
||||
static bool const isMemberFunction = false;
|
||||
using DeclType = R(__stdcall*)(ParamList...);
|
||||
using ReturnType = R;
|
||||
using Params = typename MakeTypeList<ParamList...>::Result;
|
||||
|
||||
static R call(const DeclType& fp, TypeListValues<Params>& tvl) { return doCall<R>(fp, tvl); }
|
||||
};
|
||||
|
||||
#endif // _M_IX86
|
||||
|
||||
/* Non-const member function pointers. */
|
||||
|
||||
template<class T, class R, class... ParamList>
|
||||
struct FuncTraits<R (T::*)(ParamList...)>
|
||||
{
|
||||
static bool const isMemberFunction = true;
|
||||
static bool const isConstMemberFunction = false;
|
||||
using DeclType = R (T::*)(ParamList...);
|
||||
using ClassType = T;
|
||||
using ReturnType = R;
|
||||
using Params = typename MakeTypeList<ParamList...>::Result;
|
||||
|
||||
static R call(ClassType* obj, const DeclType& fp, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return doCall<R>(obj, fp, tvl);
|
||||
}
|
||||
};
|
||||
|
||||
/* Const member function pointers. */
|
||||
|
||||
template<class T, class R, class... ParamList>
|
||||
struct FuncTraits<R (T::*)(ParamList...) const>
|
||||
{
|
||||
static bool const isMemberFunction = true;
|
||||
static bool const isConstMemberFunction = true;
|
||||
using DeclType = R (T::*)(ParamList...) const;
|
||||
using ClassType = T;
|
||||
using ReturnType = R;
|
||||
using Params = typename MakeTypeList<ParamList...>::Result;
|
||||
|
||||
static R call(const ClassType* obj, const DeclType& fp, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return doCall<R>(obj, fp, tvl);
|
||||
}
|
||||
};
|
||||
|
||||
/* std::function */
|
||||
|
||||
template<class R, class... ParamList>
|
||||
struct FuncTraits<std::function<R(ParamList...)>>
|
||||
{
|
||||
static bool const isMemberFunction = false;
|
||||
static bool const isConstMemberFunction = false;
|
||||
using DeclType = std::function<R(ParamList...)>;
|
||||
using ReturnType = R;
|
||||
using Params = typename MakeTypeList<ParamList...>::Result;
|
||||
|
||||
static ReturnType call(DeclType& fn, TypeListValues<Params>& tvl)
|
||||
{
|
||||
return doCall<ReturnType>(fn, tvl);
|
||||
}
|
||||
};
|
||||
|
||||
template<class ReturnType, class Params, int startParam>
|
||||
struct Invoke
|
||||
{
|
||||
template<class Fn>
|
||||
static int run(lua_State* L, Fn& fn)
|
||||
{
|
||||
try
|
||||
{
|
||||
ArgList<Params, startParam> args(L);
|
||||
Stack<ReturnType>::push(L, FuncTraits<Fn>::call(fn, args));
|
||||
return 1;
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
return luaL_error(L, e.what());
|
||||
}
|
||||
}
|
||||
|
||||
template<class T, class MemFn>
|
||||
static int run(lua_State* L, T* object, const MemFn& fn)
|
||||
{
|
||||
try
|
||||
{
|
||||
ArgList<Params, startParam> args(L);
|
||||
Stack<ReturnType>::push(L, FuncTraits<MemFn>::call(object, fn, args));
|
||||
return 1;
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
return luaL_error(L, e.what());
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
template<class Params, int startParam>
|
||||
struct Invoke<void, Params, startParam>
|
||||
{
|
||||
template<class Fn>
|
||||
static int run(lua_State* L, Fn& fn)
|
||||
{
|
||||
try
|
||||
{
|
||||
ArgList<Params, startParam> args(L);
|
||||
FuncTraits<Fn>::call(fn, args);
|
||||
return 0;
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
return luaL_error(L, e.what());
|
||||
}
|
||||
}
|
||||
|
||||
template<class T, class MemFn>
|
||||
static int run(lua_State* L, T* object, const MemFn& fn)
|
||||
{
|
||||
try
|
||||
{
|
||||
ArgList<Params, startParam> args(L);
|
||||
FuncTraits<MemFn>::call(object, fn, args);
|
||||
return 0;
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
return luaL_error(L, e.what());
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
} // namespace luabridge
|
||||
150
csgo2/LuaBridge/luaBridge/detail/Iterator.h
Normal file
150
csgo2/LuaBridge/luaBridge/detail/Iterator.h
Normal file
@@ -0,0 +1,150 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2018, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/LuaRef.h>
|
||||
|
||||
#include <utility>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
/** Allows table iteration.
|
||||
*/
|
||||
class Iterator
|
||||
{
|
||||
lua_State* m_L;
|
||||
LuaRef m_table;
|
||||
LuaRef m_key;
|
||||
LuaRef m_value;
|
||||
|
||||
void next()
|
||||
{
|
||||
m_table.push();
|
||||
m_key.push();
|
||||
if (lua_next(m_L, -2))
|
||||
{
|
||||
m_value.pop();
|
||||
m_key.pop();
|
||||
}
|
||||
else
|
||||
{
|
||||
m_key = Nil();
|
||||
m_value = Nil();
|
||||
}
|
||||
lua_pop(m_L, 1);
|
||||
}
|
||||
|
||||
public:
|
||||
explicit Iterator(const LuaRef& table, bool isEnd = false)
|
||||
: m_L(table.state())
|
||||
, m_table(table)
|
||||
, m_key(table.state()) // m_key is nil
|
||||
, m_value(table.state()) // m_value is nil
|
||||
{
|
||||
if (!isEnd)
|
||||
{
|
||||
next(); // get the first (key, value) pair from table
|
||||
}
|
||||
}
|
||||
|
||||
/// Return an associated Lua state.
|
||||
///
|
||||
/// @returns A Lua state.
|
||||
///
|
||||
lua_State* state() const { return m_L; }
|
||||
|
||||
/// Dereference the iterator.
|
||||
///
|
||||
/// @returns A key-value pair for a current table entry.
|
||||
///
|
||||
std::pair<LuaRef, LuaRef> operator*() const { return std::make_pair(m_key, m_value); }
|
||||
|
||||
/// Return the value referred by the iterator.
|
||||
///
|
||||
/// @returns A value for the current table entry.
|
||||
///
|
||||
LuaRef operator->() const { return m_value; }
|
||||
|
||||
/// Compare two iterators.
|
||||
///
|
||||
/// @param rhs Another iterator.
|
||||
/// @returns True if iterators point to the same entry of the same table,
|
||||
/// false otherwise.
|
||||
///
|
||||
bool operator!=(const Iterator& rhs) const
|
||||
{
|
||||
assert(m_L == rhs.m_L);
|
||||
return !m_table.rawequal(rhs.m_table) || !m_key.rawequal(rhs.m_key);
|
||||
}
|
||||
|
||||
/// Move the iterator to the next table entry.
|
||||
///
|
||||
/// @returns This iterator.
|
||||
///
|
||||
Iterator& operator++()
|
||||
{
|
||||
if (isNil())
|
||||
{
|
||||
// if the iterator reaches the end, do nothing
|
||||
return *this;
|
||||
}
|
||||
else
|
||||
{
|
||||
next();
|
||||
return *this;
|
||||
}
|
||||
}
|
||||
|
||||
/// Check if the iterator points after the last table entry.
|
||||
///
|
||||
/// @returns True if there are no more table entries to iterate,
|
||||
/// false otherwise.
|
||||
///
|
||||
bool isNil() const { return m_key.isNil(); }
|
||||
|
||||
/// Return the key for the current table entry.
|
||||
///
|
||||
/// @returns A reference to the entry key.
|
||||
///
|
||||
LuaRef key() const { return m_key; }
|
||||
|
||||
/// Return the key for the current table entry.
|
||||
///
|
||||
/// @returns A reference to the entry value.
|
||||
///
|
||||
LuaRef value() const { return m_value; }
|
||||
|
||||
private:
|
||||
// Don't use postfix increment, it is less efficient
|
||||
Iterator operator++(int);
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
class Range
|
||||
{
|
||||
Iterator m_begin;
|
||||
Iterator m_end;
|
||||
|
||||
public:
|
||||
Range(const Iterator& begin, const Iterator& end) : m_begin(begin), m_end(end) {}
|
||||
|
||||
const Iterator& begin() const { return m_begin; }
|
||||
const Iterator& end() const { return m_end; }
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
/// Return a range for the Lua table reference.
|
||||
///
|
||||
/// @returns A range suitable for range-based for statement.
|
||||
///
|
||||
inline detail::Range pairs(const LuaRef& table)
|
||||
{
|
||||
return detail::Range(Iterator(table, false), Iterator(table, true));
|
||||
}
|
||||
|
||||
} // namespace luabridge
|
||||
104
csgo2/LuaBridge/luaBridge/detail/LuaException.h
Normal file
104
csgo2/LuaBridge/luaBridge/detail/LuaException.h
Normal file
@@ -0,0 +1,104 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2008, Nigel Atkinson <suprapilot+LuaCode@gmail.com>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <exception>
|
||||
#include <string>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
class LuaException : public std::exception
|
||||
{
|
||||
private:
|
||||
lua_State* m_L;
|
||||
std::string m_what;
|
||||
|
||||
public:
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
Construct a LuaException after a lua_pcall().
|
||||
*/
|
||||
LuaException(lua_State* L, int /*code*/) : m_L(L) { whatFromStack(); }
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
LuaException(lua_State* L, char const*, char const*, long) : m_L(L) { whatFromStack(); }
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
~LuaException() throw() {}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
char const* what() const throw() { return m_what.c_str(); }
|
||||
|
||||
//============================================================================
|
||||
/**
|
||||
Throw an exception.
|
||||
|
||||
This centralizes all the exceptions thrown, so that we can set
|
||||
breakpoints before the stack is unwound, or otherwise customize the
|
||||
behavior.
|
||||
*/
|
||||
template<class Exception>
|
||||
static void Throw(Exception e)
|
||||
{
|
||||
throw e;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
Wrapper for lua_pcall that throws.
|
||||
*/
|
||||
static void pcall(lua_State* L, int nargs = 0, int nresults = 0, int msgh = 0)
|
||||
{
|
||||
int code = lua_pcall(L, nargs, nresults, msgh);
|
||||
|
||||
if (code != LUABRIDGE_LUA_OK)
|
||||
Throw(LuaException(L, code));
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
Initializes error handling. Subsequent Lua errors are translated to C++ exceptions.
|
||||
*/
|
||||
static void enableExceptions(lua_State* L) { lua_atpanic(L, throwAtPanic); }
|
||||
|
||||
/** Retrieve the lua_State associated with the exception.
|
||||
|
||||
@returns A Lua state.
|
||||
*/
|
||||
lua_State* state() const { return m_L; }
|
||||
|
||||
protected:
|
||||
void whatFromStack()
|
||||
{
|
||||
if (lua_gettop(m_L) > 0)
|
||||
{
|
||||
char const* s = lua_tostring(m_L, -1);
|
||||
m_what = s ? s : "";
|
||||
}
|
||||
else
|
||||
{
|
||||
// stack is empty
|
||||
m_what = "missing error";
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
static int throwAtPanic(lua_State* L) { throw LuaException(L, -1); }
|
||||
};
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
Initializes error handling. Subsequent Lua errors are translated to C++ exceptions.
|
||||
*/
|
||||
static void enableExceptions(lua_State* L)
|
||||
{
|
||||
LuaException::enableExceptions(L);
|
||||
}
|
||||
|
||||
} // namespace luabridge
|
||||
126
csgo2/LuaBridge/luaBridge/detail/LuaHelpers.h
Normal file
126
csgo2/LuaBridge/luaBridge/detail/LuaHelpers.h
Normal file
@@ -0,0 +1,126 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2007, Nathan Reed
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <cassert>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
// These are for Lua versions prior to 5.2.0.
|
||||
//
|
||||
#if LUA_VERSION_NUM < 502
|
||||
inline int lua_absindex(lua_State* L, int idx)
|
||||
{
|
||||
if (idx > LUA_REGISTRYINDEX && idx < 0)
|
||||
return lua_gettop(L) + idx + 1;
|
||||
else
|
||||
return idx;
|
||||
}
|
||||
|
||||
inline void lua_rawgetp(lua_State* L, int idx, void const* p)
|
||||
{
|
||||
idx = lua_absindex(L, idx);
|
||||
lua_pushlightuserdata(L, const_cast<void*>(p));
|
||||
lua_rawget(L, idx);
|
||||
}
|
||||
|
||||
inline void lua_rawsetp(lua_State* L, int idx, void const* p)
|
||||
{
|
||||
idx = lua_absindex(L, idx);
|
||||
lua_pushlightuserdata(L, const_cast<void*>(p));
|
||||
// put key behind value
|
||||
lua_insert(L, -2);
|
||||
lua_rawset(L, idx);
|
||||
}
|
||||
|
||||
#define LUA_OPEQ 1
|
||||
#define LUA_OPLT 2
|
||||
#define LUA_OPLE 3
|
||||
|
||||
inline int lua_compare(lua_State* L, int idx1, int idx2, int op)
|
||||
{
|
||||
switch (op)
|
||||
{
|
||||
case LUA_OPEQ:
|
||||
return lua_equal(L, idx1, idx2);
|
||||
break;
|
||||
|
||||
case LUA_OPLT:
|
||||
return lua_lessthan(L, idx1, idx2);
|
||||
break;
|
||||
|
||||
case LUA_OPLE:
|
||||
return lua_equal(L, idx1, idx2) || lua_lessthan(L, idx1, idx2);
|
||||
break;
|
||||
|
||||
default:
|
||||
return 0;
|
||||
};
|
||||
}
|
||||
|
||||
inline int get_length(lua_State* L, int idx)
|
||||
{
|
||||
return int(lua_objlen(L, idx));
|
||||
}
|
||||
|
||||
#else
|
||||
inline int get_length(lua_State* L, int idx)
|
||||
{
|
||||
lua_len(L, idx);
|
||||
int len = int(luaL_checknumber(L, -1));
|
||||
lua_pop(L, 1);
|
||||
return len;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef LUA_OK
|
||||
#define LUABRIDGE_LUA_OK 0
|
||||
#else
|
||||
#define LUABRIDGE_LUA_OK LUA_OK
|
||||
#endif
|
||||
|
||||
/** Get a table value, bypassing metamethods.
|
||||
*/
|
||||
inline void rawgetfield(lua_State* L, int index, char const* key)
|
||||
{
|
||||
assert(lua_istable(L, index));
|
||||
index = lua_absindex(L, index);
|
||||
lua_pushstring(L, key);
|
||||
lua_rawget(L, index);
|
||||
}
|
||||
|
||||
/** Set a table value, bypassing metamethods.
|
||||
*/
|
||||
inline void rawsetfield(lua_State* L, int index, char const* key)
|
||||
{
|
||||
assert(lua_istable(L, index));
|
||||
index = lua_absindex(L, index);
|
||||
lua_pushstring(L, key);
|
||||
lua_insert(L, -2);
|
||||
lua_rawset(L, index);
|
||||
}
|
||||
|
||||
/** Returns true if the value is a full userdata (not light).
|
||||
*/
|
||||
inline bool isfulluserdata(lua_State* L, int index)
|
||||
{
|
||||
return lua_isuserdata(L, index) && !lua_islightuserdata(L, index);
|
||||
}
|
||||
|
||||
/** Test lua_State objects for global equality.
|
||||
|
||||
This can determine if two different lua_State objects really point
|
||||
to the same global state, such as when using coroutines.
|
||||
|
||||
@note This is used for assertions.
|
||||
*/
|
||||
inline bool equalstates(lua_State* L1, lua_State* L2)
|
||||
{
|
||||
return lua_topointer(L1, LUA_REGISTRYINDEX) == lua_topointer(L2, LUA_REGISTRYINDEX);
|
||||
}
|
||||
|
||||
} // namespace luabridge
|
||||
1012
csgo2/LuaBridge/luaBridge/detail/LuaRef.h
Normal file
1012
csgo2/LuaBridge/luaBridge/detail/LuaRef.h
Normal file
File diff suppressed because it is too large
Load Diff
1395
csgo2/LuaBridge/luaBridge/detail/Namespace.h
Normal file
1395
csgo2/LuaBridge/luaBridge/detail/Namespace.h
Normal file
File diff suppressed because it is too large
Load Diff
58
csgo2/LuaBridge/luaBridge/detail/Security.h
Normal file
58
csgo2/LuaBridge/luaBridge/detail/Security.h
Normal file
@@ -0,0 +1,58 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
security options.
|
||||
*/
|
||||
class Security
|
||||
{
|
||||
public:
|
||||
static bool hideMetatables() { return getSettings().hideMetatables; }
|
||||
|
||||
static void setHideMetatables(bool shouldHide) { getSettings().hideMetatables = shouldHide; }
|
||||
|
||||
private:
|
||||
struct Settings
|
||||
{
|
||||
Settings() : hideMetatables(true) {}
|
||||
|
||||
bool hideMetatables;
|
||||
};
|
||||
|
||||
static Settings& getSettings()
|
||||
{
|
||||
static Settings settings;
|
||||
return settings;
|
||||
}
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Set a global value in the lua_State.
|
||||
|
||||
@note This works on any type specialized by `Stack`, including `LuaRef` and
|
||||
its table proxies.
|
||||
*/
|
||||
template<class T>
|
||||
inline void setGlobal(lua_State* L, T t, char const* name)
|
||||
{
|
||||
push(L, t);
|
||||
lua_setglobal(L, name);
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Change whether or not metatables are hidden (on by default).
|
||||
*/
|
||||
inline void setHideMetatables(bool shouldHide)
|
||||
{
|
||||
Security::setHideMetatables(shouldHide);
|
||||
}
|
||||
|
||||
} // namespace luabridge
|
||||
535
csgo2/LuaBridge/luaBridge/detail/Stack.h
Normal file
535
csgo2/LuaBridge/luaBridge/detail/Stack.h
Normal file
@@ -0,0 +1,535 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2019, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2007, Nathan Reed
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/LuaHelpers.h>
|
||||
#include <LuaBridge/detail/Userdata.h>
|
||||
|
||||
#include <string>
|
||||
#ifdef LUABRIDGE_CXX17
|
||||
#include <string_view>
|
||||
#endif
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
/// Lua stack traits for C++ types.
|
||||
///
|
||||
/// @tparam T A C++ type.
|
||||
///
|
||||
template<class T>
|
||||
struct Stack;
|
||||
|
||||
template<>
|
||||
struct Stack<void>
|
||||
{
|
||||
static void push(lua_State*) {}
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Receive the lua_State* as an argument.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<lua_State*>
|
||||
{
|
||||
static lua_State* get(lua_State* L, int) { return L; }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for a lua_CFunction.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<lua_CFunction>
|
||||
{
|
||||
static void push(lua_State* L, lua_CFunction f) { lua_pushcfunction(L, f); }
|
||||
|
||||
static lua_CFunction get(lua_State* L, int index) { return lua_tocfunction(L, index); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_iscfunction(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `int`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<int>
|
||||
{
|
||||
static void push(lua_State* L, int value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
|
||||
static int get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<int>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index)
|
||||
{
|
||||
if (lua_type(L, index) != LUA_TNUMBER)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
#if LUA_VERSION_NUM <= 501
|
||||
return true;
|
||||
#else
|
||||
int isNumber;
|
||||
lua_tointegerx(L, index, &isNumber);
|
||||
return isNumber;
|
||||
#endif
|
||||
}
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `unsigned int`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<unsigned int>
|
||||
{
|
||||
static void push(lua_State* L, unsigned int value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
|
||||
static unsigned int get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<unsigned int>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<int>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `unsigned char`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<unsigned char>
|
||||
{
|
||||
static void push(lua_State* L, unsigned char value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
|
||||
static unsigned char get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<unsigned char>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<int>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `short`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<short>
|
||||
{
|
||||
static void push(lua_State* L, short value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
|
||||
static short get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<short>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<int>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `unsigned short`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<unsigned short>
|
||||
{
|
||||
static void push(lua_State* L, unsigned short value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
|
||||
static unsigned short get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<unsigned short>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<int>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `long`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<long>
|
||||
{
|
||||
static void push(lua_State* L, long value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
|
||||
static long get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<long>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<int>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `unsigned long`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<unsigned long>
|
||||
{
|
||||
static void push(lua_State* L, unsigned long value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
|
||||
static unsigned long get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<unsigned long>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<int>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
* Stack specialization for `long long`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<long long>
|
||||
{
|
||||
static void push(lua_State* L, long long value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
|
||||
static long long get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<long long>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<int>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
* Stack specialization for `unsigned long long`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<unsigned long long>
|
||||
{
|
||||
static void push(lua_State* L, unsigned long long value)
|
||||
{
|
||||
lua_pushinteger(L, static_cast<lua_Integer>(value));
|
||||
}
|
||||
static unsigned long long get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<unsigned long long>(luaL_checkinteger(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<int>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `float`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<float>
|
||||
{
|
||||
static void push(lua_State* L, float value)
|
||||
{
|
||||
lua_pushnumber(L, static_cast<lua_Number>(value));
|
||||
}
|
||||
|
||||
static float get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<float>(luaL_checknumber(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_type(L, index) == LUA_TNUMBER; }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `double`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<double>
|
||||
{
|
||||
static void push(lua_State* L, double value)
|
||||
{
|
||||
lua_pushnumber(L, static_cast<lua_Number>(value));
|
||||
}
|
||||
|
||||
static double get(lua_State* L, int index)
|
||||
{
|
||||
return static_cast<double>(luaL_checknumber(L, index));
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_type(L, index) == LUA_TNUMBER; }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `bool`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<bool>
|
||||
{
|
||||
static void push(lua_State* L, bool value) { lua_pushboolean(L, value ? 1 : 0); }
|
||||
|
||||
static bool get(lua_State* L, int index) { return lua_toboolean(L, index) ? true : false; }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_isboolean(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `char`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<char>
|
||||
{
|
||||
static void push(lua_State* L, char value) { lua_pushlstring(L, &value, 1); }
|
||||
|
||||
static char get(lua_State* L, int index) { return luaL_checkstring(L, index)[0]; }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_type(L, index) == LUA_TSTRING; }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `const char*`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<char const*>
|
||||
{
|
||||
static void push(lua_State* L, char const* str)
|
||||
{
|
||||
if (str != 0)
|
||||
lua_pushstring(L, str);
|
||||
else
|
||||
lua_pushnil(L);
|
||||
}
|
||||
|
||||
static char const* get(lua_State* L, int index)
|
||||
{
|
||||
return lua_isnil(L, index) ? 0 : luaL_checkstring(L, index);
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index)
|
||||
{
|
||||
return lua_isnil(L, index) || lua_type(L, index) == LUA_TSTRING;
|
||||
}
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `std::string`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<std::string>
|
||||
{
|
||||
static void push(lua_State* L, std::string const& str)
|
||||
{
|
||||
lua_pushlstring(L, str.data(), str.size());
|
||||
}
|
||||
|
||||
static std::string get(lua_State* L, int index)
|
||||
{
|
||||
size_t len;
|
||||
if (lua_type(L, index) == LUA_TSTRING)
|
||||
{
|
||||
const char* str = lua_tolstring(L, index, &len);
|
||||
return std::string(str, len);
|
||||
}
|
||||
|
||||
// Lua reference manual:
|
||||
// If the value is a number, then lua_tolstring also changes the actual value in the stack
|
||||
// to a string. (This change confuses lua_next when lua_tolstring is applied to keys during
|
||||
// a table traversal.)
|
||||
lua_pushvalue(L, index);
|
||||
const char* str = lua_tolstring(L, -1, &len);
|
||||
std::string string(str, len);
|
||||
lua_pop(L, 1); // Pop the temporary string
|
||||
return string;
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_type(L, index) == LUA_TSTRING; }
|
||||
};
|
||||
|
||||
#ifdef LUABRIDGE_CXX17
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Stack specialization for `std::string`.
|
||||
*/
|
||||
template<>
|
||||
struct Stack<std::string_view>
|
||||
{
|
||||
static void push(lua_State* L, std::string_view str)
|
||||
{
|
||||
lua_pushlstring(L, str.data(), str.size());
|
||||
}
|
||||
|
||||
static std::string_view get(lua_State* L, int index)
|
||||
{
|
||||
size_t len;
|
||||
if (lua_type(L, index) == LUA_TSTRING)
|
||||
{
|
||||
const char* str = lua_tolstring(L, index, &len);
|
||||
return std::string_view(str, len);
|
||||
}
|
||||
|
||||
return {};
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return lua_type(L, index) == LUA_TSTRING; }
|
||||
};
|
||||
|
||||
#endif // LUABRIDGE_CXX17
|
||||
|
||||
namespace detail {
|
||||
|
||||
template<class T>
|
||||
struct StackOpSelector<T&, false>
|
||||
{
|
||||
typedef T ReturnType;
|
||||
|
||||
static void push(lua_State* L, T& value) { Stack<T>::push(L, value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Stack<T>::get(L, index); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<T>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct StackOpSelector<const T&, false>
|
||||
{
|
||||
typedef T ReturnType;
|
||||
|
||||
static void push(lua_State* L, const T& value) { Stack<T>::push(L, value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Stack<T>::get(L, index); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<T>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct StackOpSelector<T*, false>
|
||||
{
|
||||
typedef T ReturnType;
|
||||
|
||||
static void push(lua_State* L, T* value) { Stack<T>::push(L, *value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Stack<T>::get(L, index); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<T>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct StackOpSelector<const T*, false>
|
||||
{
|
||||
typedef T ReturnType;
|
||||
|
||||
static void push(lua_State* L, const T* value) { Stack<T>::push(L, *value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Stack<T>::get(L, index); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Stack<T>::isInstance(L, index); }
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
template<class T>
|
||||
struct Stack<T&>
|
||||
{
|
||||
typedef detail::StackOpSelector<T&, detail::IsUserdata<T>::value> Helper;
|
||||
typedef typename Helper::ReturnType ReturnType;
|
||||
|
||||
static void push(lua_State* L, T& value) { Helper::push(L, value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Helper::get(L, index); }
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct Stack<const T&>
|
||||
{
|
||||
typedef detail::StackOpSelector<const T&, detail::IsUserdata<T>::value> Helper;
|
||||
typedef typename Helper::ReturnType ReturnType;
|
||||
|
||||
static void push(lua_State* L, const T& value) { Helper::push(L, value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Helper::get(L, index); }
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct Stack<T*>
|
||||
{
|
||||
typedef detail::StackOpSelector<T*, detail::IsUserdata<T>::value> Helper;
|
||||
typedef typename Helper::ReturnType ReturnType;
|
||||
|
||||
static void push(lua_State* L, T* value) { Helper::push(L, value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Helper::get(L, index); }
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct Stack<const T*>
|
||||
{
|
||||
typedef detail::StackOpSelector<const T*, detail::IsUserdata<T>::value> Helper;
|
||||
typedef typename Helper::ReturnType ReturnType;
|
||||
|
||||
static void push(lua_State* L, const T* value) { Helper::push(L, value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Helper::get(L, index); }
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
* Push an object onto the Lua stack.
|
||||
*/
|
||||
template<class T>
|
||||
void push(lua_State* L, T t)
|
||||
{
|
||||
Stack<T>::push(L, t);
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
* Get an object from the Lua stack.
|
||||
*/
|
||||
template<class T>
|
||||
T get(lua_State* L, int index)
|
||||
{
|
||||
return Stack<T>::get(L, index);
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
* Check whether an object on the Lua stack is of type T.
|
||||
*/
|
||||
template<class T>
|
||||
bool isInstance(lua_State* L, int index)
|
||||
{
|
||||
return Stack<T>::isInstance(L, index);
|
||||
}
|
||||
|
||||
} // namespace luabridge
|
||||
183
csgo2/LuaBridge/luaBridge/detail/TypeList.h
Normal file
183
csgo2/LuaBridge/luaBridge/detail/TypeList.h
Normal file
@@ -0,0 +1,183 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2007, Nathan Reed
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
//==============================================================================
|
||||
/*
|
||||
This file incorporates work covered by the following copyright and
|
||||
permission notice:
|
||||
|
||||
The Loki Library
|
||||
Copyright (c) 2001 by Andrei Alexandrescu
|
||||
This code accompanies the book:
|
||||
Alexandrescu, Andrei. "Modern C++ Design: Generic Programming and Design
|
||||
Patterns Applied". Copyright (c) 2001. Addison-Wesley.
|
||||
Permission to use, copy, modify, distribute and sell this software for any
|
||||
purpose is hereby granted without fee, provided that the above copyright
|
||||
notice appear in all copies and that both that copyright notice and this
|
||||
permission notice appear in supporting documentation.
|
||||
The author or Addison-Welsey Longman make no representations about the
|
||||
suitability of this software for any purpose. It is provided "as is"
|
||||
without express or implied warranty.
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Config.h>
|
||||
#include <LuaBridge/detail/Stack.h>
|
||||
|
||||
#include <string>
|
||||
#include <typeinfo>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
namespace detail {
|
||||
|
||||
/**
|
||||
None type means void parameters or return value.
|
||||
*/
|
||||
typedef void None;
|
||||
|
||||
template<typename Head, typename Tail = None>
|
||||
struct TypeList
|
||||
{
|
||||
typedef Tail TailType;
|
||||
};
|
||||
|
||||
template<class List>
|
||||
struct TypeListSize
|
||||
{
|
||||
static const size_t value = TypeListSize<typename List::TailType>::value + 1;
|
||||
};
|
||||
|
||||
template<>
|
||||
struct TypeListSize<None>
|
||||
{
|
||||
static const size_t value = 0;
|
||||
};
|
||||
|
||||
template<class... Params>
|
||||
struct MakeTypeList;
|
||||
|
||||
template<class Param, class... Params>
|
||||
struct MakeTypeList<Param, Params...>
|
||||
{
|
||||
using Result = TypeList<Param, typename MakeTypeList<Params...>::Result>;
|
||||
};
|
||||
|
||||
template<>
|
||||
struct MakeTypeList<>
|
||||
{
|
||||
using Result = None;
|
||||
};
|
||||
|
||||
/**
|
||||
A TypeList with actual values.
|
||||
*/
|
||||
template<typename List>
|
||||
struct TypeListValues
|
||||
{
|
||||
static std::string const tostring(bool) { return ""; }
|
||||
};
|
||||
|
||||
/**
|
||||
TypeListValues recursive template definition.
|
||||
*/
|
||||
template<typename Head, typename Tail>
|
||||
struct TypeListValues<TypeList<Head, Tail>>
|
||||
{
|
||||
Head hd;
|
||||
TypeListValues<Tail> tl;
|
||||
|
||||
TypeListValues(Head hd_, TypeListValues<Tail> const& tl_) : hd(hd_), tl(tl_) {}
|
||||
|
||||
static std::string tostring(bool comma = false)
|
||||
{
|
||||
std::string s;
|
||||
|
||||
if (comma)
|
||||
s = ", ";
|
||||
|
||||
s = s + typeid(Head).name();
|
||||
|
||||
return s + TypeListValues<Tail>::tostring(true);
|
||||
}
|
||||
};
|
||||
|
||||
// Specializations of type/value list for head types that are references and
|
||||
// const-references. We need to handle these specially since we can't count
|
||||
// on the referenced object hanging around for the lifetime of the list.
|
||||
|
||||
template<typename Head, typename Tail>
|
||||
struct TypeListValues<TypeList<Head&, Tail>>
|
||||
{
|
||||
Head hd;
|
||||
TypeListValues<Tail> tl;
|
||||
|
||||
TypeListValues(Head& hd_, TypeListValues<Tail> const& tl_) : hd(hd_), tl(tl_) {}
|
||||
|
||||
static std::string const tostring(bool comma = false)
|
||||
{
|
||||
std::string s;
|
||||
|
||||
if (comma)
|
||||
s = ", ";
|
||||
|
||||
s = s + typeid(Head).name() + "&";
|
||||
|
||||
return s + TypeListValues<Tail>::tostring(true);
|
||||
}
|
||||
};
|
||||
|
||||
template<typename Head, typename Tail>
|
||||
struct TypeListValues<TypeList<Head const&, Tail>>
|
||||
{
|
||||
Head hd;
|
||||
TypeListValues<Tail> tl;
|
||||
|
||||
TypeListValues(Head const& hd_, const TypeListValues<Tail>& tl_) : hd(hd_), tl(tl_) {}
|
||||
|
||||
static std::string const tostring(bool comma = false)
|
||||
{
|
||||
std::string s;
|
||||
|
||||
if (comma)
|
||||
s = ", ";
|
||||
|
||||
s = s + typeid(Head).name() + " const&";
|
||||
|
||||
return s + TypeListValues<Tail>::tostring(true);
|
||||
}
|
||||
};
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
Subclass of a TypeListValues constructable from the Lua stack.
|
||||
*/
|
||||
|
||||
template<typename List, int Start = 1>
|
||||
struct ArgList
|
||||
{
|
||||
};
|
||||
|
||||
template<int Start>
|
||||
struct ArgList<None, Start> : public TypeListValues<None>
|
||||
{
|
||||
ArgList(lua_State*) {}
|
||||
};
|
||||
|
||||
template<typename Head, typename Tail, int Start>
|
||||
struct ArgList<TypeList<Head, Tail>, Start> : public TypeListValues<TypeList<Head, Tail>>
|
||||
{
|
||||
ArgList(lua_State* L)
|
||||
: TypeListValues<TypeList<Head, Tail>>(Stack<Head>::get(L, Start),
|
||||
ArgList<Tail, Start + 1>(L))
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
} // namespace luabridge
|
||||
112
csgo2/LuaBridge/luaBridge/detail/TypeTraits.h
Normal file
112
csgo2/LuaBridge/luaBridge/detail/TypeTraits.h
Normal file
@@ -0,0 +1,112 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2019, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/Config.h>
|
||||
|
||||
#include <string>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Container traits.
|
||||
|
||||
Unspecialized ContainerTraits has the isNotContainer typedef for SFINAE.
|
||||
All user defined containers must supply an appropriate specialization for
|
||||
ContinerTraits (without the typedef isNotContainer). The containers that
|
||||
come with LuaBridge also come with the appropriate ContainerTraits
|
||||
specialization. See the corresponding declaration for details.
|
||||
|
||||
A specialization of ContainerTraits for some generic type ContainerType
|
||||
looks like this:
|
||||
|
||||
template <class T>
|
||||
struct ContainerTraits <ContainerType <T>>
|
||||
{
|
||||
typedef typename T Type;
|
||||
|
||||
static T* get (ContainerType <T> const& c)
|
||||
{
|
||||
return c.get (); // Implementation-dependent on ContainerType
|
||||
}
|
||||
};
|
||||
*/
|
||||
template<class T>
|
||||
struct ContainerTraits
|
||||
{
|
||||
typedef bool isNotContainer;
|
||||
typedef T Type;
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Type traits.
|
||||
|
||||
Specializations return information about a type.
|
||||
*/
|
||||
struct TypeTraits
|
||||
{
|
||||
/** Determine if type T is a container.
|
||||
|
||||
To be considered a container, there must be a specialization of
|
||||
ContainerTraits with the required fields.
|
||||
*/
|
||||
template<typename T>
|
||||
class isContainer
|
||||
{
|
||||
private:
|
||||
typedef char yes[1]; // sizeof (yes) == 1
|
||||
typedef char no[2]; // sizeof (no) == 2
|
||||
|
||||
template<typename C>
|
||||
static no& test(typename C::isNotContainer*);
|
||||
|
||||
template<typename>
|
||||
static yes& test(...);
|
||||
|
||||
public:
|
||||
static const bool value = sizeof(test<ContainerTraits<T>>(0)) == sizeof(yes);
|
||||
};
|
||||
|
||||
/** Determine if T is const qualified.
|
||||
*/
|
||||
/** @{ */
|
||||
template<class T>
|
||||
struct isConst
|
||||
{
|
||||
static bool const value = false;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct isConst<T const>
|
||||
{
|
||||
static bool const value = true;
|
||||
};
|
||||
/** @} */
|
||||
|
||||
/** Remove the const qualifier from T.
|
||||
*/
|
||||
/** @{ */
|
||||
template<class T>
|
||||
struct removeConst
|
||||
{
|
||||
typedef T Type;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct removeConst<T const>
|
||||
{
|
||||
typedef T Type;
|
||||
};
|
||||
/**@}*/
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
} // namespace luabridge
|
||||
769
csgo2/LuaBridge/luaBridge/detail/Userdata.h
Normal file
769
csgo2/LuaBridge/luaBridge/detail/Userdata.h
Normal file
@@ -0,0 +1,769 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2019, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LuaBridge/detail/ClassInfo.h>
|
||||
#include <LuaBridge/detail/TypeTraits.h>
|
||||
|
||||
#include <cassert>
|
||||
#include <stdexcept>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
namespace detail {
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
Return the identity pointer for our lightuserdata tokens.
|
||||
|
||||
Because of Lua's dynamic typing and our improvised system of imposing C++
|
||||
class structure, there is the possibility that executing scripts may
|
||||
knowingly or unknowingly cause invalid data to get passed to the C functions
|
||||
created by LuaBridge. In particular, our security model addresses the
|
||||
following:
|
||||
1. Scripts cannot create a userdata (ignoring the debug lib).
|
||||
2. Scripts cannot create a lightuserdata (ignoring the debug lib).
|
||||
3. Scripts cannot set the metatable on a userdata.
|
||||
*/
|
||||
|
||||
/**
|
||||
Interface to a class pointer retrievable from a userdata.
|
||||
*/
|
||||
class Userdata
|
||||
{
|
||||
protected:
|
||||
void* m_p; // subclasses must set this
|
||||
|
||||
Userdata() : m_p(0) {}
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
Get an untyped pointer to the contained class.
|
||||
*/
|
||||
void* getPointer() { return m_p; }
|
||||
|
||||
private:
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
Validate and retrieve a Userdata on the stack.
|
||||
|
||||
The Userdata must exactly match the corresponding class table or
|
||||
const table, or else a Lua error is raised. This is used for the
|
||||
__gc metamethod.
|
||||
*/
|
||||
static Userdata* getExactClass(lua_State* L, int index, void const* /*classKey*/)
|
||||
{
|
||||
return static_cast<Userdata*>(lua_touserdata(L, lua_absindex(L, index)));
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
Validate and retrieve a Userdata on the stack.
|
||||
|
||||
The Userdata must be derived from or the same as the given base class,
|
||||
identified by the key. If canBeConst is false, generates an error if
|
||||
the resulting Userdata represents to a const object. We do the type check
|
||||
first so that the error message is informative.
|
||||
*/
|
||||
static Userdata* getClass(lua_State* L,
|
||||
int index,
|
||||
void const* registryConstKey,
|
||||
void const* registryClassKey,
|
||||
bool canBeConst)
|
||||
{
|
||||
index = lua_absindex(L, index);
|
||||
|
||||
lua_getmetatable(L, index); // Stack: object metatable (ot) | nil
|
||||
if (!lua_istable(L, -1))
|
||||
{
|
||||
lua_rawgetp(
|
||||
L, LUA_REGISTRYINDEX, registryClassKey); // Stack: registry metatable (rt) | nil
|
||||
return throwBadArg(L, index);
|
||||
}
|
||||
|
||||
lua_rawgetp(L, -1, getConstKey()); // Stack: ot | nil, const table (co) | nil
|
||||
assert(lua_istable(L, -1) || lua_isnil(L, -1));
|
||||
|
||||
// If const table is NOT present, object is const. Use non-const registry table
|
||||
// if object cannot be const, so constness validation is done automatically.
|
||||
// E.g. nonConstFn (constObj)
|
||||
// -> canBeConst = false, isConst = true
|
||||
// -> 'Class' registry table, 'const Class' object table
|
||||
// -> 'expected Class, got const Class'
|
||||
bool isConst = lua_isnil(L, -1); // Stack: ot | nil, nil, rt
|
||||
if (isConst && canBeConst)
|
||||
{
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, registryConstKey); // Stack: ot, nil, rt
|
||||
}
|
||||
else
|
||||
{
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, registryClassKey); // Stack: ot, co, rt
|
||||
}
|
||||
|
||||
lua_insert(L, -3); // Stack: rt, ot, co | nil
|
||||
lua_pop(L, 1); // Stack: rt, ot
|
||||
|
||||
for (;;)
|
||||
{
|
||||
if (lua_rawequal(L, -1, -2)) // Stack: rt, ot
|
||||
{
|
||||
lua_pop(L, 2); // Stack: -
|
||||
return static_cast<Userdata*>(lua_touserdata(L, index));
|
||||
}
|
||||
|
||||
// Replace current metatable with it's base class.
|
||||
lua_rawgetp(L, -1, getParentKey()); // Stack: rt, ot, parent ot (pot) | nil
|
||||
|
||||
if (lua_isnil(L, -1)) // Stack: rt, ot, nil
|
||||
{
|
||||
// Drop the object metatable because it may be some parent metatable
|
||||
lua_pop(L, 2); // Stack: rt
|
||||
return throwBadArg(L, index);
|
||||
}
|
||||
|
||||
lua_remove(L, -2); // Stack: rt, pot
|
||||
}
|
||||
|
||||
// no return
|
||||
}
|
||||
|
||||
static bool isInstance(lua_State* L, int index, void const* registryClassKey)
|
||||
{
|
||||
index = lua_absindex(L, index);
|
||||
|
||||
int result = lua_getmetatable(L, index); // Stack: object metatable (ot) | nothing
|
||||
if (result == 0)
|
||||
{
|
||||
return false; // Nothing was pushed on the stack
|
||||
}
|
||||
if (!lua_istable(L, -1))
|
||||
{
|
||||
lua_pop(L, 1); // Stack: -
|
||||
return false;
|
||||
}
|
||||
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, registryClassKey); // Stack: ot, rt
|
||||
lua_insert(L, -2); // Stack: rt, ot
|
||||
|
||||
for (;;)
|
||||
{
|
||||
if (lua_rawequal(L, -1, -2)) // Stack: rt, ot
|
||||
{
|
||||
lua_pop(L, 2); // Stack: -
|
||||
return true;
|
||||
}
|
||||
|
||||
// Replace current metatable with it's base class.
|
||||
lua_rawgetp(L, -1, getParentKey()); // Stack: rt, ot, parent ot (pot) | nil
|
||||
|
||||
if (lua_isnil(L, -1)) // Stack: rt, ot, nil
|
||||
{
|
||||
lua_pop(L, 3); // Stack: -
|
||||
return false;
|
||||
}
|
||||
|
||||
lua_remove(L, -2); // Stack: rt, pot
|
||||
}
|
||||
}
|
||||
|
||||
static Userdata* throwBadArg(lua_State* L, int index)
|
||||
{
|
||||
assert(lua_istable(L, -1) || lua_isnil(L, -1)); // Stack: rt | nil
|
||||
|
||||
const char* expected = 0;
|
||||
if (lua_isnil(L, -1)) // Stack: nil
|
||||
{
|
||||
expected = "unregistered class";
|
||||
}
|
||||
else
|
||||
{
|
||||
lua_rawgetp(L, -1, getTypeKey()); // Stack: rt, registry type
|
||||
expected = lua_tostring(L, -1);
|
||||
}
|
||||
|
||||
const char* got = 0;
|
||||
if (lua_isuserdata(L, index))
|
||||
{
|
||||
lua_getmetatable(L, index); // Stack: ..., ot | nil
|
||||
if (lua_istable(L, -1)) // Stack: ..., ot
|
||||
{
|
||||
lua_rawgetp(L, -1, getTypeKey()); // Stack: ..., ot, object type | nil
|
||||
if (lua_isstring(L, -1))
|
||||
{
|
||||
got = lua_tostring(L, -1);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!got)
|
||||
{
|
||||
got = lua_typename(L, lua_type(L, index));
|
||||
}
|
||||
|
||||
luaL_argerror(L, index, lua_pushfstring(L, "%s expected, got %s", expected, got));
|
||||
return 0;
|
||||
}
|
||||
|
||||
public:
|
||||
virtual ~Userdata() {}
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
Returns the Userdata* if the class on the Lua stack matches.
|
||||
If the class does not match, a Lua error is raised.
|
||||
|
||||
@tparam T A registered user class.
|
||||
@param L A Lua state.
|
||||
@param index The index of an item on the Lua stack.
|
||||
@returns A userdata pointer if the class matches.
|
||||
*/
|
||||
template<class T>
|
||||
static Userdata* getExact(lua_State* L, int index)
|
||||
{
|
||||
return getExactClass(L, index, detail::getClassRegistryKey<T>());
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
/**
|
||||
Get a pointer to the class from the Lua stack.
|
||||
If the object is not the class or a subclass, or it violates the
|
||||
const-ness, a Lua error is raised.
|
||||
|
||||
@tparam T A registered user class.
|
||||
@param L A Lua state.
|
||||
@param index The index of an item on the Lua stack.
|
||||
@param canBeConst TBD
|
||||
@returns A pointer if the class and constness match.
|
||||
*/
|
||||
template<class T>
|
||||
static T* get(lua_State* L, int index, bool canBeConst)
|
||||
{
|
||||
if (lua_isnil(L, index))
|
||||
return 0;
|
||||
|
||||
return static_cast<T*>(getClass(L,
|
||||
index,
|
||||
detail::getConstRegistryKey<T>(),
|
||||
detail::getClassRegistryKey<T>(),
|
||||
canBeConst)
|
||||
->getPointer());
|
||||
}
|
||||
|
||||
template<class T>
|
||||
static bool isInstance(lua_State* L, int index)
|
||||
{
|
||||
return isInstance(L, index, detail::getClassRegistryKey<T>());
|
||||
}
|
||||
};
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
Wraps a class object stored in a Lua userdata.
|
||||
|
||||
The lifetime of the object is managed by Lua. The object is constructed
|
||||
inside the userdata using placement new.
|
||||
*/
|
||||
template<class T>
|
||||
class UserdataValue : public Userdata
|
||||
{
|
||||
private:
|
||||
UserdataValue(UserdataValue<T> const&);
|
||||
UserdataValue<T> operator=(UserdataValue<T> const&);
|
||||
|
||||
char m_storage[sizeof(T)];
|
||||
|
||||
private:
|
||||
/**
|
||||
Used for placement construction.
|
||||
*/
|
||||
UserdataValue() { m_p = 0; }
|
||||
|
||||
~UserdataValue()
|
||||
{
|
||||
if (getPointer() != 0)
|
||||
{
|
||||
getObject()->~T();
|
||||
}
|
||||
}
|
||||
|
||||
public:
|
||||
/**
|
||||
Push a T via placement new.
|
||||
|
||||
The caller is responsible for calling placement new using the
|
||||
returned uninitialized storage.
|
||||
|
||||
@param L A Lua state.
|
||||
@returns An object referring to the newly created userdata value.
|
||||
*/
|
||||
static UserdataValue<T>* place(lua_State* const L)
|
||||
{
|
||||
UserdataValue<T>* const ud =
|
||||
new (lua_newuserdata(L, sizeof(UserdataValue<T>))) UserdataValue<T>();
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, detail::getClassRegistryKey<T>());
|
||||
if (!lua_istable(L, -1))
|
||||
{
|
||||
throw std::logic_error("The class is not registered in LuaBridge");
|
||||
}
|
||||
lua_setmetatable(L, -2);
|
||||
return ud;
|
||||
}
|
||||
|
||||
/**
|
||||
Push T via copy construction from U.
|
||||
|
||||
@tparam U A container type.
|
||||
@param L A Lua state.
|
||||
@param u A container object reference.
|
||||
*/
|
||||
template<class U>
|
||||
static inline void push(lua_State* const L, U const& u)
|
||||
{
|
||||
UserdataValue<T>* ud = place(L);
|
||||
new (ud->getObject()) U(u);
|
||||
ud->commit();
|
||||
}
|
||||
|
||||
/**
|
||||
Confirm object construction.
|
||||
*/
|
||||
void commit() { m_p = getObject(); }
|
||||
|
||||
T* getObject()
|
||||
{
|
||||
// If this fails to compile it means you forgot to provide
|
||||
// a Container specialization for your container!
|
||||
//
|
||||
return reinterpret_cast<T*>(&m_storage[0]);
|
||||
}
|
||||
};
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
/**
|
||||
Wraps a pointer to a class object inside a Lua userdata.
|
||||
|
||||
The lifetime of the object is managed by C++.
|
||||
*/
|
||||
class UserdataPtr : public Userdata
|
||||
{
|
||||
private:
|
||||
UserdataPtr(UserdataPtr const&);
|
||||
UserdataPtr operator=(UserdataPtr const&);
|
||||
|
||||
private:
|
||||
/** Push a pointer to object using metatable key.
|
||||
*/
|
||||
static void push(lua_State* L, const void* p, void const* const key)
|
||||
{
|
||||
new (lua_newuserdata(L, sizeof(UserdataPtr))) UserdataPtr(const_cast<void*>(p));
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, key);
|
||||
if (!lua_istable(L, -1))
|
||||
{
|
||||
lua_pop(L, 1); // possibly: a nil
|
||||
throw std::logic_error("The class is not registered in LuaBridge");
|
||||
}
|
||||
lua_setmetatable(L, -2);
|
||||
}
|
||||
|
||||
explicit UserdataPtr(void* const p)
|
||||
{
|
||||
m_p = p;
|
||||
|
||||
// Can't construct with a null pointer!
|
||||
//
|
||||
assert(m_p != 0);
|
||||
}
|
||||
|
||||
public:
|
||||
/** Push non-const pointer to object.
|
||||
|
||||
@tparam T A user registered class.
|
||||
@param L A Lua state.
|
||||
@param p A pointer to the user class instance.
|
||||
*/
|
||||
template<class T>
|
||||
static void push(lua_State* const L, T* const p)
|
||||
{
|
||||
if (p)
|
||||
push(L, p, getClassRegistryKey<T>());
|
||||
else
|
||||
lua_pushnil(L);
|
||||
}
|
||||
|
||||
/** Push const pointer to object.
|
||||
|
||||
@tparam T A user registered class.
|
||||
@param L A Lua state.
|
||||
@param p A pointer to the user class instance.
|
||||
*/
|
||||
template<class T>
|
||||
static void push(lua_State* const L, T const* const p)
|
||||
{
|
||||
if (p)
|
||||
push(L, p, getConstRegistryKey<T>());
|
||||
else
|
||||
lua_pushnil(L);
|
||||
}
|
||||
};
|
||||
|
||||
//============================================================================
|
||||
/**
|
||||
Wraps a container that references a class object.
|
||||
|
||||
The template argument C is the container type, ContainerTraits must be
|
||||
specialized on C or else a compile error will result.
|
||||
*/
|
||||
template<class C>
|
||||
class UserdataShared : public Userdata
|
||||
{
|
||||
private:
|
||||
UserdataShared(UserdataShared<C> const&);
|
||||
UserdataShared<C>& operator=(UserdataShared<C> const&);
|
||||
|
||||
typedef typename TypeTraits::removeConst<typename ContainerTraits<C>::Type>::Type T;
|
||||
|
||||
C m_c;
|
||||
|
||||
private:
|
||||
~UserdataShared() {}
|
||||
|
||||
public:
|
||||
/**
|
||||
Construct from a container to the class or a derived class.
|
||||
|
||||
@tparam U A container type.
|
||||
@param u A container object reference.
|
||||
*/
|
||||
template<class U>
|
||||
explicit UserdataShared(U const& u) : m_c(u)
|
||||
{
|
||||
m_p = const_cast<void*>(reinterpret_cast<void const*>((ContainerTraits<C>::get(m_c))));
|
||||
}
|
||||
|
||||
/**
|
||||
Construct from a pointer to the class or a derived class.
|
||||
|
||||
@tparam U A container type.
|
||||
@param u A container object pointer.
|
||||
*/
|
||||
template<class U>
|
||||
explicit UserdataShared(U* u) : m_c(u)
|
||||
{
|
||||
m_p = const_cast<void*>(reinterpret_cast<void const*>((ContainerTraits<C>::get(m_c))));
|
||||
}
|
||||
};
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
//
|
||||
// SFINAE helpers.
|
||||
//
|
||||
|
||||
// non-const objects
|
||||
template<class C, bool makeObjectConst>
|
||||
struct UserdataSharedHelper
|
||||
{
|
||||
typedef typename TypeTraits::removeConst<typename ContainerTraits<C>::Type>::Type T;
|
||||
|
||||
static void push(lua_State* L, C const& c)
|
||||
{
|
||||
if (ContainerTraits<C>::get(c) != 0)
|
||||
{
|
||||
new (lua_newuserdata(L, sizeof(UserdataShared<C>))) UserdataShared<C>(c);
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, getClassRegistryKey<T>());
|
||||
// If this goes off it means the class T is unregistered!
|
||||
assert(lua_istable(L, -1));
|
||||
lua_setmetatable(L, -2);
|
||||
}
|
||||
else
|
||||
{
|
||||
lua_pushnil(L);
|
||||
}
|
||||
}
|
||||
|
||||
static void push(lua_State* L, T* const t)
|
||||
{
|
||||
if (t)
|
||||
{
|
||||
new (lua_newuserdata(L, sizeof(UserdataShared<C>))) UserdataShared<C>(t);
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, getClassRegistryKey<T>());
|
||||
// If this goes off it means the class T is unregistered!
|
||||
assert(lua_istable(L, -1));
|
||||
lua_setmetatable(L, -2);
|
||||
}
|
||||
else
|
||||
{
|
||||
lua_pushnil(L);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// const objects
|
||||
template<class C>
|
||||
struct UserdataSharedHelper<C, true>
|
||||
{
|
||||
typedef typename TypeTraits::removeConst<typename ContainerTraits<C>::Type>::Type T;
|
||||
|
||||
static void push(lua_State* L, C const& c)
|
||||
{
|
||||
if (ContainerTraits<C>::get(c) != 0)
|
||||
{
|
||||
new (lua_newuserdata(L, sizeof(UserdataShared<C>))) UserdataShared<C>(c);
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, getConstRegistryKey<T>());
|
||||
// If this goes off it means the class T is unregistered!
|
||||
assert(lua_istable(L, -1));
|
||||
lua_setmetatable(L, -2);
|
||||
}
|
||||
else
|
||||
{
|
||||
lua_pushnil(L);
|
||||
}
|
||||
}
|
||||
|
||||
static void push(lua_State* L, T* const t)
|
||||
{
|
||||
if (t)
|
||||
{
|
||||
new (lua_newuserdata(L, sizeof(UserdataShared<C>))) UserdataShared<C>(t);
|
||||
lua_rawgetp(L, LUA_REGISTRYINDEX, getConstRegistryKey<T>());
|
||||
// If this goes off it means the class T is unregistered!
|
||||
assert(lua_istable(L, -1));
|
||||
lua_setmetatable(L, -2);
|
||||
}
|
||||
else
|
||||
{
|
||||
lua_pushnil(L);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
Pass by container.
|
||||
|
||||
The container controls the object lifetime. Typically this will be a
|
||||
lifetime shared by C++ and Lua using a reference count. Because of type
|
||||
erasure, containers like std::shared_ptr will not work. Containers must
|
||||
either be of the intrusive variety, or in the style of the RefCountedPtr
|
||||
type provided by LuaBridge (that uses a global hash table).
|
||||
*/
|
||||
template<class C, bool byContainer>
|
||||
struct StackHelper
|
||||
{
|
||||
static void push(lua_State* L, C const& c)
|
||||
{
|
||||
UserdataSharedHelper<C, TypeTraits::isConst<typename ContainerTraits<C>::Type>::value>::
|
||||
push(L, c);
|
||||
}
|
||||
|
||||
typedef typename TypeTraits::removeConst<typename ContainerTraits<C>::Type>::Type T;
|
||||
|
||||
static C get(lua_State* L, int index) { return Userdata::get<T>(L, index, true); }
|
||||
};
|
||||
|
||||
/**
|
||||
Pass by value.
|
||||
|
||||
Lifetime is managed by Lua. A C++ function which accesses a pointer or
|
||||
reference to an object outside the activation record in which it was
|
||||
retrieved may result in undefined behavior if Lua garbage collected it.
|
||||
*/
|
||||
template<class T>
|
||||
struct StackHelper<T, false>
|
||||
{
|
||||
static inline void push(lua_State* L, T const& t) { UserdataValue<T>::push(L, t); }
|
||||
|
||||
static inline T const& get(lua_State* L, int index)
|
||||
{
|
||||
return *Userdata::get<T>(L, index, true);
|
||||
}
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/**
|
||||
Lua stack conversions for pointers and references to class objects.
|
||||
|
||||
Lifetime is managed by C++. Lua code which remembers a reference to the
|
||||
value may result in undefined behavior if C++ destroys the object. The
|
||||
handling of the const and volatile qualifiers happens in UserdataPtr.
|
||||
*/
|
||||
|
||||
template<class C, bool byContainer>
|
||||
struct RefStackHelper
|
||||
{
|
||||
typedef C return_type;
|
||||
|
||||
static inline void push(lua_State* L, C const& t)
|
||||
{
|
||||
UserdataSharedHelper<C, TypeTraits::isConst<typename ContainerTraits<C>::Type>::value>::
|
||||
push(L, t);
|
||||
}
|
||||
|
||||
typedef typename TypeTraits::removeConst<typename ContainerTraits<C>::Type>::Type T;
|
||||
|
||||
static return_type get(lua_State* L, int index) { return Userdata::get<T>(L, index, true); }
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct RefStackHelper<T, false>
|
||||
{
|
||||
typedef T& return_type;
|
||||
|
||||
static void push(lua_State* L, T const& t) { UserdataPtr::push(L, &t); }
|
||||
|
||||
static return_type get(lua_State* L, int index)
|
||||
{
|
||||
T* t = Userdata::get<T>(L, index, true);
|
||||
|
||||
if (!t)
|
||||
luaL_error(L, "nil passed to reference");
|
||||
return *t;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Voider class template. Used to force a compiler to instantiate
|
||||
* an otherwise probably unused template parameter type T.
|
||||
* See the C++20 std::void_t <> for details.
|
||||
*/
|
||||
template<class T>
|
||||
struct Void
|
||||
{
|
||||
typedef void Type;
|
||||
};
|
||||
|
||||
/**
|
||||
* Trait class that selects whether to return a user registered
|
||||
* class object by value or by reference.
|
||||
*/
|
||||
|
||||
template<class T, class Enabler = void>
|
||||
struct UserdataGetter
|
||||
{
|
||||
typedef T* ReturnType;
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Userdata::get<T>(L, index, false); }
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct UserdataGetter<T, typename Void<T (*)()>::Type>
|
||||
{
|
||||
typedef T ReturnType;
|
||||
|
||||
static ReturnType get(lua_State* L, int index)
|
||||
{
|
||||
return StackHelper<T, TypeTraits::isContainer<T>::value>::get(L, index);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
//==============================================================================
|
||||
|
||||
/**
|
||||
Lua stack conversions for class objects passed by value.
|
||||
*/
|
||||
template<class T>
|
||||
struct Stack
|
||||
{
|
||||
typedef void IsUserdata;
|
||||
|
||||
typedef detail::UserdataGetter<T> Getter;
|
||||
typedef typename Getter::ReturnType ReturnType;
|
||||
|
||||
static void push(lua_State* L, T const& value)
|
||||
{
|
||||
using namespace detail;
|
||||
StackHelper<T, TypeTraits::isContainer<T>::value>::push(L, value);
|
||||
}
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Getter::get(L, index); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index)
|
||||
{
|
||||
return detail::Userdata::isInstance<T>(L, index);
|
||||
}
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
/**
|
||||
* Trait class indicating whether the parameter type must be
|
||||
* a user registered class. The trait checks the existence of
|
||||
* member type Stack::IsUserdata specialization for detection.
|
||||
*/
|
||||
template<class T, class Enable = void>
|
||||
struct IsUserdata
|
||||
{
|
||||
static const bool value = false;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct IsUserdata<T, typename Void<typename Stack<T>::IsUserdata>::Type>
|
||||
{
|
||||
static const bool value = true;
|
||||
};
|
||||
|
||||
/**
|
||||
* Trait class that selects a specific push/get implementation.
|
||||
*/
|
||||
template<class T, bool isUserdata>
|
||||
struct StackOpSelector;
|
||||
|
||||
// pointer
|
||||
template<class T>
|
||||
struct StackOpSelector<T*, true>
|
||||
{
|
||||
typedef T* ReturnType;
|
||||
|
||||
static void push(lua_State* L, T* value) { UserdataPtr::push(L, value); }
|
||||
|
||||
static T* get(lua_State* L, int index) { return Userdata::get<T>(L, index, false); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Userdata::isInstance<T>(L, index); }
|
||||
};
|
||||
|
||||
// pointer to const
|
||||
template<class T>
|
||||
struct StackOpSelector<const T*, true>
|
||||
{
|
||||
typedef const T* ReturnType;
|
||||
|
||||
static void push(lua_State* L, const T* value) { UserdataPtr::push(L, value); }
|
||||
|
||||
static const T* get(lua_State* L, int index) { return Userdata::get<T>(L, index, true); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Userdata::isInstance<T>(L, index); }
|
||||
};
|
||||
|
||||
// reference
|
||||
template<class T>
|
||||
struct StackOpSelector<T&, true>
|
||||
{
|
||||
typedef RefStackHelper<T, TypeTraits::isContainer<T>::value> Helper;
|
||||
typedef typename Helper::return_type ReturnType;
|
||||
|
||||
static void push(lua_State* L, T& value) { UserdataPtr::push(L, &value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Helper::get(L, index); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Userdata::isInstance<T>(L, index); }
|
||||
};
|
||||
|
||||
// reference to const
|
||||
template<class T>
|
||||
struct StackOpSelector<const T&, true>
|
||||
{
|
||||
typedef RefStackHelper<T, TypeTraits::isContainer<T>::value> Helper;
|
||||
typedef typename Helper::return_type ReturnType;
|
||||
|
||||
static void push(lua_State* L, const T& value) { Helper::push(L, value); }
|
||||
|
||||
static ReturnType get(lua_State* L, int index) { return Helper::get(L, index); }
|
||||
|
||||
static bool isInstance(lua_State* L, int index) { return Userdata::isInstance<T>(L, index); }
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
} // namespace luabridge
|
||||
125
csgo2/LuaBridge/luaBridge/detail/dump.h
Normal file
125
csgo2/LuaBridge/luaBridge/detail/dump.h
Normal file
@@ -0,0 +1,125 @@
|
||||
// https://github.com/vinniefalco/LuaBridge
|
||||
// Copyright 2019, Dmitry Tarakanov
|
||||
// Copyright 2012, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
// Copyright 2007, Nathan Reed
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "LuaBridge/detail/ClassInfo.h"
|
||||
|
||||
#include <iostream>
|
||||
#include <string>
|
||||
|
||||
namespace luabridge {
|
||||
|
||||
namespace debug {
|
||||
|
||||
inline void putIndent(std::ostream& stream, unsigned level)
|
||||
{
|
||||
for (unsigned i = 0; i < level; ++i)
|
||||
{
|
||||
stream << " ";
|
||||
}
|
||||
}
|
||||
|
||||
inline void
|
||||
dumpTable(lua_State* L, int index, std::ostream& stream, unsigned level, unsigned maxDepth);
|
||||
|
||||
inline void
|
||||
dumpValue(lua_State* L, int index, std::ostream& stream, unsigned maxDepth = 1, unsigned level = 0)
|
||||
{
|
||||
const int type = lua_type(L, index);
|
||||
switch (type)
|
||||
{
|
||||
case LUA_TNIL:
|
||||
stream << "nil";
|
||||
break;
|
||||
|
||||
case LUA_TBOOLEAN:
|
||||
stream << (lua_toboolean(L, index) ? "true" : "false");
|
||||
break;
|
||||
|
||||
case LUA_TNUMBER:
|
||||
stream << lua_tonumber(L, index);
|
||||
break;
|
||||
|
||||
case LUA_TSTRING:
|
||||
stream << '"' << lua_tostring(L, index) << '"';
|
||||
break;
|
||||
|
||||
case LUA_TFUNCTION:
|
||||
if (lua_iscfunction(L, index))
|
||||
{
|
||||
stream << "cfunction@" << lua_topointer(L, index);
|
||||
}
|
||||
else
|
||||
{
|
||||
stream << "function@" << lua_topointer(L, index);
|
||||
}
|
||||
break;
|
||||
|
||||
case LUA_TTHREAD:
|
||||
stream << "thread@" << lua_tothread(L, index);
|
||||
break;
|
||||
|
||||
case LUA_TLIGHTUSERDATA:
|
||||
stream << "lightuserdata@" << lua_touserdata(L, index);
|
||||
break;
|
||||
|
||||
case LUA_TTABLE:
|
||||
dumpTable(L, index, stream, level, maxDepth);
|
||||
break;
|
||||
|
||||
case LUA_TUSERDATA:
|
||||
stream << "userdata@" << lua_touserdata(L, index);
|
||||
break;
|
||||
|
||||
default:
|
||||
stream << lua_typename(L, type);
|
||||
;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
inline void
|
||||
dumpTable(lua_State* L, int index, std::ostream& stream, unsigned level, unsigned maxDepth)
|
||||
{
|
||||
stream << "table@" << lua_topointer(L, index);
|
||||
|
||||
if (level > maxDepth)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
index = lua_absindex(L, index);
|
||||
stream << " {";
|
||||
lua_pushnil(L); // Initial key
|
||||
while (lua_next(L, index))
|
||||
{
|
||||
stream << "\n";
|
||||
putIndent(stream, level + 1);
|
||||
dumpValue(L, -2, stream, maxDepth, level + 1); // Key
|
||||
stream << ": ";
|
||||
dumpValue(L, -1, stream, maxDepth, level + 1); // Value
|
||||
lua_pop(L, 1); // Value
|
||||
}
|
||||
stream << "\n";
|
||||
putIndent(stream, level);
|
||||
stream << "}";
|
||||
}
|
||||
|
||||
inline void dumpState(lua_State* L, std::ostream& stream = std::cerr, unsigned maxDepth = 1)
|
||||
{
|
||||
int top = lua_gettop(L);
|
||||
for (int i = 1; i <= top; ++i)
|
||||
{
|
||||
stream << "stack #" << i << ": ";
|
||||
dumpValue(L, i, stream, maxDepth, 0);
|
||||
stream << "\n";
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace debug
|
||||
|
||||
} // namespace luabridge
|
||||
Reference in New Issue
Block a user