diff options
Diffstat (limited to 'include/BLua.h')
-rw-r--r-- | include/BLua.h | 752 |
1 files changed, 376 insertions, 376 deletions
diff --git a/include/BLua.h b/include/BLua.h index 52918ee..e2fc852 100644 --- a/include/BLua.h +++ b/include/BLua.h @@ -1,376 +1,376 @@ -/*
- * Baltisot
- * Copyright (C) 1999-2003 Nicolas "Pixel" Noble
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-/* $Id: BLua.h,v 1.18 2004-11-27 21:01:20 pixel Exp $ */
-
-#ifndef __BLUA_H__
-#define __BLUA_H__
-
-struct lua_State;
-
-extern "C" {
- void do_lua_lock(lua_State *);
- void do_lua_unlock(lua_State *);
-}
-
-#define lua_lock(L) do_lua_lock(L)
-#define lua_unlock(L) do_lua_unlock(L)
-
-#include <lua.h>
-#include <map>
-#include <Exceptions.h>
-#include <Handle.h>
-
-class Lua : public Base {
- public:
- Lua();
- Lua(const Lua &) throw (GeneralException);
- virtual ~Lua();
- void open_base();
- void open_table();
- void open_io();
- void open_string();
- void open_math();
- void open_debug();
- void open_dir();
- void declarefunc(const String &, lua_CFunction, int = LUA_GLOBALSINDEX);
- void call(const String &, int = LUA_GLOBALSINDEX, int = 0, int = 0);
- void call(int = 0, int = 0);
- void push();
- void push(lua_Number);
- void push(const String &);
- void push(bool);
- void push(char *, int size = -1);
- void push(void *);
- void push(lua_CFunction, int = 0);
- void pop(int = 1);
- void newtable();
- void * newuser(size_t);
- void settable(int = -3, bool raw = false);
- void gettable(int = -2, bool raw = false);
- void setvar();
- int gettop();
- void error(const String &);
- int type(int = -1);
- bool isnil(int = -1);
- bool isboolean(int = -1);
- bool isnumber(int = -1);
- bool isstring(int = -1);
- bool istable(int = -1);
- bool isfunction(int = -1);
- bool iscfunction(int = -1);
- bool isuserdata(int = -1);
- bool islightuserdata(int = -1);
- bool toboolean(int = -1);
- lua_Number tonumber(int = -1);
- String tostring(int = -1);
- lua_CFunction tocfunction(int = -1);
- void * touserdata(int = -1);
- Lua * tothread(int = -1);
- void load(Handle *, bool docall = true) throw (GeneralException);
- void dump(Handle *, bool strip = true);
- Lua * thread();
- int yield(int nargs = 0);
- int resume(int nresults = 0);
- static Lua * find(lua_State *) throw (GeneralException);
- void showerror();
- int getmetatable(int = -1);
- int setmetatable(int = -2);
- int sethook(lua_Hook func, int mask, int count);
-
- void do_break();
-
- virtual void lock() {}
- virtual void unlock() {}
- private:
- Lua(lua_State *);
- lua_State * L;
- static std::map<lua_State *, Lua *> lualist;
-};
-
-class LuaObject : public Base {
- public:
- LuaObject() : wantdestruct(false), pushed(false) {}
- virtual void push(Lua *) throw (GeneralException);
- static void * getme(Lua *, int = 1);
- void pushdestruct(Lua *) throw (GeneralException);
- protected:
- virtual void pushmembers(Lua *) = 0;
- void pushme(Lua *, void *, bool = true);
- static void pushit(Lua *, const String &, lua_CFunction);
- static void pushmeta(Lua *, const String &, lua_CFunction);
- bool wantdestruct, pushed;
-};
-
-class LuaException : public GeneralException {
- public:
- LuaException(String);
- protected:
- LuaException();
-};
-
-enum Lua_types_t {
- LUA_OBJECT = 0x01,
- LUA_TABLE = 0x02,
- LUA_BOOLEAN = 0x04,
- LUA_NUMBER = 0x08,
- LUA_STRING = 0x10,
- LUA_FUNCTION = 0x20,
- LUA_NIL = 0x40,
- LUA_ANY = 0x7f,
-};
-
-#define MAX_TYPE 7
-
-#define MAXARGS 32
-
-struct lua_functypes_t {
- int number;
- char * name;
- int minargs, maxargs;
- int argtypes[MAXARGS];
-};
-
-#define DECLARE_METHOD(classname, enumvar) static int method_##enumvar(lua_State * L) { \
- return LuaHelpers<classname>::method_multiplex( \
- enumvar, \
- L, \
- sLua_##classname::classname##_proceed, \
- 0, \
- classname##_methods, \
- true); \
- }
-
-#define DECLARE_FUNCTION(classname, enumvar) static int function_##enumvar(lua_State * L) { \
- return LuaHelpers<classname>::method_multiplex( \
- enumvar, \
- L, \
- 0, \
- sLua_##classname::classname##_proceed_statics, \
- classname##_functions, \
- false); \
- }
-
-#define PUSH_METHOD(classname, enumvar) pushit( \
- L, \
- classname##_methods[enumvar].name, \
- sLua_##classname::method_##enumvar)
-
-#define PUSH_METAMETHOD(classname, enumvar) pushmeta( \
- L, \
- String("__") + classname##_methods[enumvar].name, \
- sLua_##classname::method_##enumvar)
-
-#define PUSH_FUNCTION(classname, enumvar) L->declarefunc( \
- classname##_functions[enumvar].name, \
- sLua_##classname::function_##enumvar)
-
-
-#define CHECK_METHODS(classname) { \
- int i = 0; \
- while (classname##_methods[i].number != -1) { \
- if (i != classname##_methods[i].number) { \
- throw GeneralException("Datas of " #classname "_methods inconsistants!"); \
- } \
- i++; \
- } \
-}
-
-#define CHECK_FUNCTIONS(classname) { \
- int i = 0; \
- while (classname##_functions[i].number != -1) { \
- if (i != classname##_functions[i].number) { \
- throw GeneralException("Datas of " #classname "_functions inconsistants!"); \
- } \
- i++; \
- } \
-}
-
-#include <typeinfo>
-
-template <class T>
-class LuaHelpers : public Base {
- public:
- static int method_multiplex(int caller, lua_State * _L, int (*proceed)(Lua * L, int n, T * obj, int caller), int (*proceed_static)(Lua * L, int n, int caller), lua_functypes_t * tab, bool method) {
- Lua * L = Lua::find(_L);
- int add = method ? 1 : 0;
- int n = L->gettop() - add;
- T * obj = 0;
- int i, j, mask;
- bool invalid = false, arg_valid;
-
- if (method)
- obj = (T *) LuaObject::getme(L);
-
- if ((n < tab[caller].minargs) || (n > tab[caller].maxargs)) {
- invalid = true;
- } else {
- for (i = 0; i < tab[caller].maxargs && !invalid; i++) {
- if (n >= (i + 1)) {
- arg_valid = false;
- for (j = 0; j < MAX_TYPE && !arg_valid; j++) {
- mask = 1 << j;
- if (tab[caller].argtypes[i] & mask) {
- switch(mask) {
- case LUA_OBJECT:
- if (L->istable(i + 1 + add)) {
- L->push("__obj");
- L->gettable(i + 1 + add);
- arg_valid = L->isuserdata();
- L->pop();
- } else {
- arg_valid = L->isnil(i + 1 + add);
- }
- break;
- case LUA_TABLE:
- arg_valid = L->istable(i + 1 + add);
- break;
- case LUA_BOOLEAN:
- arg_valid = L->isboolean(i + 1 + add);
- break;
- case LUA_NUMBER:
- arg_valid = L->isnumber(i + 1 + add);
- break;
- case LUA_STRING:
- arg_valid = L->isstring(i + 1 + add);
- break;
- case LUA_FUNCTION:
- arg_valid = L->isfunction(i + 1 + add);
- break;
- case LUA_NIL:
- arg_valid = L->isnil(i + 1 + add);
- break;
- }
- }
- }
- invalid = !arg_valid;
- }
- }
- }
-
- if (invalid) {
- if (method) {
- L->error(String("Invalid arguments to method `") + typeid(T).name() + "::" + tab[caller].name + "'");
- } else {
- L->error(String("Invalid arguments to function `") + typeid(T).name() + "::" + tab[caller].name + "'");
- }
- }
-
- if (method) {
- return proceed(L, n, obj, caller);
- } else {
- return proceed_static(L, n, caller);
- }
- }
-};
-
-
- /*******************************\
-|** Let's have a sample of use **|
- \*******************************/
-
-#ifdef THIS_IS_A_SAMPLE_WHICH_DOES_NOT_COMPILE
-Luacdfile::Luacdfile(cdfile * h) : LuaHandle(h) { }
-
-enum cdfile_methods_t {
- CDFILE_XXX = 0,
- CDFILE_YYY
-};
-
-enum cdfile_functions_t {
- CDFILE_NEWCDFILE = 0,
-};
-
-struct lua_functypes_t cdutils_methods[] = {
- { CDFILE_XXX, "xxx", 1, 1, {LUA_OBJECT} },
- { CDFILE_YYY, "yyy", 0, 2, {LUA_NUMBER, LUA_NUMBER} },
- { -1, 0, 0, 0, 0 }
-};
-
-struct lua_functypes_t cdfile_functions[] = {
- { CDFILE_NEWCDFILE, "cdfile", 1, 4, {LUA_OBJECT, LUA_ANY, LUA_NUMBER, LUA_NUMBER} },
- { -1, 0, 0, 0, 0 }
-};
-
-class sLua_cdfile : public Base {
- public:
- static int newcdfile(lua_State * L);
- DECLARE_METHOD(cdfile, CDFILE_XXX);
- DECLARE_METHOD(cdfile, CDFILE_YYY);
- DECLARE_FUNCTION(cdfile, CDFILE_NEWCDFILE);
- private:
- static int cdfile_proceed(Lua * L, int n, cdfile * obj, int caller);
- static int cdfile_proceed_statics(Lua * L, int n, int caller);
-};
-
-void Luacdfile::pushmembers(Lua * L) {
- {
- LuaHandle::pushmembers(L);
- or
- pushme(L, SomeObject);
- }
- PUSH_METHOD(cdfile, CDFILE_XXX);
- PUSH_METHOD(cdfile, CDFILE_YYY);
-}
-
-void Luacdfile::pushstatics(Lua * L) {
- CHECK_METHODS(cdfile);
- CHECK_FUNCTIONS(cdfile);
-
- PUSH_FUNCTION(cdfile, CDFILE_NEWCDFILE);
-}
-
-int sLua_cdfile::cdfile_proceed(Lua * L, int n, cdfile * cdfile, int caller) {
- int r = 0;
- SomeObj * obj;
- int arg1 = DEFAULT1, arg2 = DEFAULT2;
-
- switch(caller) {
- case CDFILE_XXX:
- obj = (SomeObj *) LuaObject::getme(L, 2);
- cdfile->xxx(obj);
- break;
- case CDFILE_YYY:
- if (n >= 1)
- arg1 = L->tonumber(2);
- if (n >= 2)
- arg2 = L->tonumber(3);
- L->push((lua_Number) cdfile->yyy(arg1, arg2));
- r = 1;
- break;
- }
-
- return r;
-}
-
-int sLua_cdfile::cdfile_proceed_statics(Lua * L, int n, int caller) {
- int r = 0;
-
- switch(caller) {
- case CDFILE_NEWCDFILE:
- /****TODO****/
- break;
- }
-
- return r;
-}
-
-#endif
-
-#endif
+/* + * Baltisot + * Copyright (C) 1999-2003 Nicolas "Pixel" Noble + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +/* $Id: BLua.h,v 1.19 2004-11-27 21:46:02 pixel Exp $ */ + +#ifndef __BLUA_H__ +#define __BLUA_H__ + +struct lua_State; + +extern "C" { + void do_lua_lock(lua_State *); + void do_lua_unlock(lua_State *); +} + +#define lua_lock(L) do_lua_lock(L) +#define lua_unlock(L) do_lua_unlock(L) + +#include <lua.h> +#include <map> +#include <Exceptions.h> +#include <Handle.h> + +class Lua : public Base { + public: + Lua(); + Lua(const Lua &) throw (GeneralException); + virtual ~Lua(); + void open_base(); + void open_table(); + void open_io(); + void open_string(); + void open_math(); + void open_debug(); + void open_dir(); + void declarefunc(const String &, lua_CFunction, int = LUA_GLOBALSINDEX); + void call(const String &, int = LUA_GLOBALSINDEX, int = 0, int = 0); + void call(int = 0, int = 0); + void push(); + void push(lua_Number); + void push(const String &); + void push(bool); + void push(char *, int size = -1); + void push(void *); + void push(lua_CFunction, int = 0); + void pop(int = 1); + void newtable(); + void * newuser(size_t); + void settable(int = -3, bool raw = false); + void gettable(int = -2, bool raw = false); + void setvar(); + int gettop(); + void error(const String &); + int type(int = -1); + bool isnil(int = -1); + bool isboolean(int = -1); + bool isnumber(int = -1); + bool isstring(int = -1); + bool istable(int = -1); + bool isfunction(int = -1); + bool iscfunction(int = -1); + bool isuserdata(int = -1); + bool islightuserdata(int = -1); + bool toboolean(int = -1); + lua_Number tonumber(int = -1); + String tostring(int = -1); + lua_CFunction tocfunction(int = -1); + void * touserdata(int = -1); + Lua * tothread(int = -1); + void load(Handle *, bool docall = true) throw (GeneralException); + void dump(Handle *, bool strip = true); + Lua * thread(); + int yield(int nargs = 0); + int resume(int nresults = 0); + static Lua * find(lua_State *) throw (GeneralException); + void showerror(); + int getmetatable(int = -1); + int setmetatable(int = -2); + int sethook(lua_Hook func, int mask, int count); + + void do_break(); + + virtual void lock() {} + virtual void unlock() {} + private: + Lua(lua_State *); + lua_State * L; + static std::map<lua_State *, Lua *> lualist; +}; + +class LuaObject : public Base { + public: + LuaObject() : wantdestruct(false), pushed(false) {} + virtual void push(Lua *) throw (GeneralException); + static void * getme(Lua *, int = 1); + void pushdestruct(Lua *) throw (GeneralException); + protected: + virtual void pushmembers(Lua *) = 0; + void pushme(Lua *, void *, bool = true); + static void pushit(Lua *, const String &, lua_CFunction); + static void pushmeta(Lua *, const String &, lua_CFunction); + bool wantdestruct, pushed; +}; + +class LuaException : public GeneralException { + public: + LuaException(String); + protected: + LuaException(); +}; + +enum Lua_types_t { + LUA_OBJECT = 0x01, + LUA_TABLE = 0x02, + LUA_BOOLEAN = 0x04, + LUA_NUMBER = 0x08, + LUA_STRING = 0x10, + LUA_FUNCTION = 0x20, + LUA_NIL = 0x40, + LUA_ANY = 0x7f, +}; + +#define MAX_TYPE 7 + +#define MAXARGS 32 + +struct lua_functypes_t { + int number; + char * name; + int minargs, maxargs; + int argtypes[MAXARGS]; +}; + +#define DECLARE_METHOD(classname, enumvar) static int method_##enumvar(lua_State * L) { \ + return LuaHelpers<classname>::method_multiplex( \ + enumvar, \ + L, \ + sLua_##classname::classname##_proceed, \ + 0, \ + classname##_methods, \ + true); \ + } + +#define DECLARE_FUNCTION(classname, enumvar) static int function_##enumvar(lua_State * L) { \ + return LuaHelpers<classname>::method_multiplex( \ + enumvar, \ + L, \ + 0, \ + sLua_##classname::classname##_proceed_statics, \ + classname##_functions, \ + false); \ + } + +#define PUSH_METHOD(classname, enumvar) pushit( \ + L, \ + classname##_methods[enumvar].name, \ + sLua_##classname::method_##enumvar) + +#define PUSH_METAMETHOD(classname, enumvar) pushmeta( \ + L, \ + String("__") + classname##_methods[enumvar].name, \ + sLua_##classname::method_##enumvar) + +#define PUSH_FUNCTION(classname, enumvar) L->declarefunc( \ + classname##_functions[enumvar].name, \ + sLua_##classname::function_##enumvar) + + +#define CHECK_METHODS(classname) { \ + int i = 0; \ + while (classname##_methods[i].number != -1) { \ + if (i != classname##_methods[i].number) { \ + throw GeneralException("Datas of " #classname "_methods inconsistants!"); \ + } \ + i++; \ + } \ +} + +#define CHECK_FUNCTIONS(classname) { \ + int i = 0; \ + while (classname##_functions[i].number != -1) { \ + if (i != classname##_functions[i].number) { \ + throw GeneralException("Datas of " #classname "_functions inconsistants!"); \ + } \ + i++; \ + } \ +} + +#include <typeinfo> + +template <class T> +class LuaHelpers : public Base { + public: + static int method_multiplex(int caller, lua_State * _L, int (*proceed)(Lua * L, int n, T * obj, int caller), int (*proceed_static)(Lua * L, int n, int caller), lua_functypes_t * tab, bool method) { + Lua * L = Lua::find(_L); + int add = method ? 1 : 0; + int n = L->gettop() - add; + T * obj = 0; + int i, j, mask; + bool invalid = false, arg_valid; + + if (method) + obj = (T *) LuaObject::getme(L); + + if ((n < tab[caller].minargs) || (n > tab[caller].maxargs)) { + invalid = true; + } else { + for (i = 0; i < tab[caller].maxargs && !invalid; i++) { + if (n >= (i + 1)) { + arg_valid = false; + for (j = 0; j < MAX_TYPE && !arg_valid; j++) { + mask = 1 << j; + if (tab[caller].argtypes[i] & mask) { + switch(mask) { + case LUA_OBJECT: + if (L->istable(i + 1 + add)) { + L->push("__obj"); + L->gettable(i + 1 + add); + arg_valid = L->isuserdata(); + L->pop(); + } else { + arg_valid = L->isnil(i + 1 + add); + } + break; + case LUA_TABLE: + arg_valid = L->istable(i + 1 + add); + break; + case LUA_BOOLEAN: + arg_valid = L->isboolean(i + 1 + add); + break; + case LUA_NUMBER: + arg_valid = L->isnumber(i + 1 + add); + break; + case LUA_STRING: + arg_valid = L->isstring(i + 1 + add); + break; + case LUA_FUNCTION: + arg_valid = L->isfunction(i + 1 + add); + break; + case LUA_NIL: + arg_valid = L->isnil(i + 1 + add); + break; + } + } + } + invalid = !arg_valid; + } + } + } + + if (invalid) { + if (method) { + L->error(String("Invalid arguments to method `") + typeid(T).name() + "::" + tab[caller].name + "'"); + } else { + L->error(String("Invalid arguments to function `") + typeid(T).name() + "::" + tab[caller].name + "'"); + } + } + + if (method) { + return proceed(L, n, obj, caller); + } else { + return proceed_static(L, n, caller); + } + } +}; + + + /*******************************\ +|** Let's have a sample of use **| + \*******************************/ + +#ifdef THIS_IS_A_SAMPLE_WHICH_DOES_NOT_COMPILE +Luacdfile::Luacdfile(cdfile * h) : LuaHandle(h) { } + +enum cdfile_methods_t { + CDFILE_XXX = 0, + CDFILE_YYY +}; + +enum cdfile_functions_t { + CDFILE_NEWCDFILE = 0, +}; + +struct lua_functypes_t cdutils_methods[] = { + { CDFILE_XXX, "xxx", 1, 1, {LUA_OBJECT} }, + { CDFILE_YYY, "yyy", 0, 2, {LUA_NUMBER, LUA_NUMBER} }, + { -1, 0, 0, 0, 0 } +}; + +struct lua_functypes_t cdfile_functions[] = { + { CDFILE_NEWCDFILE, "cdfile", 1, 4, {LUA_OBJECT, LUA_ANY, LUA_NUMBER, LUA_NUMBER} }, + { -1, 0, 0, 0, 0 } +}; + +class sLua_cdfile : public Base { + public: + static int newcdfile(lua_State * L); + DECLARE_METHOD(cdfile, CDFILE_XXX); + DECLARE_METHOD(cdfile, CDFILE_YYY); + DECLARE_FUNCTION(cdfile, CDFILE_NEWCDFILE); + private: + static int cdfile_proceed(Lua * L, int n, cdfile * obj, int caller); + static int cdfile_proceed_statics(Lua * L, int n, int caller); +}; + +void Luacdfile::pushmembers(Lua * L) { + { + LuaHandle::pushmembers(L); + or + pushme(L, SomeObject); + } + PUSH_METHOD(cdfile, CDFILE_XXX); + PUSH_METHOD(cdfile, CDFILE_YYY); +} + +void Luacdfile::pushstatics(Lua * L) { + CHECK_METHODS(cdfile); + CHECK_FUNCTIONS(cdfile); + + PUSH_FUNCTION(cdfile, CDFILE_NEWCDFILE); +} + +int sLua_cdfile::cdfile_proceed(Lua * L, int n, cdfile * cdfile, int caller) { + int r = 0; + SomeObj * obj; + int arg1 = DEFAULT1, arg2 = DEFAULT2; + + switch(caller) { + case CDFILE_XXX: + obj = (SomeObj *) LuaObject::getme(L, 2); + cdfile->xxx(obj); + break; + case CDFILE_YYY: + if (n >= 1) + arg1 = L->tonumber(2); + if (n >= 2) + arg2 = L->tonumber(3); + L->push((lua_Number) cdfile->yyy(arg1, arg2)); + r = 1; + break; + } + + return r; +} + +int sLua_cdfile::cdfile_proceed_statics(Lua * L, int n, int caller) { + int r = 0; + + switch(caller) { + case CDFILE_NEWCDFILE: + /****TODO****/ + break; + } + + return r; +} + +#endif + +#endif |