mirror of
https://github.com/ziglang/zig.git
synced 2025-12-06 06:13:07 +00:00
std.json: avoid dangling pointers in ValueTree
Closes https://github.com/ziglang/zig/issues/5229.
This commit is contained in:
parent
73c857415e
commit
b42caff2a2
@ -1163,11 +1163,12 @@ const ArrayList = std.ArrayList;
|
|||||||
const StringArrayHashMap = std.StringArrayHashMap;
|
const StringArrayHashMap = std.StringArrayHashMap;
|
||||||
|
|
||||||
pub const ValueTree = struct {
|
pub const ValueTree = struct {
|
||||||
arena: ArenaAllocator,
|
arena: *ArenaAllocator,
|
||||||
root: Value,
|
root: Value,
|
||||||
|
|
||||||
pub fn deinit(self: *ValueTree) void {
|
pub fn deinit(self: *ValueTree) void {
|
||||||
self.arena.deinit();
|
self.arena.deinit();
|
||||||
|
self.arena.child_allocator.destroy(self.arena);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1809,8 +1810,12 @@ pub const Parser = struct {
|
|||||||
pub fn parse(p: *Parser, input: []const u8) !ValueTree {
|
pub fn parse(p: *Parser, input: []const u8) !ValueTree {
|
||||||
var s = TokenStream.init(input);
|
var s = TokenStream.init(input);
|
||||||
|
|
||||||
var arena = ArenaAllocator.init(p.allocator);
|
var arena = try p.allocator.create(ArenaAllocator);
|
||||||
|
errdefer p.allocator.destroy(arena);
|
||||||
|
|
||||||
|
arena.* = ArenaAllocator.init(p.allocator);
|
||||||
errdefer arena.deinit();
|
errdefer arena.deinit();
|
||||||
|
|
||||||
const allocator = arena.allocator();
|
const allocator = arena.allocator();
|
||||||
|
|
||||||
while (try s.next()) |token| {
|
while (try s.next()) |token| {
|
||||||
|
|||||||
@ -2589,6 +2589,24 @@ test "parsing empty string gives appropriate error" {
|
|||||||
try testing.expectError(error.UnexpectedEndOfJson, testParse(arena_allocator.allocator(), ""));
|
try testing.expectError(error.UnexpectedEndOfJson, testParse(arena_allocator.allocator(), ""));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
test "parse tree should not contain dangling pointers" {
|
||||||
|
var arena_allocator = std.heap.ArenaAllocator.init(std.testing.allocator);
|
||||||
|
defer arena_allocator.deinit();
|
||||||
|
|
||||||
|
var p = json.Parser.init(arena_allocator.allocator(), false);
|
||||||
|
defer p.deinit();
|
||||||
|
|
||||||
|
var tree = try p.parse("[]");
|
||||||
|
defer tree.deinit();
|
||||||
|
|
||||||
|
// Allocation should succeed
|
||||||
|
var i: usize = 0;
|
||||||
|
while (i < 100) : (i += 1) {
|
||||||
|
try tree.root.Array.append(std.json.Value{ .Integer = 100 });
|
||||||
|
}
|
||||||
|
try testing.expectEqual(tree.root.Array.items.len, 100);
|
||||||
|
}
|
||||||
|
|
||||||
test "integer after float has proper type" {
|
test "integer after float has proper type" {
|
||||||
var arena_allocator = std.heap.ArenaAllocator.init(std.testing.allocator);
|
var arena_allocator = std.heap.ArenaAllocator.init(std.testing.allocator);
|
||||||
defer arena_allocator.deinit();
|
defer arena_allocator.deinit();
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user