%% SCRAP: architecture/03-architecture/heartbeat-system/implementation-plan %% SOURCE: docs/working/architecture/03-architecture/heartbeat-system/implementation-plan.md %% STATUS: HISTORICAL %% FITS: dev-guide/ch-heartbeat %% EDITORIAL: lifted — prose rewritten to press voice \section{Implementation Plan: Heartbeat Rate Logging} This plan captures the \lstinline{tick_ns} trajectory---the heartbeat rate as it actually changes during execution---so that each configuration can be analyzed for how well it modulates heartrate in response to workload. The work was scoped as a prerequisite to the Phase 2 DoE and touches four files. \subsection{Data Structures} A per-sample record and a buffer carried on the VM hold the trajectory. \begin{lstlisting}[language=C] #define HEARTBEAT_RATE_SAMPLE_MAX 100000 typedef struct { uint64_t tick_number; /* absolute tick count */ uint64_t tick_ns; /* heartbeat rate (ns) */ uint64_t workload_ops_this_tick; /* dictionary lookups this tick */ uint64_t timestamp_ns; /* wall-clock timestamp */ uint64_t hot_word_count; /* physics state */ uint64_t total_heat; /* physics state */ } HeartbeatRateSample; /* in VM */ HeartbeatRateSample *heartbeat_rate_samples; uint64_t heartbeat_rate_sample_count; uint64_t workload_ops_current_tick; \end{lstlisting} The buffer is allocated with \lstinline{calloc} in \lstinline{vm_init()} and released in \lstinline{vm_cleanup()}. \subsection{Capturing a Sample Per Tick} A lightweight helper writes one sample per tick, halting once the buffer is full so sampling never overruns its allocation. \begin{lstlisting}[language=C] static void capture_heartbeat_rate_sample(VM *vm, uint64_t tick_ns, uint64_t workload_ops) { if (!vm || !vm->heartbeat_rate_samples) return; if (vm->heartbeat_rate_sample_count >= HEARTBEAT_RATE_SAMPLE_MAX) return; HeartbeatRateSample *s = &vm->heartbeat_rate_samples[vm->heartbeat_rate_sample_count]; s->tick_number = vm->heartbeat.tick_count; s->tick_ns = tick_ns; s->workload_ops_this_tick = workload_ops; s->timestamp_ns = platform_monotonic_ns(); s->hot_word_count = vm->hot_word_count_at_check; s->total_heat = vm->total_heat_at_last_check; vm->heartbeat_rate_sample_count++; } \end{lstlisting} The interpreter increments \lstinline{workload_ops_current_tick} on each successful dictionary lookup; \lstinline{vm_heartbeat_run_cycle()} latches and resets that counter per tick; and \lstinline{heartbeat_thread_main()} calls the capture helper immediately before sleeping for \lstinline{tick_ns}. \subsection{Derived Metrics} The DoE metrics structure gains heartrate fields covering rate statistics (mean frequency, standard deviation, coefficient of variation, min/max interval, modulation range), load response (correlation, response direction, adaptation and settling latency), convergence (convergence time, a converged flag, oscillation amplitude), and two composite scores for responsiveness and stability. The analysis routine \lstinline{analyze_heartbeat_rate_trajectory()} walks the captured samples to compute these. Frequency is $f_{\text{Hz}} = 10^{9} / \mathtt{tick\_ns}$. The coefficient of variation is \begin{equation} \mathrm{CV} = \frac{\sigma_{f}}{\bar{f}}, \end{equation} and the headline figure is the Pearson correlation between per-tick workload and heartrate. A correlation above a small positive threshold marks the configuration as responding in the desired direction. The responsiveness score rewards strong correlation and penalizes high CV; the stability score rewards low CV and convergence. \Qtype{} fixed-point is used elsewhere in the runtime, but this offline analysis runs in floating point. \subsection{CSV Schema and Downstream Analysis} The CSV writers gain columns for the new heartrate fields so each run emits one augmented row. A revised R analysis then ranks configurations primarily by mean load--heartrate correlation, blended with the responsiveness and stability scores into a single golden score, and renders correlation and responsiveness box plots across configurations. \subsection{Build and Verification} After editing \lstinline{include/vm.h}, \lstinline{include/doe_metrics.h}, \lstinline{src/vm.c}, and \lstinline{src/doe_metrics.c}, the build is \lstinline{make clean && make fastest}. Verification confirms a clean compile, a non-zero sample count after a run, the presence of the new CSV columns, computed correlation metrics, and an R ranking ordered by load response. %% TODO(bob): confirm whether this logging was implemented as written, or %% superseded by the heartbeat_export.c / HeartbeatTickSnapshot path; the two %% plans overlap and status should be reconciled.