Faster Delta Updates
How concurrent HTTP fetching in Rugix Ctrl 1.4 makes dynamic delta updates faster on networks with latency, with benchmarks of installation time and network traffic.
- rugix
- benchmarks
- delta updates
- ota
- embedded linux
Rugix Ctrl supports dynamic delta updates, which reduce downloads by reusing data that is already on a device. Downloading only the missing data saves bandwidth, but it can still take a long time when an installer sends thousands of small HTTP requests one after another.
In Rugix Ctrl 1.4, we improved how the installer fetches that missing data. We benchmarked the new fetcher alongside Rugix Ctrl 1.3.0 and RAUC 1.15.2, another popular update engine that supports dynamic delta updates.
Across three Debian update scenarios with 40 ms of added round-trip latency, Rugix Ctrl 1.3.0 and RAUC had similar installation times. With the new fetcher, median installations were about 14–31× faster than with Rugix Ctrl 1.3.0 and RAUC 1.15.2. With no added latency, we found no consistent improvement over Rugix Ctrl 1.3.0.
We also measured network traffic in both directions. Across the three scenarios at 10 ms of added round-trip latency, Rugix Ctrl 1.3.0 transferred about 20–23% fewer bytes than RAUC, and the new fetcher transferred 25–29% fewer bytes.
Where the Time Goes
An update bundle carries a block index listing the hashes of its data chunks. A device uses the index to find chunks it can reuse locally and fetches the rest through HTTP byte-range requests. Efficient Delta Updates explains the approach in more detail.
Fetching missing chunks can require thousands of small requests. Rugix Ctrl 1.3.0 sent them sequentially and frequently opened new connections, so network round trips accumulated with every request.
Rugix Ctrl 1.4 combines adjacent missing chunks into larger ranges, reuses connections, and keeps several requests in flight at once. Downloads continue while the installer verifies, decompresses, and writes the data it has already received. These improvements are enabled by default and work with existing bundles that include block indices.
Faster Installations
We tested a monthly Bookworm update, an annual Bookworm update, and an upgrade from Bullseye to Bookworm. Each installer reconstructed the same 1.38 GiB filesystem image from a different source image per scenario.
We limited the link to 20 MiB/s, added 0, 10, or 40 ms of round-trip latency, and repeated each measurement five times. The table shows median installation times over HTTP/1.1, including downloading, decoding, verification, and writes.
| Installer | 0 ms | 10 ms | 40 ms |
|---|---|---|---|
| Rugix Ctrl 1.3.0 | 16.4 | 134.8 | 457.6 |
| Rugix Ctrl 1.4 Fetcher | 18.8 | 18.8 | 31.0 |
| RAUC 1.15.2 | 24.9 | 134.6 | 440.5 |
Five installs per condition. Columns show added round-trip latency.
For the monthly update at 40 ms added latency, the median installation time fell from 457.6 seconds with Rugix Ctrl 1.3.0 to 31.0 seconds with the new fetcher. RAUC took 440.5 seconds under the same conditions.
At 10 ms added latency, the monthly update required 2,750 requests over 2,750 connections with Rugix Ctrl 1.3.0. The new fetcher used 931 requests over four connections. RAUC used 9,932 requests over 16 connections.
Network Traffic
We measured traffic in both directions on the device’s network interface, including protocol overhead, requests, acknowledgments, and retransmissions.
Medians from five installs per scenario at 10 ms added RTT. Includes traffic in both directions and network framing.
For the monthly update at 10 ms added latency, total traffic fell from 197.1 MiB with Rugix Ctrl 1.3.0 to 175.9 MiB with the new fetcher. RAUC transferred 246.1 MiB.
Traffic also depends on chunking and compression. Rugix Ctrl uses content-defined chunks, whose boundaries follow the data rather than fixed offsets, and compresses each chunk individually. RAUC uses fixed 4 KiB blocks compressed in groups, so fetching one missing block can require downloading other data in its group.
The measurements also informed our delta update savings calculator. The calibration report explains how they relate to its models.
Benchmark Setup and Limits
We benchmarked revision b82749f, labeled “Rugix Ctrl 1.4 Fetcher” in the results. Its fetching implementation is unchanged in Rugix Ctrl 1.4. Speedups are medians of installation-time ratios from matching repetitions.
Tests ran in fresh x86-64 KVM guests with four virtual CPUs, 8 GiB of RAM, blank target slots, prepared source indices, and warm caches. Times exclude initial index generation, booting, and rebooting. Every reconstructed image passed an independent verification check.
Both Rugix Ctrl versions used the same pinned compiler, Casync chunks with a nominal size of 64 KiB, and XZ compression. We used the new fetcher’s default settings. RAUC used its block-hash-index method with 64 KiB XZ compression groups. We also tested RAUC with HTTP/2 over TLS, which did not substantially change installation times in these measurements.
These results cover selected update pairs. Embedded CPUs, flash storage, cold caches, and different networks can change installation times. The benchmark suite contains the reproducible setup, individual measurements, and HTTP/2 results.
Try It with Your Own Images
The fetching improvements ship in Rugix Ctrl 1.4 and work with HTTP servers that support byte-range requests. See the documentation to get started.
At Silitics, we help companies build robust embedded Linux products. If you need help evaluating delta updates or integrating Rugix into an existing platform, we would love to hear from you.
