Skip to content

Engineering proof · Thursday 22 October 2026 · 09:15 BST

Linux 7.3 + OpenZFS 2.4.4: Real Hardware Validation Progress

SaphiraD has booted Linux 7.3.0 via UEFI on Minimer—an Intel N100 machine with an NVMe system disk—and loaded OpenZFS 2.4.4-1 against that running kernel. The existing tank pool imported, its filesystems mounted, and the recorded pool status is clean.

Saphira Linux dragon mascot

What happened

This is not a successful cross-compile reported from a build machine. It is a real SaphiraD boot on Minimer: physical Intel N100 hardware, UEFI firmware and an NVMe root disk. Linux 7.3.0 is running, the OpenZFS module is loaded, and the existing tank pool is online with its expected datasets mounted.

Host

Minimer
A tiny PELADN WI-6: roughly 1 inch tall and 5 × 5 inches square, shorter than an iPhone SE. It has four Intel N100 cores, 14 GiB RAM and a Samsung 970 EVO Plus 500 GB NVMe drive; booted by UEFI from /dev/nvme0n1p2.

Operating system

SaphiraD
The systemd 262 edition of Saphira Linux, using the same native APK packages and service package definitions as Saphira.

Running kernel

Linux 7.3.0
Installed from saphira-kernel-7.3-1-r1.

Loaded ZFS

OpenZFS 2.4.4-1
Installed from the signed APK saphira-zfs-7.3-2.4.4-r1, with the matching userspace package installed too.

The machine identity is from firmware, not a marketing label:dmidecode reports manufacturer PELADN and productWI-6. “Minimer” really is the small node name: the OpenZFS and OpenStack evidence below comes from this compact appliance-sized host.

System Information: Manufacturer: PELADN · Product Name: WI-6
Base Board Information: Manufacturer: PELADN · Product Name: WI-6
BIOS Information: AMI 100E_P dated 2024-02-20, UEFI supported

The NVMe path is a useful constraint: the device supports PCIe 3.0 ×4 but Minimer is operating it at PCIe 3.0 ×1 (8 GT/s). That is a link-width observation, not a storage benchmark, and makes the successful software result more interesting without changing the experimental status of this ZFS/kernel pairing.

$ sudo lspci -s 03:00.0 -vv | grep -E 'LnkCap:|LnkSta:'
LnkCap: Port #0, Speed 8GT/s, Width x4, ASPM L1, Exit Latency L1 <64us
LnkSta: Speed 8GT/s, Width x1 (downgraded)

Important: OpenZFS marks this pairing experimental

This is a successful engineering proof, not a production recommendation.

The module wrote this warning to Minimer’s kernel log when it loaded. It comes from OpenZFS itself and must be taken literally.

[    3.594459] ZFS: Loaded module v2.4.4-1, ZFS pool version 5000, ZFS filesystem version 5
[    3.595762] ZFS: Using ZFS with kernel 7.3.0 is EXPERIMENTAL and SERIOUS DATA LOSS may occur!
[    3.596894] ZFS: Please report your results at: https://github.com/openzfs/zfs/issues/new

Saphira’s five compatibility patches make the build and this observed boot possible; they do not convert upstream’s experimental warning into a support guarantee. Keep backups, retain the fallback kernel, test only with a recovery plan, and do not upgrade a pool merely because the module has loaded. The next work is careful validation, not premature production deployment.

The observed record

These are the facts observed on Minimer at the time of the record. They prove a boot, module load, pool import and mounted filesystems. They are deliberately not presented as a completed production qualification.

$ uname -r
7.3.0

$ modinfo zfs | sed -n '1,24p'
filename:       /lib/modules/7.3.0/extra/zfs.ko
version:        2.4.4-1
vermagic:       7.3.0 SMP preempt mod_unload
sig_id:         PKCS#7

$ lsmod | grep -E '^(zfs|spl)'
zfs                  6365184  13
spl                   147456  1 zfs

$ zpool status tank
  pool: tank
 state: ONLINE
  scan: scrub repaired 0B in 00:01:10 with 0 errors on Thu Oct 22 08:21:26 2026
config:

	NAME         STATE     READ WRITE CKSUM
	tank         ONLINE       0     0     0
	  nvme0n1p4  ONLINE       0     0     0

errors: No known data errors

The module file is exactly where a kernel module for this running release should be:/lib/modules/7.3.0/extra/zfs.ko. Its vermagic field matches the running kernel’s release. The active pool also mounted /tank,/home, /var/lib/libvirt/images and the Saphira build datasets. This is useful live data, not an empty test pool created for an announcement.

The live tank pool is a single nvme0n1p4 vdev: 416 GiB in total, with 51.9 GiB allocated, 364 GiB free, 19% fragmentation and 12% capacity in use. Its ashift is 12. This is useful context, not redundancy: a single-device pool cannot protect against the loss of that device.

Separate Intel i915 graphics and firmware messages were also present in the boot record. They are not ZFS failures and are kept separate from this storage validation.

A bounded ZFS data-path test

The first live test used a new, capped dataset rather than an existing workload. It has a 2 GiB quota and zstd compression. A 256 MiB random file was written with fsync, then hashed, snapshotted, cloned and compared byte-for-byte. The snapshot stream was then sent to a separately received dataset, mounted and compared again.

# The write, snapshot and clone were performed on Minimer.
sudo zfs create -o mountpoint=/tank/SAPHIRA/zfs73-test -o quota=2G -o compression=zstd tank/SAPHIRA/zfs73-test
sudo dd if=/dev/urandom of=/tank/SAPHIRA/zfs73-test/test.bin bs=1M count=256 conv=fsync status=progress
sudo sha256sum /tank/SAPHIRA/zfs73-test/test.bin
sudo zfs snapshot tank/SAPHIRA/zfs73-test@verified
sudo zfs clone -o mountpoint=/tank/SAPHIRA/zfs73-clone tank/SAPHIRA/zfs73-test@verified tank/SAPHIRA/zfs73-clone
sudo zfs send tank/SAPHIRA/zfs73-test@verified | sudo zfs receive -u -o mountpoint=/tank/SAPHIRA/zfs73-recv tank/SAPHIRA/zfs73-recv
sudo zfs mount tank/SAPHIRA/zfs73-recv
sudo cmp /tank/SAPHIRA/zfs73-test/test.bin /tank/SAPHIRA/zfs73-recv/test.bin

003c2038504dce6622569c3c69e2d8408e0b7cea125daf70ef93fc1902c50040  test.bin

All three copies—the source, clone and received dataset—have the same SHA-256 value. Both comparisons exited successfully. The clone correctly recordstank/SAPHIRA/zfs73-test@verified as its origin; the received dataset is mounted and has no receive-resume token. This proves this bounded sequence of synced write, snapshot, clone, stream send, stream receive and mount on this host. It is not a performance benchmark or a substitute for long-running workload validation.

Minimer also has three existing ZFS volumes (zvols): one 8 GiB volume and two 64 GiB volumes, all using 16 KiB volume blocks. A zvol is a block device backed by a ZFS dataset, useful to virtual machines and similar consumers. It uses the same running ZFS userspace and module version—zfs-2.4.4-1 andzfs-kmod-2.4.4-1—rather than having an independent “zvol version”. Their presence is live configuration evidence, not a claim that guest I/O has yet completed the same validation.

Initial data-write results

Two additional non-benchmark checks completed on the live pool. They show how the filesystem handled highly compressible data and incompressible data, but neither result is a maximum NVMe-speed claim.

Zero-block handling

1 GiB · /dev/zero
A 1 GiB write using conv=fsync reported approximately 2.7 GB/s. The apparent file size is 1.0 GiB, while du reported only 512 bytes allocated. This demonstrates effective zero-block handling; it is not physical NVMe write bandwidth.

Incompressible data

1 GiB · /dev/random
A 1 GiB overwrite completed in approximately 3.75 seconds at an average reported 286 MB/s. Physical allocation was approximately 1.1 GB and the logical pool usage rose by about 1 GiB.
$ sha256sum /tank/test.dd
69603a8dfc4f0eaf5455287085a66ada468158b6a7c30d0f20b2e07a962d7f69  /tank/test.dd

The checksum read completed successfully and gives us a reference for later persistence testing. The 286 MB/s figure includes random-data generation and filesystem processing; it is not a storage ceiling. After the reboot below, the same file was hashed again and the digest was identical (69603a8d…b6a7c30d), as was the 256 MiB test file (003c2038…fc1902c5): post-reboot persistence is now observed, not just planned.

The host after reboot

This timing was captured after a reboot, with the same SaphiraD systemd host bringing its normal services back. Minimer is also running a complete OpenStack controller, so this is a live infrastructure machine rather than an isolated storage test bench.

$ sudo systemd-analyze
Startup finished in 5.718s (firmware) + 3.725s (loader) + 1.427s (kernel) + 49.290s (userspace) = 1min 162ms
multi-user.target reached after 49.289s in userspace.

The boot timing is a record of this machine and workload at this point in time. It is not a promise of a universal startup time, and it does not by itself prove that every OpenStack service or virtual-machine workload has completed independent qualification.

The service manager reported no failed units after this reboot. The controller services shown in the startup report included RabbitMQ, Neutron API, Keystone, Horizon, Glance, Cinder API, Nova API, Placement and Nova conductor, alongside Open vSwitch, libvirt daemons and ZFS import/mount services.

$ systemctl --failed
0 loaded units listed.

$ systemd-analyze blame | head -10
46.773s rabbitmq-server.service
 1.934s neutron-api.service
 1.888s keystone.service
 1.623s horizon.service
 1.399s glance.service
 1.304s cinder-api.service
 1.196s nova-api.service
 1.159s placement.service

$ systemd-analyze critical-chain
multi-user.target @49.289s
`-rabbitmq-server.service @2.515s +46.773s
  `-network-online.target @2.280s
    `-openvswitch.service @1.971s +305ms
      `-tank-SAPHIRA.mount @2.803s

RabbitMQ accounts for 46.773 seconds in this critical chain; that is an observed service-start cost, not a failed service. It gives future tuning and repeat-boot tests a concrete starting point instead of turning the overall startup time into a vague claim about Saphira or OpenStack.

ZFS benchmark on Linux 7.3

Minimer has now completed a verified fio workload against/tank/bench73/fio-test. It used a 1 GiB file, random 4 KiB writes, synchronous I/O at queue depth 1, direct I/O, fsync at the end and SHA-256 verification of the data. The test ran on the DRAMless NVMe device through its deliberately intended PCIe 3.0 ×1 link.

Test resultObserved value
Random 4 KiB writes3,856 IOPS · 15.1 MiB/s
Verified reads3,421 IOPS · 13.4 MiB/s
Data written and read1 GiB each
Total 4 KiB operations524,288
VerificationSHA-256 passed · err=0 · verification errors 0
$ sudo fio --name=zfs73-verify --filename=/tank/bench73/fio-test --size=1G --rw=randwrite --bs=4k --ioengine=psync --direct=1 --verify=sha256 --do_verify=1 --verify_fatal=1 --end_fsync=1 --group_reporting
fio-3.43 · queue depth 1 · 262,144 writes + 262,144 verified reads
fio result: err=0

This is substantially stronger evidence than a module-load check: more than half a million small I/O operations were written, flushed, read and verified. It is still one controlled run, not a maximum-performance claim, a production guarantee or a substitute for repeated reboot and workload testing.

The supplementary Bonnie++ run has now also completed: version 1.04 (Saphira's own packaged build) against /tank/bench73 with a 29,312 MiB file, roughly double the host's 14 GiB RAM per Bonnie++'s own guidance.

Bonnie++ resultObserved value
Sequential output, per-char124,000 K/sec · 98% CPU
Sequential output, block1,452,782 K/sec · 85% CPU
Sequential rewrite1,028,080 K/sec · 89% CPU
Sequential input, per-char163,918 K/sec · 99% CPU
Sequential input, block2,672,860 K/sec · 99% CPU
Random seeks+++++ (above timer resolution)
File create/read/delete, sequential and random+++++ throughout (above timer resolution)
$ sudo bonnie++ -d /tank/bench73 -s 29312 -m minimer -u 0:0
Version 1.04 · 29,312 MiB file · metadata ops above timer resolution

Read the +++++ marks honestly: they mean the operations completed faster than Bonnie++'s timer resolution, largely served from ARC and page cache rather than the NVMe device. They prove metadata-path correctness under load, not disk speed. The sequential block figures exercised the ZFS I/O path for real; like the fio run, this is one controlled run, not a ceiling.

A carefully bounded first-boot claim

To Saphira’s current knowledge, this is the first reported real-hardware boot combining Linux 7.3 final with OpenZFS 2.4.4-1. We cannot prove a negative about every system everywhere, so this is a bounded “to our knowledge” statement, not an assertion that no earlier private or public experiment exists.

What is unambiguous is Saphira’s own evidence: a signed, versioned kernel package and a matching versioned ZFS module package have reached a physical UEFI N100 host; the module loaded; an existing pool imported; and its datasets mounted with a clean recorded pool status. That is a meaningful engineering milestone worth documenting plainly.

Why this took Saphira engineering

OpenZFS 2.4.4 was not published upstream as a ready-made Linux 7.3 pairing. Saphira’ssaphira-zfs-7.3 recipe builds against the exact published kernel configuration and carries five focused compatibility patches. The patches cover the changed block-vector field, kernel-thread filesystem context, CPU-feature check, inode-create interface and the Linux 7.3 idmap-era interface.

The recipe reconstructs a matching kernel build tree from verified inputs, runs its compatibility probes, and signs each resulting module with the builder’s required module signing key. It fails closed when that key is unavailable. The runtime packages remain separate and versioned, so installing Linux 7.3 does not erase an earlier kernel line.

That is why this is more than “it compiled”: the compatibility work is visible in the recipe, the package is native to Saphira, and the result has now met real firmware, hardware, an NVMe device and an existing ZFS pool.

Inspect the Saphira package recipes →

The build underneath the result

Saphira is not a generic x86-64 build assembled from an unrelated host. The SDK bootstraps GCC with AKADATA’s branch-cost patch, and that policy is carried through the native toolchain and the full system build. The resulting Saphira x86_64-v3 system is compiled with the branch-cost adjustment in place.

That build provenance matters when reading this record: a small Intel N100, an NVMe device running on a single PCIe lane and a complete systemd/OpenStack controller can work together cleanly because the distribution is built as one integrated system. It is an engineering explanation, not a claim that one patch alone caused any measured throughput or proves universal hardware support.

The OpenZFS compatibility work remains separate and explicit: five Linux 7.3 patches make this module build and load, while OpenZFS itself still labels the pairing experimental. Both facts belong in the same record.

The complete patch pack is public

The exact five-patch port used for this result is published with its build notes. The README keeps the attribution clear: robn’s Linux 7.3 branch supplied useful API analysis, but its diffs target a newer, drifted tree and do not apply directly to OpenZFS 2.4.4. Saphira’s pack is the 2.4.4 backport that was actually built.

The pack also records the important negative: no Linux kernel source patch was needed. These are out-of-tree ZFS compatibility changes, applied in numbered order; there is deliberately no 0004. The combined patch has been checked against pristine OpenZFS 2.4.4 with zero fuzz and zero offset.

What this proves—and what it does not

Proven on Minimer

  • SaphiraD boots Linux 7.3.0 through UEFI on Intel N100/NVMe hardware.
  • OpenZFS 2.4.4-1 loads from the matching Linux 7.3 module directory.
  • The observed module ABI string matches the running kernel.
  • The NVMe device reports PCIe 3.0 ×4 capability and an operating ×1 link.
  • The existing tank pool imports, is ONLINE and has no recorded data errors.
  • Existing ZFS filesystems mount, including home and libvirt image storage.
  • A scrub completed over 51.9 GiB in 1m10s: 0B repaired and 0 errors.
  • A fsynced 256 MiB random file survived snapshot, clone, ZFS send/receive and exact byte comparisons.
  • The boot journal contains none of the checked oops, BUG:,call trace, hung task or deadlock markers.
  • Initial zero-block and incompressible-data writes completed and were flushed.
  • A 1 GiB direct-I/O fio random-write workload completed with SHA-256 verification and err=0.
  • Minimer reached multi-user.target after reboot with its OpenStack controller host.

Still to prove

  • Repeated fio runs across sequential, mixed, direct-I/O and varied verification patterns.
  • Repeated reboot persistence: one reboot with identical post-reboot checksums is observed; further reboot cycles remain future work.
  • Kernel-side verification of the module signature and its trust chain.
  • Guest I/O validation for the existing zvol-backed workloads.
  • Idmapped mounts, extended attributes, ACLs, concurrency and storage operations.
  • Broader hardware, storage-controller and workload coverage before any production label.

The module-signature note

modinfo reports a PKCS#7 signature record for the loaded ZFS module, but its signer and key fields are blank and the hash field is unknown in this observation. That records the presence of a signature container; it does not by itself prove that the running kernel accepted the module through its trusted-key verification path.

Secure Boot is disabled on Minimer. The running kernel was built with module-signing support, but this observation does not demonstrate an enforced Secure-Boot or trusted module-signature path. The normal CDDL licence message also marks the loaded ZFS module as tainting the kernel. Neither fact invalidates the functional result; both belong in the record so that it is not mistaken for a different kind of proof.

The next debug record should inspect the boot and module-load messages, the active kernel keyrings and the module-signing policy. This is a separate verification task. It does not diminish the successful boot, module load or pool import, but it prevents us making a stronger signature claim than the evidence supports.

# Read-only evidence for the next verification record.
dmesg | grep -Ei 'zfs|module verification|signature|key'
cat /proc/keys
modinfo zfs | sed -n '/^sig_id:/,/^signature:/p'

The next careful steps

  1. Preserve the working boot entry and retain a known-good fallback kernel. Do not treat a successful first boot as permission to remove recovery paths.
  2. The first scrub is complete: it scanned 51.9 GiB in 1m10s, repaired 0B and reported 0 errors. Follow it with measured, varied read/write work on a suitable non-critical dataset rather than improvising against irreplaceable data.
  3. Reboot deliberately and verify the same kernel, module, pool import and mounted datasets again. Repeat that evidence after normal package and service activity.
  4. Do not run zpool upgrade merely because a newer module booted. Keep the pool format where it is until compatibility, backup and recovery decisions have been made deliberately.

This is the Saphira approach: celebrate the evidence, publish the work, then keep doing the unglamorous validation that makes a production claim worth believing. Your hardware. Your data. Software as Yours.

Related guidance