diff --git a/include/Nazara/Lua/LuaInstance.hpp b/include/Nazara/Lua/LuaInstance.hpp index f36ee1ae5..a7d530c6a 100644 --- a/include/Nazara/Lua/LuaInstance.hpp +++ b/include/Nazara/Lua/LuaInstance.hpp @@ -30,6 +30,11 @@ class NAZARA_API NzLuaInstance : NzNonCopyable NzLuaInstance(); ~NzLuaInstance(); + void ArgCheck(bool condition, unsigned int argNum, const char* error); + void ArgCheck(bool condition, unsigned int argNum, const NzString& error); + int ArgError(unsigned int argNum, const char* error); + int ArgError(unsigned int argNum, const NzString& error); + void CheckAny(int index) const; bool CheckBoolean(int index) const; bool CheckBoolean(int index, bool defValue) const; @@ -52,6 +57,9 @@ class NAZARA_API NzLuaInstance : NzNonCopyable void Concatenate(int count); + int CreateReference(); + void DestroyReference(int ref); + NzString DumpStack() const; void Error(const char* message); @@ -106,6 +114,7 @@ class NAZARA_API NzLuaInstance : NzNonCopyable void PushMetatable(const NzString& str); void PushNil(); void PushNumber(double value); + void PushReference(int ref); void PushString(const char* str); void PushString(const NzString& str); void PushTable(unsigned int sequenceElementCount = 0, unsigned int arrayElementCount = 0); @@ -130,6 +139,7 @@ class NAZARA_API NzLuaInstance : NzNonCopyable bool ToBoolean(int index) const; int ToInteger(int index, bool* succeeded = nullptr) const; double ToNumber(int index, bool* succeeded = nullptr) const; + const void* ToPointer(int index) const; const char* ToString(int index, std::size_t* length = nullptr) const; unsigned int ToUnsigned(int index, bool* succeeded = nullptr) const; void* ToUserdata(int index) const; diff --git a/src/Nazara/Lua/LuaInstance.cpp b/src/Nazara/Lua/LuaInstance.cpp index 23c3ab9fe..e3fa382e5 100644 --- a/src/Nazara/Lua/LuaInstance.cpp +++ b/src/Nazara/Lua/LuaInstance.cpp @@ -28,9 +28,9 @@ namespace int AtPanic(lua_State* state) { - NazaraUnused(state); + NzString lastError(lua_tostring(state, -1)); - throw std::runtime_error("Lua panic !"); + throw std::runtime_error("Lua panic: " + lastError); } const char* StreamReader(lua_State* state, void* data, std::size_t* size) @@ -48,13 +48,15 @@ namespace } } - int s_comparisons[nzLuaComparison_Max+1] = { + int s_comparisons[] = { LUA_OPEQ, // nzLuaComparison_Equality LUA_OPLT, // nzLuaComparison_Less LUA_OPLE // nzLuaComparison_LessOrEqual }; - int s_operations[nzLuaOperation_Max+1] = { + static_assert(sizeof(s_comparisons)/sizeof(int) == nzLuaComparison_Max+1, "Lua comparison array is incomplete"); + + int s_operations[] = { LUA_OPADD, // nzLuaOperation_Addition LUA_OPDIV, // nzLuaOperation_Division LUA_OPPOW, // nzLuaOperation_Exponentiation @@ -64,7 +66,9 @@ namespace LUA_OPSUB // nzLuaOperation_Substraction }; - int s_types[nzLuaType_Max+1] = { + static_assert(sizeof(s_operations)/sizeof(int) == nzLuaOperation_Max+1, "Lua operation array is incomplete"); + + int s_types[] = { LUA_TBOOLEAN, // nzLuaType_Boolean LUA_TFUNCTION, // nzLuaType_Function LUA_TLIGHTUSERDATA, // nzLuaType_LightUserdata @@ -76,6 +80,8 @@ namespace LUA_TTHREAD, // nzLuaType_Thread LUA_TUSERDATA // nzLuaType_Userdata }; + + static_assert(sizeof(s_types)/sizeof(int) == nzLuaType_Max+1, "Lua type array is incomplete"); } NzLuaInstance::NzLuaInstance() : @@ -95,6 +101,26 @@ NzLuaInstance::~NzLuaInstance() lua_close(m_state); } +void NzLuaInstance::ArgCheck(bool condition, unsigned int argNum, const char* error) +{ + luaL_argcheck(m_state, condition, argNum, error); +} + +void NzLuaInstance::ArgCheck(bool condition, unsigned int argNum, const NzString& error) +{ + luaL_argcheck(m_state, condition, argNum, error.GetConstBuffer()); +} + +int NzLuaInstance::ArgError(unsigned int argNum, const char* error) +{ + return luaL_argerror(m_state, argNum, error); +} + +int NzLuaInstance::ArgError(unsigned int argNum, const NzString& error) +{ + return luaL_argerror(m_state, argNum, error.GetConstBuffer()); +} + void NzLuaInstance::CheckAny(int index) const { luaL_checkany(m_state, index); @@ -224,6 +250,16 @@ void NzLuaInstance::Concatenate(int count) lua_concat(m_state, count); } +int NzLuaInstance::CreateReference() +{ + return luaL_ref(m_state, LUA_REGISTRYINDEX); +} + +void NzLuaInstance::DestroyReference(int ref) +{ + luaL_unref(m_state, LUA_REGISTRYINDEX, ref); +} + NzString NzLuaInstance::DumpStack() const { NzStringStream stream; @@ -240,7 +276,7 @@ NzString NzLuaInstance::DumpStack() const break; case nzLuaType_Function: - stream << "Function"; + stream << "Function(" << ToPointer(i) << ')'; break; case nzLuaType_LightUserdata: @@ -265,15 +301,15 @@ NzString NzLuaInstance::DumpStack() const break; case nzLuaType_Table: - stream << "Table"; + stream << "Table(" << ToPointer(i) << ')'; break; case nzLuaType_Thread: - stream << "Thread"; + stream << "Thread(" << ToPointer(i) << ')'; break; default: - stream << "Unknown"; + stream << "Unknown(" << ToPointer(i) << ')'; break; } @@ -620,6 +656,11 @@ void NzLuaInstance::PushNumber(double value) lua_pushnumber(m_state, value); } +void NzLuaInstance::PushReference(int ref) +{ + lua_rawgeti(m_state, LUA_REGISTRYINDEX, ref); +} + void NzLuaInstance::PushString(const char* str) { lua_pushstring(m_state, str); @@ -745,6 +786,11 @@ double NzLuaInstance::ToNumber(int index, bool* succeeded) const return result; } +const void* NzLuaInstance::ToPointer(int index) const +{ + return lua_topointer(m_state, index); +} + const char* NzLuaInstance::ToString(int index, std::size_t* length) const { return lua_tolstring(m_state, index, length);