From bca069283e9639ef2515cdb2e19a4d8f1e72bc88 Mon Sep 17 00:00:00 2001 From: StefanaHanc Date: Fri, 3 Oct 2025 21:33:01 +0300 Subject: [PATCH] expand-rootfs --- .../recipes-core/images/edgeos-image.bb | 2 + .../expand-rootfs/expand-rootfs.bb | 34 +++++++++ .../expand-rootfs/files/expand-rootfs.service | 17 +++++ .../expand-rootfs/files/expand-rootfs.sh | 69 +++++++++++++++++++ 4 files changed, 122 insertions(+) create mode 100644 meta-edgeos/recipes-support/expand-rootfs/expand-rootfs.bb create mode 100644 meta-edgeos/recipes-support/expand-rootfs/files/expand-rootfs.service create mode 100644 meta-edgeos/recipes-support/expand-rootfs/files/expand-rootfs.sh diff --git a/meta-edgeos/recipes-core/images/edgeos-image.bb b/meta-edgeos/recipes-core/images/edgeos-image.bb index 0a54f19..86dd09b 100644 --- a/meta-edgeos/recipes-core/images/edgeos-image.bb +++ b/meta-edgeos/recipes-core/images/edgeos-image.bb @@ -43,3 +43,5 @@ BUILDCFG_VARS += " \ # Disable WIC's automatic fstab updates WIC_CREATE_EXTRA_ARGS = "--no-fstab-update" + +IMAGE_INSTALL:append = "expand-rootfs" \ No newline at end of file diff --git a/meta-edgeos/recipes-support/expand-rootfs/expand-rootfs.bb b/meta-edgeos/recipes-support/expand-rootfs/expand-rootfs.bb new file mode 100644 index 0000000..ea45b9a --- /dev/null +++ b/meta-edgeos/recipes-support/expand-rootfs/expand-rootfs.bb @@ -0,0 +1,34 @@ +SUMMARY = "First-boot rootfs auto-expansion service" +DESCRIPTION = "Expands the active root partition and grows the filesystem on first boot." +LICENSE = "CLOSED" + +PR = "r4" + + +SRC_URI = " \ + file://expand-rootfs.sh \ + file://expand-rootfs.service \ +" + +S = "${WORKDIR}" + +inherit systemd + +do_install() { + install -d ${D}/usr/local/sbin + install -m 0755 ${WORKDIR}/expand-rootfs.sh ${D}/usr/local/sbin/expand-rootfs.sh + + install -d ${D}${systemd_unitdir}/system + install -m 0644 ${WORKDIR}/expand-rootfs.service ${D}${systemd_unitdir}/system/expand-rootfs.service +} + +FILES:${PN} += " \ + /usr/local/sbin/expand-rootfs.sh \ + ${systemd_unitdir}/system/expand-rootfs.service \ +" + +SYSTEMD_SERVICE:${PN} = "expand-rootfs.service" +SYSTEMD_AUTO_ENABLE = "enable" + +RDEPENDS:${PN} = "bash coreutils util-linux parted e2fsprogs-resize2fs udev gptfdisk" + diff --git a/meta-edgeos/recipes-support/expand-rootfs/files/expand-rootfs.service b/meta-edgeos/recipes-support/expand-rootfs/files/expand-rootfs.service new file mode 100644 index 0000000..c102442 --- /dev/null +++ b/meta-edgeos/recipes-support/expand-rootfs/files/expand-rootfs.service @@ -0,0 +1,17 @@ +[Unit] +Description=Expand root partition and filesystem (first boot) +DefaultDependencies=no +After=local-fs.target systemd-udev-settle.service +Wants=systemd-udev-settle.service +ConditionPathExists=!/var/lib/expand-rootfs.done + +[Service] +Type=oneshot +ExecStart=/usr/local/sbin/expand-rootfs.sh +RemainAfterExit=no +TimeoutSec=0 +StandardOutput=journal+console +StandardError=journal+console + +[Install] +WantedBy=multi-user.target diff --git a/meta-edgeos/recipes-support/expand-rootfs/files/expand-rootfs.sh b/meta-edgeos/recipes-support/expand-rootfs/files/expand-rootfs.sh new file mode 100644 index 0000000..86f648b --- /dev/null +++ b/meta-edgeos/recipes-support/expand-rootfs/files/expand-rootfs.sh @@ -0,0 +1,69 @@ +#!/usr/bin/env bash +set -euo pipefail + +STAMP="/var/lib/expand-rootfs.done" +LOG="/var/log/expand-rootfs.log" + +# Redirect all output to log file and console +exec > >(tee -a "$LOG") 2>&1 || true +echo "[expand-rootfs] Start $(date -Is || true)" + +# Run only once +if [[ -f "$STAMP" ]]; then + echo "[expand-rootfs] Stamp file exists; exiting." + exit 0 +fi + +# Detect root device and filesystem type +ROOTDEV="$(findmnt -n -o SOURCE /)" +FSTYPE="$(findmnt -n -o FSTYPE /)" + +if [[ "$ROOTDEV" != /dev/* ]]; then + echo "[expand-rootfs] Root device is not a physical partition ($ROOTDEV) -> skip." + mkdir -p "$(dirname "$STAMP")"; touch "$STAMP"; exit 0 +fi + +# Use sysfs to find partition number and parent disk (portable) +PART_BASENAME="$(basename "$ROOTDEV")" # e.g. mmcblk0p2 +PARTNUM="$(cat "/sys/class/block/${PART_BASENAME}/partition")" +PARENT_SYS="$(readlink -f "/sys/class/block/${PART_BASENAME}/..")" +DISK="/dev/$(basename "$PARENT_SYS")" # e.g. /dev/mmcblk0 +echo "[expand-rootfs] RootDEV=$ROOTDEV Disk=$DISK Part=$PARTNUM FS=$FSTYPE" + +# Skip if an A/B rootfs layout is detected (e.g. mender) +if lsblk -rno PARTLABEL "$DISK" 2>/dev/null | grep -qiE 'root[a-b]'; then + echo "[expand-rootfs] Detected A/B rootfs layout -> skip." + mkdir -p "$(dirname "$STAMP")"; touch "$STAMP"; exit 0 +fi + +# GPT backup header when image is flashed to a larger card +if command -v sgdisk >/dev/null 2>&1; then + echo "[expand-rootfs] sgdisk -e $DISK (fix GPT backup at end)" + sgdisk -e "$DISK" || true + command -v partprobe >/dev/null 2>&1 && partprobe "$DISK" || true + udevadm settle || true +fi + +#Resize root partition to fill the entire disk +if command -v growpart >/dev/null 2>&1; then + echo "[expand-rootfs] growpart $DISK $PARTNUM" + growpart "$DISK" "$PARTNUM" || true +else + echo "[expand-rootfs] parted -s $DISK unit % resizepart $PARTNUM 100%" + parted -s "$DISK" unit % resizepart "$PARTNUM" 100% || true +fi + +command -v partprobe >/dev/null 2>&1 && partprobe "$DISK" || true +udevadm settle || true + +#Resize filesystem +case "$FSTYPE" in + ext4|ext3|ext2) resize2fs "$ROOTDEV" ;; + xfs) xfs_growfs / ;; + btrfs) btrfs filesystem resize max / ;; + *) echo "[expand-rootfs] Unknown filesystem type: $FSTYPE -> skipping resize." ;; +esac + +echo "[expand-rootfs] OK" +mkdir -p "$(dirname "$STAMP")" +touch "$STAMP"