twnlua: use stb_ds.h for enum conversions
This commit is contained in:
		| @@ -32,11 +32,13 @@ def default(parameter): | ||||
|  | ||||
|  | ||||
| print('#include "twn_game_api.h"\n') | ||||
| print('#define STB_DS_IMPLEMENTATION') # TODO: reuse implementation from the engine | ||||
| print('#include <stb_ds.h>') | ||||
| print('#include <lua.h>') | ||||
| print('#include <lualib.h>') | ||||
| print('#include <lauxlib.h>\n') | ||||
| print('#include <string.h>\n') | ||||
|  | ||||
| storages, converters, initializers, deinitializers = [], [], [], [] | ||||
|  | ||||
| for typename, typedesc in api["types"].items(): | ||||
|     converter = "static %s to_%s(lua_State *L, int idx) {\n" % (typename, typename.lower()) | ||||
| @@ -53,21 +55,29 @@ for typename, typedesc in api["types"].items(): | ||||
|                 raise BaseException("Unhandled converter field type '%s'" % (field["type"])) | ||||
|             converter += "    lua_pop(L, 1);\n"; | ||||
|  | ||||
|     # todo: use a hashtable instead | ||||
|     # TODO: wild idea: use compile time built hash table | ||||
|     elif "enums" in typedesc: | ||||
|         storages += ["struct %sHashItem { char *key; %s value; };\nstatic struct %sHashItem *%s_map = NULL;\n" % (typename, typename, typename, typename.lower())] | ||||
|  | ||||
|         # TODO: use arena | ||||
|         for enum in typedesc["enums"]: | ||||
|             initializer = "    shput(%s_map, \"%s\", %s);" % (typename.lower(), enum, typedesc["enums"][enum]) | ||||
|             initializers += [initializer] | ||||
|  | ||||
|         deinitializers += ["    shfree(%s_map);" % typename.lower()] | ||||
|  | ||||
|         converter += "    char *value = lua_tostring(L, -1);\n"; | ||||
|         for index, enum in enumerate(typedesc["enums"]): | ||||
|             if index == 0: | ||||
|                 converter += "    if (strncmp(\"%s\", value, sizeof(\"%s\")) == 0)\n" % (enum, enum) | ||||
|             else: | ||||
|                 converter += "    else if (strncmp(\"%s\", value, sizeof(\"%s\")) == 0)\n" % (enum, enum) | ||||
|             converter += "        %s = %s;\n" % (typename.lower(), typedesc["enums"][enum]) | ||||
|         converter += "        %s = shget(%s_map, value);\n" % (typename.lower(), typename.lower()) | ||||
|         converter += "    lua_pop(L, 1);\n"; | ||||
|  | ||||
|     converter += "    return %s;\n}\n" % (typename.lower()) | ||||
|     print(converter) | ||||
|     converters += [converter] | ||||
|  | ||||
| print('\n'.join(storages)) | ||||
| print("void bindgen_init(void) {\n" + '\n'.join(initializers) + "\n}\n") | ||||
| print('\n'.join(converters)) | ||||
|  | ||||
| bindings = [] | ||||
| for procedure, procedure_desc in api["procedures"].items(): | ||||
|     binding = "static int binding_%s(lua_State *L) {\n" % procedure | ||||
|     binding += "    luaL_checktype(L, 1, LUA_TTABLE);\n" | ||||
| @@ -118,6 +128,7 @@ for procedure, procedure_desc in api["procedures"].items(): | ||||
| loader = "void bindgen_load_%s(lua_State *L) {\n" % api["name"] | ||||
| modules = set(api["procedures"][procedure]["module"] for procedure in api["procedures"]) | ||||
| for module in modules: | ||||
|     loader += "    bindgen_init();\n" | ||||
|     loader += "    lua_newtable(L);\n" | ||||
|     for procedure, procedure_desc in api["procedures"].items(): | ||||
|         if procedure_desc["module"] == module: | ||||
| @@ -128,3 +139,9 @@ for module in modules: | ||||
|  | ||||
| loader += "}" | ||||
| print(loader) | ||||
|  | ||||
|  | ||||
| unloader = "void bindgen_unload_%s(lua_State *L) {\n" % api["name"] | ||||
| unloader += '\n'.join(deinitializers) | ||||
| unloader += "}" | ||||
| print(unloader) | ||||
|   | ||||
| @@ -12,6 +12,7 @@ | ||||
|  | ||||
| /* generated by bindgen.py */ | ||||
| void bindgen_load_twn(lua_State *L); | ||||
| void bindgen_unload_twn(lua_State *L); | ||||
|  | ||||
|  | ||||
| /* require will go through physicsfs exclusively so that scripts can be in the data dir */ | ||||
| @@ -119,6 +120,7 @@ void game_tick(void) { | ||||
|  | ||||
| void game_end(void) { | ||||
|     State *state = ctx.udata; | ||||
|     bindgen_unload_twn(state->L); | ||||
|     lua_close(state->L); | ||||
|     free(state); | ||||
| } | ||||
|   | ||||
		Reference in New Issue
	
	Block a user