diff options
Diffstat (limited to '')
| -rw-r--r-- | lua_cjson.c | 73 | 
1 files changed, 57 insertions, 16 deletions
| diff --git a/lua_cjson.c b/lua_cjson.c index 8e9b237..be5cdc2 100644 --- a/lua_cjson.c +++ b/lua_cjson.c | |||
| @@ -45,6 +45,10 @@ | |||
| 45 | #include "strbuf.h" | 45 | #include "strbuf.h" | 
| 46 | #include "fpconv.h" | 46 | #include "fpconv.h" | 
| 47 | 47 | ||
| 48 | #ifndef CJSON_MODNAME | ||
| 49 | #define CJSON_MODNAME "cjson" | ||
| 50 | #endif | ||
| 51 | |||
| 48 | #ifndef CJSON_VERSION | 52 | #ifndef CJSON_VERSION | 
| 49 | #define CJSON_VERSION "1.0devel" | 53 | #define CJSON_VERSION "1.0devel" | 
| 50 | #endif | 54 | #endif | 
| @@ -175,22 +179,16 @@ static const char *char2escape[256] = { | |||
| 175 | NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, | 179 | NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, | 
| 176 | }; | 180 | }; | 
| 177 | 181 | ||
| 178 | static int json_config_key; | ||
| 179 | |||
| 180 | /* ===== CONFIGURATION ===== */ | 182 | /* ===== CONFIGURATION ===== */ | 
| 181 | 183 | ||
| 182 | static json_config_t *json_fetch_config(lua_State *l) | 184 | static json_config_t *json_fetch_config(lua_State *l) | 
| 183 | { | 185 | { | 
| 184 | json_config_t *cfg; | 186 | json_config_t *cfg; | 
| 185 | 187 | ||
| 186 | lua_pushlightuserdata(l, &json_config_key); | 188 | cfg = lua_touserdata(l, lua_upvalueindex(1)); | 
| 187 | lua_gettable(l, LUA_REGISTRYINDEX); | ||
| 188 | cfg = lua_touserdata(l, -1); | ||
| 189 | if (!cfg) | 189 | if (!cfg) | 
| 190 | luaL_error(l, "BUG: Unable to fetch CJSON configuration"); | 190 | luaL_error(l, "BUG: Unable to fetch CJSON configuration"); | 
| 191 | 191 | ||
| 192 | lua_pop(l, 1); | ||
| 193 | |||
| 194 | return cfg; | 192 | return cfg; | 
| 195 | } | 193 | } | 
| 196 | 194 | ||
| @@ -1246,7 +1244,27 @@ static int json_decode(lua_State *l) | |||
| 1246 | 1244 | ||
| 1247 | /* ===== INITIALISATION ===== */ | 1245 | /* ===== INITIALISATION ===== */ | 
| 1248 | 1246 | ||
| 1249 | int luaopen_cjson(lua_State *l) | 1247 | #if !defined(LUA_VERSION_NUM) || LUA_VERSION_NUM < 502 | 
| 1248 | /* Compatibility for Lua 5.1. | ||
| 1249 | * | ||
| 1250 | * luaL_setfuncs() is used to create a module table where the functions have | ||
| 1251 | * json_config_t as their first upvalue. Code borrowed from Lua 5.2 source. */ | ||
| 1252 | static void luaL_setfuncs (lua_State *l, const luaL_Reg *reg, int nup) | ||
| 1253 | { | ||
| 1254 | int i; | ||
| 1255 | |||
| 1256 | luaL_checkstack(l, nup, "too many upvalues"); | ||
| 1257 | for (; reg->name != NULL; reg++) { /* fill the table with given functions */ | ||
| 1258 | for (i = 0; i < nup; i++) /* copy upvalues to the top */ | ||
| 1259 | lua_pushvalue(l, -nup); | ||
| 1260 | lua_pushcclosure(l, reg->func, nup); /* closure with those upvalues */ | ||
| 1261 | lua_setfield(l, -(nup + 2), reg->name); | ||
| 1262 | } | ||
| 1263 | lua_pop(l, nup); /* remove upvalues */ | ||
| 1264 | } | ||
| 1265 | #endif | ||
| 1266 | |||
| 1267 | static int lua_cjson_new(lua_State *l) | ||
| 1250 | { | 1268 | { | 
| 1251 | luaL_Reg reg[] = { | 1269 | luaL_Reg reg[] = { | 
| 1252 | { "encode", json_encode }, | 1270 | { "encode", json_encode }, | 
| @@ -1257,28 +1275,51 @@ int luaopen_cjson(lua_State *l) | |||
| 1257 | { "encode_keep_buffer", json_cfg_encode_keep_buffer }, | 1275 | { "encode_keep_buffer", json_cfg_encode_keep_buffer }, | 
| 1258 | { "refuse_invalid_numbers", json_cfg_refuse_invalid_numbers }, | 1276 | { "refuse_invalid_numbers", json_cfg_refuse_invalid_numbers }, | 
| 1259 | { "update_locale", json_update_locale }, | 1277 | { "update_locale", json_update_locale }, | 
| 1278 | { "new", lua_cjson_new }, | ||
| 1260 | { NULL, NULL } | 1279 | { NULL, NULL } | 
| 1261 | }; | 1280 | }; | 
| 1262 | 1281 | ||
| 1263 | /* Update the current locale for g_fmt/strtod */ | 1282 | /* Update the current locale for g_fmt/strtod. | 
| 1283 | * Using different locales per-thread is not supported. */ | ||
| 1264 | fpconv_update_locale(); | 1284 | fpconv_update_locale(); | 
| 1265 | 1285 | ||
| 1266 | /* Use json_config_key as a pointer. | 1286 | /* cjson module table */ | 
| 1267 | * It's faster than using a config string, and more unique */ | 1287 | lua_newtable(l); | 
| 1268 | lua_pushlightuserdata(l, &json_config_key); | ||
| 1269 | json_create_config(l); | ||
| 1270 | lua_settable(l, LUA_REGISTRYINDEX); | ||
| 1271 | 1288 | ||
| 1272 | luaL_register(l, "cjson", reg); | 1289 | /* Register functions with config data as upvalue */ | 
| 1290 | json_create_config(l); | ||
| 1291 | luaL_setfuncs(l, reg, 1); | ||
| 1273 | 1292 | ||
| 1274 | /* Set cjson.null */ | 1293 | /* Set cjson.null */ | 
| 1275 | lua_pushlightuserdata(l, NULL); | 1294 | lua_pushlightuserdata(l, NULL); | 
| 1276 | lua_setfield(l, -2, "null"); | 1295 | lua_setfield(l, -2, "null"); | 
| 1277 | 1296 | ||
| 1278 | /* Set cjson.version */ | 1297 | /* Set module name / version fields */ | 
| 1298 | lua_pushliteral(l, CJSON_MODNAME); | ||
| 1299 | lua_setfield(l, -2, "_NAME"); | ||
| 1300 | lua_pushliteral(l, CJSON_VERSION); | ||
| 1301 | lua_setfield(l, -2, "_VERSION"); | ||
| 1279 | lua_pushliteral(l, CJSON_VERSION); | 1302 | lua_pushliteral(l, CJSON_VERSION); | 
| 1280 | lua_setfield(l, -2, "version"); | 1303 | lua_setfield(l, -2, "version"); | 
| 1281 | 1304 | ||
| 1305 | return 1; | ||
| 1306 | } | ||
| 1307 | |||
| 1308 | int luaopen_cjson(lua_State *l) | ||
| 1309 | { | ||
| 1310 | lua_cjson_new(l); | ||
| 1311 | |||
| 1312 | #if !defined(DISABLE_CJSON_GLOBAL) && (!defined(LUA_VERSION_NUM) || LUA_VERSION_NUM < 502) | ||
| 1313 | /* Register a global "cjson" table to maintain compatibility with earlier | ||
| 1314 | * versions of Lua CJSON which used luaL_register() under Lua 5.1. | ||
| 1315 | * | ||
| 1316 | * From Lua 5.2 onwards, Lua CJSON does not automatically register a global | ||
| 1317 | * table. | ||
| 1318 | */ | ||
| 1319 | lua_pushvalue(l, -1); | ||
| 1320 | lua_setglobal(l, CJSON_MODNAME); | ||
| 1321 | #endif | ||
| 1322 | |||
| 1282 | /* Return cjson table */ | 1323 | /* Return cjson table */ | 
| 1283 | return 1; | 1324 | return 1; | 
| 1284 | } | 1325 | } | 
