Comparative Analysis of Numerical Methods for Solving the Discrete Algebraic Riccati Equation in Resource-Constrained Embedded Systems — data and code
Replication package for the paper submitted to DINAME 2027 (XXI International Symposium on Dynamic Problems of Mechanics, ABCM): "Comparative Analysis of Numerical Methods for Solving the Discrete Algebraic Riccati Equation in Resource-Constrained Embedded Systems". Stabilising a small quadrotor demands feedback above 50 Hz, and with the state-dependent Riccati equation (SDRE) method that forces a discrete algebraic Riccati equation (DARE) to be solved once per control period — the dominant cost on a microcontroller with no hardware floating-point unit. This work formulates the structure-preserving doubling algorithm, four variants and classical value iteration in Q13.18 fixed point, and compares the twelve resulting solvers on an FPU-less ESP32-S2 over 60000 operating points drawn from six trajectories, and over 475444 consecutive hardware control cycles of the complete flight loop at 167 Hz. The central result is a matrix generalisation of the classical recursive-filter deadband: near convergence the relative step reports the number format rather than the solution, below an analytic floor set by format resolution and solution norm. Measuring that step at the instant each solver stops resolves the deadband into two opposite symptoms — a bit-exact fixed point in quadratically convergent doubling, and a one-least-significant-bit limit cycle in linearly convergent value iteration. CONTENTS raw.zip — the 20 serial captures exactly as they came off the boards: the main benchmark on the ESP32-S2 and on the ESP32-S3 (which has an FPU), the tolerance and weighting sweeps, the repeatability and convergence-test microbenchmarks, and the ten 360-second windows of the complete flight loop. Each capture begins with a provenance stamp giving the git commit, build timestamp, chip, revision and clock of the firmware that produced it. derived.zip — the same measurements as tabular CSV with headers: one row per solver call (time, iterations, achieved residual, outcome, and the relative step and bit-exactness flag at termination), the closed-loop cost and time series for all six trajectories, the operating-point coverage with conditioning and solution norm, the double-precision reference residual, and the firmware memory metrics. code.zip — snapshot of the repository at the commit that produced these measurements: the flight firmware, the eight experiment firmwares, the twelve solver implementations in C++ and the Python analysis, audit and figure-generation scripts. MANIFEST.md — SHA-256 of every file, and the git commit of origin. README.md — what each file contains and how to recompute the published numbers. PROVENANCE.md — the provenance of the captures: what the audit reports about them and why it reports it. REPRODUCING With the code and the captures in place, every number and figure in the paper can be recomputed without the hardware. An audit script checks the provenance stamp of each capture, verifies 253 numerical claims against the raw data, confirms that the figures were generated from the current measurements, and reports how many of the numbers in the paper are covered by an automated check. On this package its numerical, figure and flight-cycle steps all report zero divergences. The provenance step is the exception, and the record says so rather than hiding it: it reports eight of the nine captures as taken from a modified working tree, because the campaign ran overnight with the change to the convergence test not yet committed. PROVENANCE.md, at the top level of this record, sets out why those captures remain traceable — all nine came from the same build, the exact working-tree diff travels with them in raw/provenance/, and the one experiment recaptured after the commit returned seven measured quantities identical to the hundredth of a microsecond. The defect is in the label, not in the data. That the recipe works was established on version 3, reproduced end to end from its own package alone: following README.md, all six figures came back pixel-for-pixel identical to the published ones. Re-running the measurements from scratch requires an ESP32-S2 and an ESP32-S3 and takes about ten hours. VERSIONS Version 1 (10.5281/zenodo.22236199) was created automatically by the GitHub–Zenodo integration and contains only the source archive; it does not include the serial captures, which are not tracked in the git repository. Version 2 (10.5281/zenodo.22236293) was the first complete package. Its MANIFEST.md, however, lists SHA-256 checksums for the three zip archives that do not match those archives — the manifest was written before the archives were repacked. The archives themselves are intact, but the document meant to prove that is wrong, so anyone verifying integrity against it would wrongly conclude the download was corrupt. Its README.md also numbers two figures one off and omits a renaming step, without which the reproduction recipe does not run. Version 3 (10.5281/zenodo.22238478) carries the same measurement data as version 2. It corrects the manifest, the figure numbering and the reproduction recipe, adds the firmware memory metrics in the form the audit reads, and removes a nested archive inside code.zip. Version 4 is this one, and it is the first whose measurements differ. Every capture in raw.zip was taken again, after the convergence test in the Q13.18 kernel was changed to evaluate its inequality in integer arithmetic instead of converting each stored value to floating point. The criterion itself is unchanged — the same relative Frobenius norm, the same tolerance, the same iteration budget, the same decisions — and the integer form is exact where the converted form rounded, so what changed is the cost of asking, not the answer. The scientific results reproduce unaltered: the deadband floor and its two symptoms, the bit-exact counts, the convergence counts of value iteration, the weighting safety map, and the closed-loop accumulated cost. The times fall: the fastest fixed-point doubling solver from 3.68 to 3.15 ms, and the complete flight cycle from a median of 4.70 to 4.20 ms, with period overruns dropping from 21 to 2 in roughly 475000 cycles. The paper's title also changed in this version, to the one under which the abstract was accepted. SOURCE https://github.com/guilherme-ali/SDRE_VECTORIZED LICENCE Measurement data (raw.zip and derived.zip) and figures: CC BY 4.0. Software (everything in code.zip): MIT.