Skip to content

build: fix two deploy races on a fresh tree, and usr do_clean - #48

Merged
daniel-rossier merged 2 commits into
mainfrom
fix/deploy-races-and-usr-clean
Sep 26, 2026
Merged

daniel-rossier merged 2 commits into
mainfrom
fix/deploy-races-and-usr-clean

Conversation

@daniel-rossier

Copy link
Copy Markdown
Contributor

Three generic defects found while aligning the pos course trees onto this build system. Details and root causes are in the commit message; in short:

  • do_deploy_boot_chain vs. the storage image. With IB_FIRST_STAGE_FROM_CARD, the virt64 chain writes U-Boot into the raw area of sdcard.img, but nothing ordered the task after the image creation. On a fresh tree it failed ("no storage image … run init_storage.sh first"), and with bsp-linux it raced filesystem:do_fs_check. It now depends on filesystem:do_fs_check.
  • Partition nodes. A fixed 2 s sleep, then an unchecked mkfs. In the build container /dev/loopNp1 regularly appears later, so p1 stayed unformatted and the next deploy failed mounting it. The nodes are now polled, and both mkfs calls check their result.
  • usr do_clean. usr.bbclass defines do_clean in Python and the usr recipes appended shell to it, so -c clean died on a SyntaxError. The shell now lives in named shell functions called from a Python append. Running it for real surfaced two latent bugs, fixed here too: a module clean run against a kernel tree that does not exist yet, and (where present) an lvgl clean wiping WORKDIR/temp.
  • dbuild.sh forwards IB_FORCE_ATTACH / IB_PARTITION_LAYOUT to the container: the attach guard's own advice (IB_FORCE_ATTACH=1) never reached bitbake under dbuild.sh.

Validation:

  • bitbake -c clean usr-linux passes on this branch (and usr-so3 where it has the lvgl append).
  • The same storage and deploy changes were exercised end to end in the pos trees: a fresh virt64 card was created in the container, U-Boot was written to the raw area and read off the card by QEMU's boot ROM, and SO3 and Linux both booted.

Three independent defects, all generic, found while aligning the pos
course trees onto this build system.

do_deploy_boot_chain ran before the storage image existed. With
IB_FIRST_STAGE_FROM_CARD the virt64 chain dd's U-Boot into the raw area
of sdcard.img, but nothing ordered the task after the image creation:
on a fresh tree it failed with "no storage image ... run init_storage.sh
first", and with bsp-linux it raced filesystem:do_fs_check. It now
depends on filesystem:do_fs_check, which is a no-op when the image
exists.

Partitioning waited a fixed 2 s for the loop partition nodes. Inside the
build container they come from the host's udev and regularly take longer:
mkfs.fat then ran on a missing /dev/loopNp1, failed silently (no check),
and the next deploy died on "wrong fs type" when mounting p1. The nodes
are now polled (up to 20 s, fatal otherwise) and both mkfs calls check
their exit status.

usr.bbclass defines do_clean in Python, but the usr recipes appended
shell to it; bitbake pastes the append verbatim, so `-c clean` failed on
a SyntaxError. The shell bodies now live in named shell functions called
from a Python append. Running them for real surfaced two latent bugs,
fixed here too: the module clean ran make against a kernel tree that
does not exist before the first linux build, and (where present) the
lvgl clean of usr-so3 wiped WORKDIR/temp, which holds the running task's
own fifo.

Also: dbuild.sh now forwards IB_FORCE_ATTACH and IB_PARTITION_LAYOUT to
the container. The attach guard tells the user to set IB_FORCE_ATTACH=1,
which never reached bitbake under dbuild.sh.
In the IB_RAMFS_SOURCE = "rootfs" case, do_deploy extracts rootfs.cpio,
rsyncs the user space into it and re-packs it. A failed rsync left the
root-owned extracted tree behind, where the p2 path unmounts in a
finally (raised in review of the edgem1 MR).

Not a plain finally here: __do_rootfs_umount re-packs the tree INTO
rootfs.cpio, so it would bake a half-copied user space into the archive.
On failure the tree is dropped and rootfs.cpio is left as it was; the
next deploy starts over from it.

Verified in pos_student with IB_RAMFS_SOURCE = "rootfs": a normal deploy
re-packs rootfs.cpio with the apps; a deploy made to fail (a file where
the rootfs has a directory, rsync exit 23) fails the task, leaves
rootfs.cpio byte-identical and removes the extracted tree.
@daniel-rossier

Copy link
Copy Markdown
Contributor Author

Added one commit: in usr-linux do_deploy with IB_RAMFS_SOURCE = "rootfs", a failed rsync now drops the extracted rootfs tree instead of leaving it behind. This is not a plain finally: __do_rootfs_umount re-packs the tree into rootfs.cpio and would bake a half-copied user space into it. Verified both ways in pos_student: on success rootfs.cpio is re-packed; on a forced rsync failure (exit 23) rootfs.cpio stays byte-identical and the tree is removed.

@daniel-rossier
daniel-rossier merged commit ca120a3 into main Sep 26, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant