| ... | ... | @@ -39,7 +39,7 @@ test_results: TestResults, |
| 39 | 39 | |
| 40 | 40 | /// The return address associated with creation of this step that can be useful |
| 41 | 41 | /// to print along with debugging messages. |
| 42 | | debug_stack_trace: [n_debug_stack_frames]usize, |
| 42 | debug_stack_trace: []usize, |
| 43 | 43 | |
| 44 | 44 | pub const TestResults = struct { |
| 45 | 45 | fail_count: u32 = 0, |
| ... | ... | @@ -58,8 +58,6 @@ pub const TestResults = struct { |
| 58 | 58 | |
| 59 | 59 | pub const MakeFn = *const fn (self: *Step, prog_node: *std.Progress.Node) anyerror!void; |
| 60 | 60 | |
| 61 | | const n_debug_stack_frames = 4; |
| 62 | | |
| 63 | 61 | pub const State = enum { |
| 64 | 62 | precheck_unstarted, |
| 65 | 63 | precheck_started, |
| ... | ... | @@ -140,14 +138,6 @@ pub const StepOptions = struct { |
| 140 | 138 | pub fn init(options: StepOptions) Step { |
| 141 | 139 | const arena = options.owner.allocator; |
| 142 | 140 | |
| 143 | | var addresses = [1]usize{0} ** n_debug_stack_frames; |
| 144 | | const first_ret_addr = options.first_ret_addr orelse @returnAddress(); |
| 145 | | var stack_trace = std.builtin.StackTrace{ |
| 146 | | .instruction_addresses = &addresses, |
| 147 | | .index = 0, |
| 148 | | }; |
| 149 | | std.debug.captureStackTrace(first_ret_addr, &stack_trace); |
| 150 | | |
| 151 | 141 | return .{ |
| 152 | 142 | .id = options.id, |
| 153 | 143 | .name = arena.dupe(u8, options.name) catch @panic("OOM"), |
| ... | ... | @@ -157,7 +147,17 @@ pub fn init(options: StepOptions) Step { |
| 157 | 147 | .dependants = .{}, |
| 158 | 148 | .state = .precheck_unstarted, |
| 159 | 149 | .max_rss = options.max_rss, |
| 160 | | .debug_stack_trace = addresses, |
| 150 | .debug_stack_trace = blk: { |
| 151 | const addresses = arena.alloc(usize, options.owner.debug_stack_frames_count) catch @panic("OOM"); |
| 152 | @memset(addresses, 0); |
| 153 | const first_ret_addr = options.first_ret_addr orelse @returnAddress(); |
| 154 | var stack_trace = std.builtin.StackTrace{ |
| 155 | .instruction_addresses = addresses, |
| 156 | .index = 0, |
| 157 | }; |
| 158 | std.debug.captureStackTrace(first_ret_addr, &stack_trace); |
| 159 | break :blk addresses; |
| 160 | }, |
| 161 | 161 | .result_error_msgs = .{}, |
| 162 | 162 | .result_error_bundle = std.zig.ErrorBundle.empty, |
| 163 | 163 | .result_cached = false, |
| ... | ... | @@ -199,14 +199,14 @@ pub fn dependOn(self: *Step, other: *Step) void { |
| 199 | 199 | self.dependencies.append(other) catch @panic("OOM"); |
| 200 | 200 | } |
| 201 | 201 | |
| 202 | | pub fn getStackTrace(s: *Step) std.builtin.StackTrace { |
| 203 | | const stack_addresses = &s.debug_stack_trace; |
| 202 | pub fn getStackTrace(s: *Step) ?std.builtin.StackTrace { |
| 204 | 203 | var len: usize = 0; |
| 205 | | while (len < n_debug_stack_frames and stack_addresses[len] != 0) { |
| 204 | while (len < s.debug_stack_trace.len and s.debug_stack_trace[len] != 0) { |
| 206 | 205 | len += 1; |
| 207 | 206 | } |
| 208 | | return .{ |
| 209 | | .instruction_addresses = stack_addresses, |
| 207 | |
| 208 | return if (len == 0) null else .{ |
| 209 | .instruction_addresses = s.debug_stack_trace, |
| 210 | 210 | .index = len, |
| 211 | 211 | }; |
| 212 | 212 | } |
| ... | ... | @@ -231,13 +231,9 @@ pub fn cast(step: *Step, comptime T: type) ?*T { |
| 231 | 231 | } |
| 232 | 232 | |
| 233 | 233 | /// For debugging purposes, prints identifying information about this Step. |
| 234 | | pub fn dump(step: *Step) void { |
| 235 | | std.debug.getStderrMutex().lock(); |
| 236 | | defer std.debug.getStderrMutex().unlock(); |
| 237 | | |
| 238 | | const stderr = std.io.getStdErr(); |
| 239 | | const w = stderr.writer(); |
| 240 | | const tty_config = std.io.tty.detectConfig(stderr); |
| 234 | pub fn dump(step: *Step, file: std.fs.File) void { |
| 235 | const w = file.writer(); |
| 236 | const tty_config = std.io.tty.detectConfig(file); |
| 241 | 237 | const debug_info = std.debug.getSelfDebugInfo() catch |err| { |
| 242 | 238 | w.print("Unable to dump stack trace: Unable to open debug info: {s}\n", .{ |
| 243 | 239 | @errorName(err), |
| ... | ... | @@ -245,11 +241,19 @@ pub fn dump(step: *Step) void { |
| 245 | 241 | return; |
| 246 | 242 | }; |
| 247 | 243 | const ally = debug_info.allocator; |
| 248 | | w.print("name: '{s}'. creation stack trace:\n", .{step.name}) catch {}; |
| 249 | | std.debug.writeStackTrace(step.getStackTrace(), w, ally, debug_info, tty_config) catch |err| { |
| 250 | | stderr.writer().print("Unable to dump stack trace: {s}\n", .{@errorName(err)}) catch {}; |
| 251 | | return; |
| 252 | | }; |
| 244 | if (step.getStackTrace()) |stack_trace| { |
| 245 | w.print("name: '{s}'. creation stack trace:\n", .{step.name}) catch {}; |
| 246 | std.debug.writeStackTrace(stack_trace, w, ally, debug_info, tty_config) catch |err| { |
| 247 | w.print("Unable to dump stack trace: {s}\n", .{@errorName(err)}) catch {}; |
| 248 | return; |
| 249 | }; |
| 250 | } else { |
| 251 | const field = "debug_stack_frames_count"; |
| 252 | comptime assert(@hasField(Build, field)); |
| 253 | tty_config.setColor(w, .yellow) catch {}; |
| 254 | w.print("name: '{s}'. no stack trace collected for this step, see std.Build." ++ field ++ "\n", .{step.name}) catch {}; |
| 255 | tty_config.setColor(w, .reset) catch {}; |
| 256 | } |
| 253 | 257 | } |
| 254 | 258 | |
| 255 | 259 | const Step = @This(); |