aboutsummaryrefslogtreecommitdiff
path: root/utils/uvol
diff options
context:
space:
mode:
authorDaniel Golle <daniel@makrotopia.org>2021-07-24 04:35:10 +0100
committerDaniel Golle <daniel@makrotopia.org>2021-07-25 00:40:41 +0100
commitf4afa4189e7ae35aa1ba1a6a60f5ed7dba877f6c (patch)
tree6dacf93881d4a42afaa1516235f1ba2781953acc /utils/uvol
parent1614cdde0a452d002fd90d8496f8a22be9229389 (diff)
uvol: update to version 0.3
* genrate UCI fstab configs for each volume before first 'up' * remove UCI section on volume remove * use autofs automounter for read-only volumes * try umount on 'down' * emulate hotplug events for UBI volume up/down * more robust error paths Signed-off-by: Daniel Golle <daniel@makrotopia.org>
Diffstat (limited to 'utils/uvol')
-rw-r--r--utils/uvol/Makefile6
-rw-r--r--utils/uvol/files/common.sh66
-rw-r--r--utils/uvol/files/lvm.sh57
-rw-r--r--utils/uvol/files/ubi.sh50
4 files changed, 145 insertions, 34 deletions
diff --git a/utils/uvol/Makefile b/utils/uvol/Makefile
index f470e5143..f929ba515 100644
--- a/utils/uvol/Makefile
+++ b/utils/uvol/Makefile
@@ -1,7 +1,7 @@
include $(TOPDIR)/rules.mk
PKG_NAME:=uvol
-PKG_VERSION:=0.2
+PKG_VERSION:=0.3
PKG_RELEASE:=$(AUTORELEASE)
PKG_MAINTAINER:=Daniel Golle <daniel@makrotopia.org>
@@ -28,6 +28,7 @@ define Package/uvol
CATEGORY:=Utilities
SUBMENU:=Disc
TITLE:=OpenWrt UBI/LVM volume abstraction
+ DEPENDS:=+blockd
PKGARCH=all
endef
@@ -63,8 +64,9 @@ define Package/autopart/install
endef
define Package/uvol/install
- $(INSTALL_DIR) $(1)/etc/init.d $(1)/usr/libexec/uvol $(1)/usr/sbin
+ $(INSTALL_DIR) $(1)/etc/init.d $(1)/usr/libexec/uvol $(1)/usr/sbin $(1)/lib/functions
$(INSTALL_BIN) ./files/uvol.init $(1)/etc/init.d/uvol
+ $(INSTALL_BIN) ./files/common.sh $(1)/lib/functions/uvol.sh
$(INSTALL_BIN) ./files/ubi.sh $(1)/usr/libexec/uvol/20-ubi.sh
$(INSTALL_BIN) ./files/lvm.sh $(1)/usr/libexec/uvol/50-lvm.sh
$(INSTALL_BIN) ./files/uvol $(1)/usr/sbin
diff --git a/utils/uvol/files/common.sh b/utils/uvol/files/common.sh
new file mode 100644
index 000000000..0eee6d432
--- /dev/null
+++ b/utils/uvol/files/common.sh
@@ -0,0 +1,66 @@
+#!/bin/sh
+
+UCI_SPOOLDIR="/var/spool/uvol"
+
+_uvol_init_spooldir() {
+ [ ! -d "$(dirname "$UCI_SPOOLDIR")" ] && mkdir -p "$(dirname "$UCI_SPOOLDIR")"
+ mkdir -m 0700 -p "$UCI_SPOOLDIR"
+}
+
+uvol_uci_add() {
+ local volname="$1"
+ local devname="$2"
+ local mode="$3"
+ local autofs uuid uciname
+
+ uciname=${volname//-/_}
+ uuid="$(/sbin/block info | grep "^$2" | xargs -n 1 echo | grep "^UUID=.*")"
+ [ "$uuid" ] || return 22
+ _uvol_init_spooldir
+ uuid="${uuid:5}"
+ autofs=0
+ [ "$mode" = "ro" ] && autofs=1
+ if [ -e "${UCI_SPOOLDIR}/remove-$1" ]; then
+ rm "${UCI_SPOOLDIR}/remove-$1"
+ fi
+
+ cat >"${UCI_SPOOLDIR}/add-$1" <<EOF
+set fstab.$uciname=mount
+set fstab.$uciname.uuid=$uuid
+set fstab.$uciname.target=/var/run/uvol/$volname
+set fstab.$uciname.options=$mode
+set fstab.$uciname.autofs=$autofs
+set fstab.$uciname.enabled=1
+commit fstab
+EOF
+}
+
+uvol_uci_remove() {
+ local volname="$1"
+ local uciname
+
+ uciname=${volname//-/_}
+ if [ -e "${UCI_SPOOLDIR}/add-$1" ]; then
+ rm "${UCI_SPOOLDIR}/add-$1"
+ return
+ fi
+ _uvol_init_spooldir
+ cat >"${UCI_SPOOLDIR}/remove-$1" <<EOF
+delete fstab.$uciname
+commit fstab
+EOF
+}
+
+uvol_uci_commit() {
+ local volname="$1"
+
+ if [ -e "${UCI_SPOOLDIR}/add-$1" ]; then
+ uci batch < "${UCI_SPOOLDIR}/add-$1"
+ rm "${UCI_SPOOLDIR}/add-$1"
+ elif [ -e "${UCI_SPOOLDIR}/remove-$1" ]; then
+ uci batch < "${UCI_SPOOLDIR}/remove-$1"
+ rm "${UCI_SPOOLDIR}/remove-$1"
+ fi
+
+ return $?
+}
diff --git a/utils/uvol/files/lvm.sh b/utils/uvol/files/lvm.sh
index 082be5f25..c06e2f102 100644
--- a/utils/uvol/files/lvm.sh
+++ b/utils/uvol/files/lvm.sh
@@ -11,6 +11,7 @@ fi
command -v lvm >/dev/null || return 1
. /lib/functions.sh
+. /lib/functions/uvol.sh
. /lib/upgrade/common.sh
. /usr/share/libubox/jshn.sh
@@ -147,15 +148,21 @@ exportlv() {
getdev() {
local dms dm_name
- existvol "$1" || return 1
- exportlv "$1"
for dms in /sys/devices/virtual/block/dm-* ; do
+ [ "$dms" = "/sys/devices/virtual/block/dm-*" ] && break
read -r dm_name < "$dms/dm/name"
[ $(basename "$lv_dm_path") = "$dm_name" ] && echo "$(basename "$dms")"
done
}
+getuserdev() {
+ local dms dm_name
+ existvol "$1" || return 1
+ exportlv "$1"
+ getdev "$@"
+}
+
getsize() {
exportlv "$1"
[ "$lv_size" ] && echo "$lv_size"
@@ -171,8 +178,9 @@ activatevol() {
;;
*)
[ "$lv_active" = "active" ] && return 0
- lvm_cmd lvchange -k n "$lv_full_name" || return $?
+ uvol_uci_commit "$1"
lvm_cmd lvchange -a y "$lv_full_name" || return $?
+ lvm_cmd lvchange -k n "$lv_full_name" || return $?
return 0
;;
esac
@@ -180,6 +188,7 @@ activatevol() {
disactivatevol() {
exportlv "$1"
+ local devname
[ "$lv_path" ] || return 2
case "$lv_path" in
/dev/*/wo_*|\
@@ -188,7 +197,9 @@ disactivatevol() {
;;
*)
[ "$lv_active" = "active" ] || return 0
- lvm_cmd lvchange -a n "$lv_full_name" || return $?
+ devname="$(getdev "$1")"
+ [ "$devname" ] && /sbin/block umount "$devname"
+ lvm_cmd lvchange -a n "$lv_full_name"
lvm_cmd lvchange -k y "$lv_full_name" || return $?
return 0
;;
@@ -225,30 +236,41 @@ createvol() {
;;
esac
- lvm_cmd lvcreate -p "$lvmode" -a n -y -W n -Z n -n "${mode}_$1" -l "$size_ext" "$vg_name"
+ lvm_cmd lvcreate -p "$lvmode" -a n -y -W n -Z n -n "${mode}_$1" -l "$size_ext" "$vg_name" || return $?
ret=$?
if [ ! $ret -eq 0 ] || [ "$lvmode" = "r" ]; then
return $ret
fi
exportlv "$1"
[ "$lv_full_name" ] || return 22
- lvm_cmd lvchange -a y "$lv_full_name" || return 1
+ lvm_cmd lvchange -a y "$lv_full_name" || return $?
if [ "$lv_size" -gt $(( 100 * 1024 * 1024 )) ]; then
mkfs.f2fs -f -l "$1" "$lv_path"
ret=$?
- [ $ret != 0 ] && [ $ret != 134 ] && return 1
+ [ $ret != 0 ] && [ $ret != 134 ] && {
+ lvm_cmd lvchange -a n "$lv_full_name" || return $?
+ return $ret
+ }
else
- mke2fs -F -L "$1" "$lv_path" || return 1
+ mke2fs -F -L "$1" "$lv_path" || {
+ ret=$?
+ lvm_cmd lvchange -a n "$lv_full_name" || return $?
+ return $ret
+ }
fi
- lvm_cmd lvrename "$vg_name" "wp_$1" "rw_$1"
- exportlv "$1"
+ uvol_uci_add "$1" "/dev/$(getdev "$1")" "rw"
+ lvm_cmd lvchange -a n "$lv_full_name" || return $?
+ lvm_cmd lvrename "$vg_name" "wp_$1" "rw_$1" || return $?
return 0
}
removevol() {
exportlv "$1"
[ "$lv_full_name" ] || return 2
- lvm_cmd lvremove -y "$lv_full_name"
+ [ "$lv_active" = "active" ] && return 16
+ lvm_cmd lvremove -y "$lv_full_name" || return $?
+ uvol_uci_remove "$1"
+ uvol_uci_commit "$1"
}
updatevol() {
@@ -257,12 +279,13 @@ updatevol() {
[ "$lv_size" -ge "$2" ] || return 27
case "$lv_path" in
/dev/*/wo_*)
- lvm_cmd lvchange -p rw "$lv_full_name"
- lvm_cmd lvchange -a y "$lv_full_name"
+ lvm_cmd lvchange -p rw "$lv_full_name" || return $?
+ lvm_cmd lvchange -a y "$lv_full_name" || return $?
dd of="$lv_path"
- lvm_cmd lvchange -a n "$lv_full_name"
- lvm_cmd lvchange -p r "$lv_full_name"
- lvm_cmd lvrename "$lv_full_name" "${lv_full_name%%/*}/ro_$1"
+ uvol_uci_add "$1" "/dev/$(getdev "$1")" "ro"
+ lvm_cmd lvchange -a n "$lv_full_name" || return $?
+ lvm_cmd lvchange -p r "$lv_full_name" || return $?
+ lvm_cmd lvrename "$lv_full_name" "${lv_full_name%%/*}/ro_$1" || return $?
return 0
;;
default)
@@ -344,7 +367,7 @@ case "$cmd" in
removevol "$@"
;;
device)
- getdev "$@"
+ getuserdev "$@"
;;
size)
getsize "$@"
diff --git a/utils/uvol/files/ubi.sh b/utils/uvol/files/ubi.sh
index 3eb79adb9..9ddda54da 100644
--- a/utils/uvol/files/ubi.sh
+++ b/utils/uvol/files/ubi.sh
@@ -17,6 +17,8 @@ ubidev=$(ls -1 /sys/devices/virtual/ubi | head -n 1)
read -r ebsize < "/sys/devices/virtual/ubi/${ubidev}/eraseblock_size"
+. /lib/functions/uvol.sh
+
freebytes() {
read -r availeb < "/sys/devices/virtual/ubi/${ubidev}/avail_eraseblocks"
echo $((availeb * ebsize))
@@ -87,9 +89,10 @@ getuserdev() {
mkubifs() {
local tmp_mp
tmp_mp="$(mktemp -d)"
- mount -t ubifs "$1" "$tmp_mp"
- umount "$tmp_mp"
- rmdir "$tmp_mp"
+ mount -t ubifs "$1" "$tmp_mp" || return $?
+ umount "$tmp_mp" || return $?
+ rmdir "$tmp_mp" || return $?
+ return 0
}
createvol() {
@@ -107,22 +110,33 @@ createvol() {
return 22
;;
esac
- ubimkvol "/dev/$ubidev" -N "uvol-$mode-$1" -s "$2"
+ ubimkvol "/dev/$ubidev" -N "uvol-$mode-$1" -s "$2" || return $?
ret=$?
[ $ret -eq 0 ] || return $ret
voldev="$(getdev "$@")"
- ubiupdatevol -t "/dev/$voldev"
+ ubiupdatevol -t "/dev/$voldev" || return $?
[ "$mode" = "wp" ] || return 0
- mkubifs "/dev/$voldev"
- ubirename "/dev/$ubidev" "uvol-wp-$1" "uvol-wd-$1"
+ mkubifs "/dev/$voldev" || return $?
+ uvol_uci_add "$1" "/dev/$voldev" "rw"
+ ubirename "/dev/$ubidev" "uvol-wp-$1" "uvol-wd-$1" || return $?
}
removevol() {
- local voldev
+ local voldev volnum
voldev=$(getdev "$@")
[ "$voldev" ] || return 2
- local volnum="${voldev#${ubidev}_}"
+ vol_is_mode "$voldev" rw && return 16
+ vol_is_mode "$voldev" ro && return 16
+ volnum="${voldev#${ubidev}_}"
ubirmvol "/dev/$ubidev" -n "$volnum" || return $?
+ uvol_uci_remove "$1"
+ uvol_uci_commit "$1"
+}
+
+block_hotplug() {
+ export ACTION="$1"
+ export DEVNAME="$2"
+ /sbin/block hotplug
}
activatevol() {
@@ -133,12 +147,15 @@ activatevol() {
vol_is_mode "$voldev" ro && return 0
vol_is_mode "$voldev" wo && return 22
vol_is_mode "$voldev" wp && return 16
+ uvol_uci_commit "$1"
if vol_is_mode "$voldev" rd; then
- ubirename "/dev/$ubidev" "uvol-rd-$1" "uvol-ro-$1"
- ubiblock --create "/dev/$voldev"
+ ubirename "/dev/$ubidev" "uvol-rd-$1" "uvol-ro-$1" || return $?
+ ubiblock --create "/dev/$voldev" || return $?
+ block_hotplug add "ubiblock${voldev:3}"
return 0
elif vol_is_mode "$voldev" wd; then
- ubirename "/dev/$ubidev" "uvol-wd-$1" "uvol-rw-$1"
+ ubirename "/dev/$ubidev" "uvol-wd-$1" "uvol-rw-$1" || return $?
+ block_hotplug add "$voldev"
return 0
fi
}
@@ -152,12 +169,14 @@ disactivatevol() {
vol_is_mode "$voldev" wo && return 22
vol_is_mode "$voldev" wp && return 16
if vol_is_mode "$voldev" ro; then
- [ -e "/dev/ubiblock${voldev:3}" ] || return 0
- ubiblock --remove "/dev/$voldev" || return $?
+ /sbin/block umount "ubiblock${voldev:3}"
+ ubiblock --remove "/dev/$voldev"
ubirename "/dev/$ubidev" "uvol-ro-$1" "uvol-rd-$1" || return $?
return 0
elif vol_is_mode "$voldev" rw; then
+ /sbin/block umount "$voldev"
ubirename "/dev/$ubidev" "uvol-rw-$1" "uvol-wd-$1" || return $?
+ block_hotplug remove "$voldev"
return 0
fi
}
@@ -169,6 +188,7 @@ updatevol() {
[ "$2" ] || return 22
vol_is_mode "$voldev" wo || return 22
ubiupdatevol -s "$2" "/dev/$voldev" -
+ uvol_uci_add "$1" "/dev/$voldev" "ro"
ubirename "/dev/$ubidev" "uvol-wo-$1" "uvol-rd-$1"
}
@@ -199,7 +219,7 @@ bootvols() {
case "$volname" in
uvol-ro-*)
voldev="/dev/ubiblock${voldev:3}"
- ubiblock --create "/dev/$voldev"
+ ubiblock --create "/dev/$voldev" || return $?
;;
*)
continue