From 0283222e3aebc0a3ccaee08265260729a779611e Mon Sep 17 00:00:00 2001 From: Alexandros Naskos Date: Thu, 7 May 2020 12:50:25 +0300 Subject: [PATCH] Added build option to enable the leak counting allocator. Log the allocation count to the client at the end of the main loop. Fixed two memory leaks in analysis.zig --- build.zig | 6 ++++++ src/analysis.zig | 6 ++++-- src/main.zig | 23 +++++++++++++++++++---- 3 files changed, 29 insertions(+), 6 deletions(-) diff --git a/build.zig b/build.zig index 5bea2c8..b6768c9 100644 --- a/build.zig +++ b/build.zig @@ -16,6 +16,12 @@ pub fn build(b: *std.build.Builder) void { exe.addPackagePath("data", "src/data/0.6.0.zig"); + exe.addBuildOption( + bool, + "leak_detection", + b.option(bool, "leak_detection", "Use testing.LeakCountAllocator to track leaks.") orelse false, + ); + exe.setTarget(target); exe.setBuildMode(mode); exe.install(); diff --git a/src/analysis.zig b/src/analysis.zig index 7940482..2fee411 100644 --- a/src/analysis.zig +++ b/src/analysis.zig @@ -30,12 +30,13 @@ pub fn getDocComments(allocator: *std.mem.Allocator, tree: *std.zig.ast.Tree, no if (func.doc_comments) |doc_comments| { var doc_it = doc_comments.lines.iterator(0); var lines = std.ArrayList([]const u8).init(allocator); + defer lines.deinit(); while (doc_it.next()) |doc_comment| { _ = try lines.append(std.fmt.trim(tree.tokenSlice(doc_comment.*)[3..])); } - return try std.mem.join(allocator, "\n", lines.toOwnedSlice()); + return try std.mem.join(allocator, "\n", lines.items); } else { return null; } @@ -45,12 +46,13 @@ pub fn getDocComments(allocator: *std.mem.Allocator, tree: *std.zig.ast.Tree, no if (var_decl.doc_comments) |doc_comments| { var doc_it = doc_comments.lines.iterator(0); var lines = std.ArrayList([]const u8).init(allocator); + defer lines.deinit(); while (doc_it.next()) |doc_comment| { _ = try lines.append(std.fmt.trim(tree.tokenSlice(doc_comment.*)[3..])); } - return try std.mem.join(allocator, "\n", lines.toOwnedSlice()); + return try std.mem.join(allocator, "\n", lines.items); } else { return null; } diff --git a/src/main.zig b/src/main.zig index b355a2e..9c9f4ea 100644 --- a/src/main.zig +++ b/src/main.zig @@ -164,7 +164,8 @@ pub fn completeGlobal(id: i64, document: types.TextDocument) !void { var completions = std.ArrayList(types.CompletionItem).init(allocator); - // try log("{}", .{&tree.root_node.decls}); + // @TODO + try log("{}", .{&tree.root_node.decls}); var decls = tree.root_node.decls.iterator(0); while (decls.next()) |decl_ptr| { @@ -356,9 +357,14 @@ pub fn processJsonRpc(json: []const u8) !void { } else { try log("Method without return value not implemented: {}", .{method}); } - } +const use_leak_count_alloc = @import("build_options").leak_detection; + +var leak_alloc_global: std.testing.LeakCountAllocator = undefined; +// We can now use if(leak_count_alloc) |alloc| { ... } as a comptime check. +const leak_count_alloc: ?*std.testing.LeakCountAllocator = if (use_leak_count_alloc) &leak_alloc_global else null; + pub fn main() anyerror!void { // Init memory @@ -367,6 +373,12 @@ pub fn main() anyerror!void { defer arena.deinit(); allocator = &arena.allocator; + if (use_leak_count_alloc) { + // Initialize the leak counting allocator. + leak_alloc_global = std.testing.LeakCountAllocator.init(allocator); + allocator = &leak_alloc_global.allocator; + } + // Init buffer for stdin read var buffer = std.ArrayList(u8).init(allocator); @@ -391,7 +403,7 @@ pub fn main() anyerror!void { // var bytes = stdin.read(buffer.items[0..6]) catch return; - if (offset >= 16 and std.mem.eql(u8, "Content-Length: ", buffer.items[0..16])) { + if (offset >= 16 and std.mem.startsWith(u8, buffer.items, "Content-Length: ")) { index = 16; while (index <= offset + 10) : (index += 1) { @@ -430,7 +442,7 @@ pub fn main() anyerror!void { } } else if (offset >= 16) { - try log("Offset is greater than 16!", .{}); + try log("OffseOt is greater than 16!", .{}); return; } @@ -460,5 +472,8 @@ pub fn main() anyerror!void { offset += bytes_read; + if (leak_count_alloc) |leaks| { + try log("Allocations alive after message: {}", .{leaks.count}); + } } }