webmcp

changeset 123:402fce94f98c

Added function json.isnull(...) to JSON library
author jbe
date Sat Jul 26 05:27:42 2014 +0200 (2014-07-26)
parents ff39d4a310b9
children ece4e6f683c9
files libraries/json/json.c
line diff
     1.1 --- a/libraries/json/json.c	Fri Jul 25 22:50:12 2014 +0200
     1.2 +++ b/libraries/json/json.c	Sat Jul 26 05:27:42 2014 +0200
     1.3 @@ -3,6 +3,9 @@
     1.4  #include <stdlib.h>
     1.5  #include <string.h>
     1.6  
     1.7 +#define JSON_UPVAL_ARYLEN lua_upvalueindex(1)
     1.8 +#define JSON_UPVAL_NULLS lua_upvalueindex(2)
     1.9 +
    1.10  #define JSON_VALUE 0
    1.11  #define JSON_OBJECT_KEY 1
    1.12  #define JSON_OBJECT_KEY_TERMINATOR 2
    1.13 @@ -41,6 +44,10 @@
    1.14        goto json_import_syntax_error;
    1.15      pos++;
    1.16      lua_newtable(L);
    1.17 +    lua_newtable(L);  // stores set of NULL values
    1.18 +    lua_pushvalue(L, -2);
    1.19 +    lua_pushvalue(L, -2);
    1.20 +    lua_rawset(L, JSON_UPVAL_NULLS);
    1.21      mode = JSON_OBJECT_KEY;
    1.22      level++;
    1.23      goto json_import_loop;
    1.24 @@ -49,6 +56,10 @@
    1.25        goto json_import_syntax_error;
    1.26      pos++;
    1.27      lua_newtable(L);
    1.28 +    lua_newtable(L);  // stores set of NULL values
    1.29 +    lua_pushvalue(L, -2);
    1.30 +    lua_pushvalue(L, -2);
    1.31 +    lua_rawset(L, JSON_UPVAL_NULLS);
    1.32      lua_pushinteger(L, 0);  // length of array (since it may contain nil's)
    1.33      mode = JSON_ARRAY_VALUE;
    1.34      level++;
    1.35 @@ -62,10 +73,11 @@
    1.36        goto json_import_syntax_error;
    1.37      lua_pushvalue(L, -2);  // use array table as key
    1.38      lua_insert(L, -2);  // use length of array as value
    1.39 -    lua_rawset(L, lua_upvalueindex(1));  // store length in ephemeron table
    1.40 +    lua_rawset(L, JSON_UPVAL_ARYLEN);  // store length in ephemeron table
    1.41      // leaves array table on top of stack
    1.42    json_import_close:
    1.43      pos++;
    1.44 +    lua_pop(L, 1);  // pop table that stores set of NULL values
    1.45      if (--level) {
    1.46        if (lua_type(L, -2) == LUA_TNUMBER) {
    1.47          mode = JSON_ARRAY_VALUE;
    1.48 @@ -172,12 +184,22 @@
    1.49      mode = JSON_OBJECT_KEY_TERMINATOR;
    1.50      goto json_import_loop;
    1.51    case JSON_OBJECT_VALUE:
    1.52 -    lua_rawset(L, -3);
    1.53 +    if (lua_isnil(L, -1)) {
    1.54 +      lua_pushvalue(L, -2);
    1.55 +      lua_pushboolean(L, 1);
    1.56 +      lua_rawset(L, -5);
    1.57 +    }
    1.58 +    lua_rawset(L, -4);
    1.59      mode = JSON_OBJECT_SEPARATOR;
    1.60      goto json_import_loop;
    1.61    case JSON_ARRAY_VALUE:
    1.62      aryidx = lua_tointeger(L, -2) + 1;
    1.63 -    lua_rawseti(L, -3, aryidx);
    1.64 +    if (lua_isnil(L, -1)) {
    1.65 +      lua_pushinteger(L, aryidx);
    1.66 +      lua_pushboolean(L, 1);
    1.67 +      lua_rawset(L, -5);
    1.68 +    }
    1.69 +    lua_rawseti(L, -4, aryidx);
    1.70      lua_pop(L, 1);
    1.71      lua_pushinteger(L, aryidx);
    1.72      mode = JSON_ARRAY_SEPARATOR;
    1.73 @@ -194,24 +216,40 @@
    1.74  
    1.75  static int json_arylen(lua_State *L) {
    1.76    lua_settop(L, 1);
    1.77 -  lua_rawget(L, lua_upvalueindex(1));
    1.78 +  lua_rawget(L, JSON_UPVAL_ARYLEN);
    1.79 +  return 1;
    1.80 +}
    1.81 +
    1.82 +static int json_isnull(lua_State *L) {
    1.83 +  lua_pushvalue(L, 1);
    1.84 +  lua_rawget(L, JSON_UPVAL_NULLS);
    1.85 +  if (lua_isnil(L, -1)) goto json_isnull_false;
    1.86 +  lua_pushvalue(L, 2);
    1.87 +  lua_rawget(L, -2);
    1.88 +  if (!lua_isnil(L, -1)) return 1;
    1.89 +json_isnull_false:
    1.90 +  lua_pushboolean(L, 0);
    1.91    return 1;
    1.92  }
    1.93  
    1.94  static const struct luaL_Reg json_module_functions[] = {
    1.95    {"import", json_import},
    1.96    {"arylen", json_arylen},
    1.97 +  {"isnull", json_isnull},
    1.98    {NULL, NULL}
    1.99  };
   1.100  
   1.101  int luaopen_json(lua_State *L) {
   1.102    lua_newtable(L);  // library table
   1.103    lua_newtable(L);  // ephemeron table to store the length of arrays (that may contain nil's)
   1.104 +  lua_newtable(L);  // ephemeron table to store a set of keys associated with JSON-null values
   1.105    lua_newtable(L);  // meta table for ephemeron table
   1.106    lua_pushliteral(L, "__mode");
   1.107    lua_pushliteral(L, "k");
   1.108    lua_rawset(L, -3);
   1.109 +  lua_pushvalue(L, -1);
   1.110 +  lua_setmetatable(L, -3);
   1.111    lua_setmetatable(L, -2);
   1.112 -  luaL_setfuncs(L, json_module_functions, 1);
   1.113 +  luaL_setfuncs(L, json_module_functions, 2);
   1.114    return 1;
   1.115  }

Impressum / About Us