Files
Daniel Golle cb60600aec uvol: bump version to 1.1
manage volume state over ubus instead of the rootfs

Rework the volume lifecycle around blockd's ubus API, so volume state
lives entirely on the self-describing LVM/UBI backing store and never
leaks into the firmware rootfs.

- register active volumes with blockd over ubus (mount.uc) instead of
  spooling mounts into /etc/config/fstab (uci.uc)

- bootstrap .meta from 'uvol boot' and drop the broken 90-uvol-init
  uci-default

- run 'uvol boot' straight from the mount.ready trigger, and query
  'ubus call block status' at service start to cover storage already
  being ready

- defer removal of a volume whose backing device is still held, and
  reap it from the mount.umount trigger once it is free

- enforce content-addressed "<algo>-<hexdigest>" volumes in the
  dispatcher: reuse an existing volume of the same digest, verify
  every write

- verify a content-addressed write in place while the volume is still
  incomplete, reporting EBADMSG on mismatch instead of flipping
  volume state

- purge incomplete wo/wp leftovers on boot and reclaim an exactly
  matching one on create

- serialise mutating commands with a device-wide lock, plus a
  per-volume lock ordered after it so a slow write cannot stall other
  volumes

- add a grow-only 'resize' verb to both backends: lvextend plus the
  matching fs-grow tool for lvm, ubirsvol for ubi

- create ext4 volumes with a journal (was ext2) and request check_fs
  when registering a read-write volume

- declare read-only mounts to blockd rather than letting block guess
  from the filesystem

- reject non-numeric and non-positive sizes in create and resize

- report its own version

- simplify command line parsing (drop compatibility with ancient ucode)

Requires the matching fstools changes from
openwrt/openwrt@9b11fa4088.

Signed-off-by: Daniel Golle <daniel@makrotopia.org>
2026-07-25 23:53:57 +01:00

65 lines
1.5 KiB
Ucode

// SPDX-License-Identifier: GPL-2.0-or-later
// blockd mount registration for uvol
// (c) 2022 Daniel Golle <daniel@makrotopia.org>
//
// Register volumes with blockd over ubus instead of writing /etc/config/fstab,
// so volume state stays on the self-describing backing store and never leaks
// into the firmware rootfs.
let mount_fs = require("fs");
let mount_ubus = require("ubus");
let uvol_target = function(vol_name) {
return sprintf("/tmp/run/uvol/%s", vol_name);
};
uvol_mount = {
register: function(vol_name, dev_name, read_only) {
if (!dev_name)
return 22;
if (substr(vol_name, 0, 1) == "." && vol_name != ".meta")
return 1;
let target = uvol_target(vol_name);
let st = mount_fs.lstat(target);
if (st && st.type == "link")
mount_fs.unlink(target);
else if (st && st.type == "directory")
mount_fs.rmdir(target);
let data = {
device: dev_name,
target: target,
autofs: 1,
};
// declare the volume's read-only-ness to blockd, which carries it
// to block as a mount option; block never guesses from the fs type.
if (read_only)
data.options = "ro";
else
data.check_fs = 1;
mount_ubus.call({
object: "block",
method: "hotplug",
data: data,
});
return mount_ubus.error() ? -1 : 0;
},
unregister: function(dev_name) {
if (!dev_name)
return 22;
mount_ubus.call({
object: "block",
method: "hotplug",
data: {
device: dev_name,
remove: 1,
},
});
return mount_ubus.error() ? -1 : 0;
}
};