From: Daan De Meyer Date: Tue, 11 Mar 2025 20:12:11 +0000 (+0100) Subject: Try to find volatile overlay upperdir directory that's not on overlayfs X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=refs%2Fpull%2F3588%2Fhead;p=thirdparty%2Fmkosi.git Try to find volatile overlay upperdir directory that's not on overlayfs Making a directory on overlayfs the upperdir of another overlayfs is rejected by the kernel. Let's try to find a directory that's not on overlayfs. The /dev/shm fallback is because on a default podman container even /tmp is on overlayfs. --- diff --git a/mkosi/__init__.py b/mkosi/__init__.py index 8fd96aa0e..d649d5ef1 100644 --- a/mkosi/__init__.py +++ b/mkosi/__init__.py @@ -87,7 +87,12 @@ from mkosi.installer import clean_package_manager_metadata from mkosi.kmod import gen_required_kernel_modules, loaded_modules, process_kernel_modules from mkosi.log import ARG_DEBUG, complete_step, die, log_notice, log_step from mkosi.manifest import Manifest -from mkosi.mounts import finalize_certificate_mounts, finalize_source_mounts, mount_overlay +from mkosi.mounts import ( + finalize_certificate_mounts, + finalize_source_mounts, + finalize_volatile_tmpdir, + mount_overlay, +) from mkosi.pager import page from mkosi.partition import Partition, finalize_root, finalize_roothash from mkosi.qemu import ( @@ -501,7 +506,12 @@ def setup_build_overlay(context: Context, volatile: bool = False) -> Iterator[No if volatile: context.lowerdirs = [d] context.upperdir = Path( - stack.enter_context(tempfile.TemporaryDirectory(prefix="volatile-overlay")) + stack.enter_context( + tempfile.TemporaryDirectory( + prefix="volatile-overlay.", + dir=finalize_volatile_tmpdir(), + ) + ) ) os.chmod(context.upperdir, d.stat().st_mode) else: diff --git a/mkosi/mounts.py b/mkosi/mounts.py index 4bc571343..8efefb679 100644 --- a/mkosi/mounts.py +++ b/mkosi/mounts.py @@ -10,7 +10,7 @@ from typing import Optional, Union from mkosi.config import BuildSourcesEphemeral, Config from mkosi.log import die -from mkosi.sandbox import OverlayOperation +from mkosi.sandbox import OVERLAYFS_SUPER_MAGIC, OverlayOperation, statfs from mkosi.util import PathString, flatten @@ -30,6 +30,20 @@ def delete_whiteout_files(path: Path) -> None: entry.unlink() +def finalize_volatile_tmpdir() -> Path: + if tempfile.tempdir and statfs(tempfile.tempdir) != OVERLAYFS_SUPER_MAGIC: + return Path(tempfile.tempdir) + + for path in ("/var/tmp", "/tmp", "/dev/shm"): + if Path(path).exists() and statfs(path) != OVERLAYFS_SUPER_MAGIC: + return Path(path) + + die( + "Cannot find temporary directory for volatile overlayfs upperdir", + hint="Either /var/tmp, /tmp or /dev/shm must exist and not be located on overlayfs", + ) + + @contextlib.contextmanager def mount_overlay( lowerdirs: Sequence[Path], @@ -39,7 +53,14 @@ def mount_overlay( ) -> Iterator[Path]: with contextlib.ExitStack() as stack: if upperdir is None: - upperdir = Path(stack.enter_context(tempfile.TemporaryDirectory(prefix="volatile-overlay"))) + upperdir = Path( + stack.enter_context( + tempfile.TemporaryDirectory( + prefix="volatile-overlay.", + dir=finalize_volatile_tmpdir(), + ) + ) + ) st = lowerdirs[-1].stat() os.chmod(upperdir, st.st_mode) @@ -85,7 +106,12 @@ def finalize_source_mounts( upperdir.mkdir(mode=src.stat().st_mode, exist_ok=True) else: upperdir = Path( - stack.enter_context(tempfile.TemporaryDirectory(prefix="volatile-overlay.")) + stack.enter_context( + tempfile.TemporaryDirectory( + prefix="volatile-overlay.", + dir=finalize_volatile_tmpdir(), + ) + ) ) os.chmod(upperdir, src.stat().st_mode)