Virtual Disk in a LXD Container

In the last tutorial “Virtual Disks in Linux”, we learned that a file can be created, formatted and mounted as a virtual disk in a bare metal or virtual machine. In the tutorial “LXD Containers Mount Host folders” we learned that the LXD host can share folders with a LXD container which is the recommended method.

The virtual disk capability is not easy to achieve inside of a LXD container because it relies on accessing the “loop” device on the LXD host and having privilege to execute mount commands. This is not recommended from a security perspective, but is valuable as a case study to understand how it might be accomplished.

I created a container without starting it using the “lxc init” as opposed to “lxc launch” which starts the container after it is created. I also created the container with my “untagged” profile which is covered in the video “Network Bridge vs Macvlan on LXD”.

My test container:

lxc init images:ubuntu/jammy test-lxd --profile default --profile untagged -c boot.autostart=true -c security.privileged=true -c security.syscalls.intercept.mount=true -c security.syscalls.intercept.mount.allowed=ext4 -c limits.memory=2048MB -c limits.cpu.allowance=20%

Next, I added the ability to access the loop device:

lxc config device add test-lxd loop-control unix-char path=/dev/loop-control

On my system, the “loop3” device was available. If your mount fails inside the container, try a different loop device:

lxc config device add test-lxd loop3 unix-block path=/dev/loop3

Next I started the container:

lxc start test-lxd

Connect to the LXD console for the container:

lxc exec test-lxd bash

Create a file to hold our virtual disk. Mine was 1GB:

truncate -s 1GiB /media/disk.img

Format the container:

mkfs.ext4 /media/disk.img

Create a mount point folder:

mkdir /mnt/virtual-disk

Mount the virtual disk:

mount -t ext4 -o loop /media/disk.img /mnt/virtual-disk

Check to see it is mounted:

mount | grep virtual-disk

You can also use the “df” command.

I also mounted an ISO image for the Ubuntu Server installation media in the video. I copied the ISO file into the /media folder beforehand.

Next, I created a mount point:

mkdir /mnt/ubuntu-server

To mount the ISO image:

mount -o loop /media/ubuntu-20.04.2-live-server-amd64.iso  /mnt/ubuntu-server

The mount command failed for me and I attached other loop devices to the LXD container:

lxc config device add test-lxd loop4 unix-block path=/dev/loop4

Ultimately, the mount did not work until I dismounted the virtual disk mounted earlier:

umount /mnt/virtual-disk

I am under the impression that I might only be able to mount one loop device at a time.

After that, it was possible to mount the ISO:

mount -o loop /media/ubuntu-20.04.2-live-server-amd64.iso  /mnt/ubuntu-server

This was mainly an exercise to see if it could be done. Thanks to Thomas Parrott over at the Linux Containers Forum for help in understanding the requirements to mount devices inside a LXD container.

Realize that the proper way to access data that is external to a LXD container I covered in my “LXD Containers Mount Host folders” video.