prefect server in zig

fix use-after-free in retry scheduling

stack buffer for scheduled_time was escaping scope via ctx.scheduleRetry().
moved buffer to RuleContext struct to ensure lifetime.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

+5 -3
+2 -3
src/orchestration/flow_rules.zig
··· 142 142 const now_us = time_util.nowMicros(); 143 143 const scheduled_us = now_us + delay_seconds * 1_000_000; 144 144 145 - // format as ISO timestamp using stack buffer 146 - var buf: [32]u8 = undefined; 147 - const scheduled_time = time_util.formatMicros(&buf, scheduled_us); 145 + // format as ISO timestamp using context's buffer (not stack buffer - avoids use-after-free) 146 + const scheduled_time = time_util.formatMicros(&ctx._retry_time_buf, scheduled_us); 148 147 149 148 ctx.scheduleRetry("Retrying", scheduled_time); 150 149 }
+3
src/orchestration/rules.zig
··· 49 49 retry_state_name: ?[]const u8 = null, 50 50 retry_scheduled_time: ?[]const u8 = null, 51 51 52 + // internal buffer for retry_scheduled_time (to avoid use-after-free from stack buffers) 53 + _retry_time_buf: [32]u8 = undefined, 54 + 52 55 // empirical_policy mutation flags (set by RetryFailedFlows) 53 56 // when set, API handler should update the policy JSON accordingly 54 57 set_retry_type_in_process: bool = false, // set retry_type = "in_process"