[lua] Fix crashes setting values out of bounds in JSON objects (fix #4166)

This commit is contained in:
David Capello 2023-11-30 18:40:02 -03:00
parent 82375462ae
commit eeb5be9bed
3 changed files with 36 additions and 7 deletions

View File

@ -159,15 +159,14 @@ int JsonObj_newindex(lua_State* L)
auto obj = get_obj<JsonObj>(L, 1);
if (obj->type() == json11::Json::OBJECT) {
if (auto key = lua_tostring(L, 2)) {
// TODO ugly hack, but it works
const_cast<std::map<std::string, json11::Json>&>
(obj->object_items())[key] = get_json_value(L, 3);
obj->set_object_item(key, get_json_value(L, 3));
}
}
else if (obj->type() == json11::Json::ARRAY) {
auto i = lua_tointeger(L, 2) - 1; // Adjust to 0-based index
const_cast<std::vector<json11::Json>&>
(obj->array_items())[i] = get_json_value(L, 3);
auto i = lua_tointeger(L, 2);
// Adjust to 0-based index
if (i > 0)
obj->set_array_item(i-1, get_json_value(L, 3));
}
return 0;
}

View File

@ -71,3 +71,33 @@ do
assert(obj.d[2] == 8)
assert(obj.d[3].a == 2)
end
-- Test crash setting fields (index out of bounds, or setting a field
-- in an array object, etc.).
-- https://github.com/aseprite/aseprite/issues/4166
do
local o = json.decode('{"a":[10,20,30]}')
assert(#o == 1)
assert(#o.a == 3)
assert(o.a[1] == 10)
assert(o.a[2] == 20)
assert(o.a[3] == 30)
assert(o.a[4] == nil)
assert(o.a["b"] == nil)
o.a[4] = 40
assert(#o.a == 4)
assert(o.a[4] == 40)
-- Cannot add a map field to an array
o.a.b = "d"
assert(o.a.b == nil)
-- Creating a field that is an object and set a field
o.b = { c=1 }
o.b.d = 2
assert(o.b.c == 1)
assert(o.b.d == 2)
assert(tostring(o) == '{"a": [10, 20, 30, 40], "b": {"c": 1, "d": 2}}')
end

2
third_party/json11 vendored

@ -1 +1 @@
Subproject commit 818c5e01e76c2cee2103a9ba05d74f7d3fc05eaa
Subproject commit e5868fff1fc5128077ed7699bdaa20ae47c47eca