diff --git a/src/log.zig b/src/log.zig new file mode 100644 index 0000000000000000000000000000000000000000..f5679efacfbad7cc392959eb53398f4e28114122 --- /dev/null +++ b/src/log.zig @@ -0,0 +1,19 @@ +const std = @import("std"); +const tracer = @import("./mod.zig"); +const log = std.log.scoped(.tracer); + +pub fn init() void {} + +pub fn deinit() void {} + +pub fn init2() void {} + +pub fn deinit2() void {} + +pub inline fn trace_begin(ctx: tracer.Ctx) void { + log.debug("{s}:{d}:{d} ({s})", .{ ctx.src.file, ctx.src.line, ctx.src.column, ctx.src.fn_name }); +} + +pub inline fn trace_end(ctx: tracer.Ctx) void { + _ = ctx; +} diff --git a/src/mod.zig b/src/mod.zig index 95a0b682a71942e4010a9c8ee96461fb9a3b53a3..7ebf7a1c3c4255b35ca72ba6e657e317de778fa6 100644 --- a/src/mod.zig +++ b/src/mod.zig @@ -1 +1,42 @@ const std = @import("std"); +const root = @import("root"); +const impl = std.meta.globalOption("tracer_impl", type) orelse none; + +var started = false; + +pub const none = @import("./none.zig"); +pub const log = @import("./log.zig"); +pub const spall = @import("./spall.zig"); + +pub fn init() !void { + impl.init(); +} + +pub fn deinit() void { + impl.deinit(); +} + +pub fn init2() !void { + impl.init2(); + started = true; +} + +pub fn deinit2() void { + impl.deinit2(); +} + +pub inline fn trace(src: std.builtin.SourceLocation) Ctx { + const ctx = Ctx{ + .src = src, + }; + if (started) impl.trace_begin(ctx); + return ctx; +} + +pub const Ctx = struct { + src: std.builtin.SourceLocation, + + pub inline fn end(self: Ctx) void { + if (started) impl.trace_end(self); + } +}; diff --git a/src/none.zig b/src/none.zig new file mode 100644 index 0000000000000000000000000000000000000000..154a721a8969c9c465ece986f2e661a6093f2cc7 --- /dev/null +++ b/src/none.zig @@ -0,0 +1,19 @@ +const std = @import("std"); +const tracer = @import("./mod.zig"); +const log = std.log.scoped(.tracer); + +pub fn init() void {} + +pub fn deinit() void {} + +pub fn init2() void {} + +pub fn deinit2() void {} + +pub inline fn trace_begin(ctx: tracer.Ctx) void { + _ = ctx; +} + +pub inline fn trace_end(ctx: tracer.Ctx) void { + _ = ctx; +} diff --git a/src/spall.zig b/src/spall.zig new file mode 100644 index 0000000000000000000000000000000000000000..ad4237d74bd367a4cf03b02205e10b193daeb91b --- /dev/null +++ b/src/spall.zig @@ -0,0 +1,66 @@ +const std = @import("std"); +const tracer = @import("./mod.zig"); +const alloc = std.heap.c_allocator; +const log = std.log.scoped(.tracer); +const root = @import("root"); +const trim_count = root.build_options.src_file_trimlen; + +var pid: std.os.linux.pid_t = undefined; +threadlocal var tid: std.os.linux.pid_t = undefined; +threadlocal var path: []const u8 = undefined; +threadlocal var file: std.fs.File = undefined; + +pub fn init() void { + pid = std.os.linux.getpid(); +} + +pub fn deinit() void { + // +} + +pub fn init2() void { + tid = std.os.linux.gettid(); + + path = std.fmt.allocPrint(alloc, "/data/trace.{d}.{d}.spall.jsonl", .{ pid, tid }) catch @panic("oom"); + file = std.fs.cwd().createFile(path, .{}) catch @panic("create fail"); + file.writer().writeAll("[\n") catch @panic("["); +} + +pub fn deinit2() void { + defer alloc.free(path); + defer file.close(); + + file.writer().writeAll("]\n") catch {}; + log.debug("{s}", .{path}); +} + +pub inline fn trace_begin(ctx: tracer.Ctx) void { + file.writer().print( + \\{{"cat":"function", "name":"{s}:{d}:{d} ({s})", "ph": "B", "pid": {d}, "tid": {d}, "ts": {d}}}, + \\ + , + .{ + if (ctx.src.file[0] == '/') ctx.src.file[trim_count..] else ctx.src.file, + ctx.src.line, + ctx.src.column, + ctx.src.fn_name, + pid, + tid, + std.time.microTimestamp(), + }, + ) catch {}; +} + +pub inline fn trace_end(ctx: tracer.Ctx) void { + _ = ctx; + file.writer().print( + \\{{"cat":"function", "ph": "E", "pid": {d}, "tid": {d}, "ts": {d}}}, + \\ + , + .{ + pid, + tid, + std.time.microTimestamp(), + }, + ) catch {}; +}