From bf57663a71afb5aba40b849ebfd456010a3789a9 Mon Sep 17 00:00:00 2001 From: Olivier Le Thanh Duong Date: Fri, 23 Aug 2024 10:48:58 +0200 Subject: [PATCH 1/3] Problem: FirecrackerVM not working if /var/lib and /var/cache on two separate partion The prepare step for jailer was failing because it couldn't create a link to rootfs file when the CACHE and EXECUTION were not on the same partition This was due do trying to make a hardlink instead of as soft symlink (contrary to what the docstring indicated) Solution: Make a symlink --- src/aleph/vm/hypervisors/firecracker/microvm.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/aleph/vm/hypervisors/firecracker/microvm.py b/src/aleph/vm/hypervisors/firecracker/microvm.py index e5a7c94dc..909cde06d 100644 --- a/src/aleph/vm/hypervisors/firecracker/microvm.py +++ b/src/aleph/vm/hypervisors/firecracker/microvm.py @@ -324,7 +324,7 @@ def enable_file_rootfs(self, path_on_host: Path) -> Path: rootfs_filename = Path(path_on_host).name jailer_path_on_host = f"/opt/{rootfs_filename}" try: - os.link(path_on_host, f"{self.jailer_path}/{jailer_path_on_host}") + os.symlink(path_on_host, f"{self.jailer_path}/{jailer_path_on_host}") except FileExistsError: logger.debug(f"File {jailer_path_on_host} already exists") return Path(jailer_path_on_host) From 35f62270a9e9e1eda1c9e6fce707fa6c246de7f8 Mon Sep 17 00:00:00 2001 From: Olivier Le Thanh Duong Date: Thu, 29 Aug 2024 15:37:05 +0200 Subject: [PATCH 2/3] doesn't work with a symlink make a copy instead --- src/aleph/vm/hypervisors/firecracker/microvm.py | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/src/aleph/vm/hypervisors/firecracker/microvm.py b/src/aleph/vm/hypervisors/firecracker/microvm.py index 909cde06d..48b38ea29 100644 --- a/src/aleph/vm/hypervisors/firecracker/microvm.py +++ b/src/aleph/vm/hypervisors/firecracker/microvm.py @@ -1,4 +1,5 @@ import asyncio +import errno import json import logging import os.path @@ -318,7 +319,8 @@ def enable_rootfs(self, path_on_host: Path) -> Path: def enable_file_rootfs(self, path_on_host: Path) -> Path: """Make a rootfs available to the VM. - Creates a symlink to the rootfs file if jailer is in use. + If jailer is in use, try to create a hardlink + If it is not possible to create a link because the dir are in separate device made a copy. """ if self.use_jailer: rootfs_filename = Path(path_on_host).name @@ -327,6 +329,13 @@ def enable_file_rootfs(self, path_on_host: Path) -> Path: os.symlink(path_on_host, f"{self.jailer_path}/{jailer_path_on_host}") except FileExistsError: logger.debug(f"File {jailer_path_on_host} already exists") + except OSError as err: + if err.errno == errno.EXDEV: + # Invalid cross-device link: + # cannot make hard link between partition. Make a copy instead + shutil.copyfile(path_on_host, f"{self.jailer_path}/{jailer_path_on_host}") + else: + raise return Path(jailer_path_on_host) else: return path_on_host From 6a7ec5e025caf48c3dc4b768b1dfa46d42a6c82f Mon Sep 17 00:00:00 2001 From: Olivier Le Thanh Duong Date: Mon, 2 Sep 2024 13:50:13 +0200 Subject: [PATCH 3/3] Update src/aleph/vm/hypervisors/firecracker/microvm.py Co-authored-by: nesitor --- src/aleph/vm/hypervisors/firecracker/microvm.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/aleph/vm/hypervisors/firecracker/microvm.py b/src/aleph/vm/hypervisors/firecracker/microvm.py index 48b38ea29..9cbe3c8ae 100644 --- a/src/aleph/vm/hypervisors/firecracker/microvm.py +++ b/src/aleph/vm/hypervisors/firecracker/microvm.py @@ -326,7 +326,7 @@ def enable_file_rootfs(self, path_on_host: Path) -> Path: rootfs_filename = Path(path_on_host).name jailer_path_on_host = f"/opt/{rootfs_filename}" try: - os.symlink(path_on_host, f"{self.jailer_path}/{jailer_path_on_host}") + os.link(path_on_host, f"{self.jailer_path}/{jailer_path_on_host}") except FileExistsError: logger.debug(f"File {jailer_path_on_host} already exists") except OSError as err: