# HG changeset patch # User jbe # Date 1406677077 -7200 # Node ID 641619d3fcb150ca812ec25fdcf97c571e99c03a # Parent a4ce17051eff38e7e71cbea248d8ecf3a25d11a5 Fixed problem with unbalanced stack in json.import(...) function diff -r a4ce17051eff -r 641619d3fcb1 libraries/json/json.c --- a/libraries/json/json.c Tue Jul 29 22:02:01 2014 +0200 +++ b/libraries/json/json.c Wed Jul 30 01:37:57 2014 +0200 @@ -162,6 +162,8 @@ lua_pushvalue(L, -2); lua_pushvalue(L, -2); lua_rawset(L, json_import_shadowtbl_idx); + // add nil as key (needed to keep stack balance) and as magic to detect arrays: + lua_pushnil(L); // increment level: level++; // expect array value (or end of array) and continue with loop: @@ -179,6 +181,8 @@ // if end of JSON array is not expected here, then return an error: if (mode != JSON_STATE_ARRAY_VALUE && mode != JSON_STATE_ARRAY_SEPARATOR) goto json_import_syntax_error; + // pop nil key/magic: + lua_pop(L, 1); // continue with common code for end of JSON object and JSON array: // common code for end of JSON object or JSON array: json_import_close: @@ -189,23 +193,17 @@ // check if nested: if (--level) { // if nested, then check if outer(!) structure is an array or object: - lua_getmetatable(L, c == '}' ? -4 : -3); // TODO: this approach doesn't work, because objects have an extra key on stack! - if (lua_rawequal(L, -1, json_import_arraymt_idx)) { + if (lua_isnil(L, -2)) { // select array value processing: - fprintf(stderr, "DEBUG: Process array\n"); mode = JSON_STATE_ARRAY_VALUE; } else { // select object value processing: - fprintf(stderr, "DEBUG: Process object\n"); mode = JSON_STATE_OBJECT_VALUE; } - // pop metatable from stack (that was needed for type distinction): - lua_pop(L, 1); // store value in outer structure: goto json_import_process_value; } // if not nested, then expect end of JSON document and continue with loop: - fprintf(stderr, "DEBUG: Process document\n"); mode = JSON_STATE_END; goto json_import_loop; // key terminator: @@ -354,7 +352,7 @@ // an array value has been read: case JSON_STATE_ARRAY_VALUE: // store value in outer shadow table: - lua_rawseti(L, -2, lua_rawlen(L, -2) + 1); + lua_rawseti(L, -3, lua_rawlen(L, -3) + 1); // expect value terminator (or end of object) and continue with loop: mode = JSON_STATE_ARRAY_SEPARATOR; goto json_import_loop;