loop device setup (losetup, mount, etc) fails in a container immediately after host reboot - centos

I'm trying to populate a disk image in a container environment (podman) on Centos 8. I had originally run into issues with accessing the loop device from the container until finding on SO and other sources that I needed to run podman as root and with the --privileged option.
While this did solve my problem in general, I noticed that after rebooting my host, my first attempt to setup a loop device in the container would fail (failed to set up loop device: No such file or directory), but after exiting and relaunching the container it would succeed (/dev/loop0). If for some reason I needed to set up a second loop device (/dev/loop1) in the container (after having gotten a first one working), it too would fail until I exited and relaunched the container.
Experimenting a bit further, I found I could avoid the errors entirely if I ran losetup --find --show <file created with dd> enough times to attach the maximum number of loop devices I would need, then detached all of those with losetup -D, I could avoid the loop device errors in the container entirely.
I suspect I'm missing something obvious about what losetup does on the host which it is apparently not able to do entirely within a container, or maybe this is more specifically a Centos+podman+losetup issue. Any insight as to what is going on and why I have to preattach/detach the loop devices after a reboot to avoid problems inside my container?
Steps to reproduce on a Centos 8 system (after having attached/detached once following a reboot):
$ dd if=/dev/zero of=file bs=1024k count=10
10+0 records in
10+0 records out
10485760 bytes (10 MB, 10 MiB) copied, 0.00826706 s, 1.3 GB/s
$ cp file 1.img
$ cp file 2.img
$ cp file 3.img
$ cp file 4.img
$ sudo podman run -it --privileged --rm -v .:/images centos:8 bash
[root#2da5317bde3e /]# cd images
[root#2da5317bde3e images]# ls
1.img 2.img 3.img 4.img file
[root#2da5317bde3e images]# losetup --find --show 1.img
/dev/loop0
[root#2da5317bde3e images]# losetup --find --show 2.img
losetup: 2.img: failed to set up loop device: No such file or directory
[root#2da5317bde3e images]# losetup -D
[root#2da5317bde3e images]# exit
exit
$ sudo podman run -it --privileged --rm -v .:/images centos:8 bash
[root#f9e41a21aea4 /]# cd images
[root#f9e41a21aea4 images]# losetup --find --show 1.img
/dev/loop0
[root#f9e41a21aea4 images]# losetup --find --show 2.img
/dev/loop1
[root#f9e41a21aea4 images]# losetup --find --show 3.img
losetup: 3.img: failed to set up loop device: No such file or directory
[root#f9e41a21aea4 /]# losetup -D
[root#f9e41a21aea4 images]# exit
exit
$ sudo podman run -it --privileged --rm -v .:/images centos:8 bash
[root#c93cb71b838a /]# cd images
[root#c93cb71b838a images]# losetup --find --show 1.img
/dev/loop0
[root#c93cb71b838a images]# losetup --find --show 2.img
/dev/loop1
[root#c93cb71b838a images]# losetup --find --show 3.img
/dev/loop2
[root#c93cb71b838a images]# losetup --find --show 4.img
losetup: 4.img: failed to set up loop device: No such file or directory

I know it's a little old but I've stumbled across similar problem and here what I've discovered:
After my vm boots up it does not have any loop device configured and it's ok since mount can create additional devices if needed but:
it seems that docker puts overlay over /dev so it won't see any changes that were done in /dev/ after container was started so even if mount requested new loop devices to be created and they actually were created my running container won't see it and fail to mount because of no loop device available.
Once you restart container it will pick up new changes from /dev and see loop devices and successfully mount until it run out of them and try to request again.
So what i tried (and it seems working) I passed /dev to docker as volume mount like this
docker -v /dev:/dev -it --rm <image> <command> and it did work.
If you still have this stuff I was wondering if you could try it too to see if it helps.

The only other method I can think of, beyond what you've already found is to create the /dev/loop devices yourself on boot. Something like this should work:
modprobe loop # This may not be necessary, depending on your kernel build but is harmless.
major=$(grep loop /proc/devices | cut -c3)
for index in 0 1 2 3 4 5
do
mknod /dev/loop$i $major $i
done
Put this in /etc/rc.local, your system's equivalent or otherwise arrange for it to run on boot.

Related

cannot connect to "workspaceMount" at container launch from vscode

using vscode and wsl2, I have tried to launch a container using the default method and no customization. This generated the same error as below.
so following vscode docs I set a "workspaceMount" in devcontainer.json
"workspaceMount": "source=${localWorkspaceFolder},target=/workspaces/myRepo,type=bind,consistency=delegated",
"workspaceFolder": "/workspaces",
I select Reopen in container, the launch sequence happens but an error is generated
a mount config is invalid, make sure it has the right format and a source folder that exists on the machine where the Docker daemon is running
the log error is
Command failed: docker run -a STDOUT -a STDERR --mount source=d:\git\myRepo,target=/workspaces/myRepo,type=bind,consistency=delegated --mount type=volume,src=vscode,dst=/vscode -l vsch.quality=stable -l vsch.remote.devPort=0 -l vsch.local.folder=d:\git\myRepo --cap-add=SYS_PTRACE --security-opt seccomp=unconfined --entrypoint /bin/sh vsc-myRepo-a878aa9edbcf04f717c76e764dabcde6 -c echo Container started ; trap "exit 0" 15; while sleep 1 & wait $!; do :; done
by launching the container from docker desktop I can confirm
cd /workspaces
ls -l
drwxr-xr-x 2 root root 4096 Dec 3 11:48 myRepo
Is this issue due to owner root:root ?
Should this be changed by chown in the Dokerfile? if so could you provide a sample code to do this, is it by RUN chown ...?
I guess you followed the documentation in https://code.visualstudio.com/docs/remote/containers-advanced
The source should contains the subfolder "myRepo" and the target only "workspaces"
"workspaceMount": "source=${localWorkspaceFolder}/myRepo,target=/workspaces,type=bind,consistency=delegated",
"workspaceFolder": "/workspaces",

gcsfuse won't write to folder

I am trying to figure out why if I don't need to do this step
(Ubuntu before wily only) Add yourself to the fuse group, then log out and back in:
sudo usermod -a -G fuse $USER
exit
Then why can't I write to files; I keep getting the following error:
Using mount point: /mnt/c/Users/russe/Documents/gstorage
Opening GCS connection...
Opening bucket...
Mounting file system...
daemonize.Run: readFromProcess: sub-process: mountWithArgs: mountWithConn: Mount: mount: running fusermount: exit status 1
stderr:
fusermount: fuse device not found, try 'modprobe fuse' first
I am using Ubuntu (on Windows App Store).
Even running:
sudo mount -t gcsfuse -o implicit_dirs,allow_other,uid=1000,gid=1000,key_file=/mnt/c/Users/russe/Documents/RadioMedia-ba86f56a2aa6.json radiomediapod
cast gstorage
had an error:
Calling gcsfuse with arguments: --uid 1000 --gid 1000 --key-file /mnt/c/Users/russe/Documents/RadioMedia-ba86f56a2aa6.json -o rw --implicit-dirs -o allow_other radiomediapodcast /mnt/c/Users/russe/Documents/gstorage
Using mount point: /mnt/c/Users/russe/Documents/gstorage
Opening GCS connection...
Opening bucket...
Mounting file system...
daemonize.Run: readFromProcess: sub-process: mountWithArgs: mountWithConn: Mount: mount: running fusermount: exit status 1
stderr:
fusermount: fuse device not found, try 'modprobe fuse' first
running gcsfuse: exit status 1
The problem you are having might be because of two things:
-Permissions on the OS after mounting, to solve this mount your bucket with the following command:
sudo mount -t gcsfuse -o implicit_dirs,allow_other,uid=1000,gid=1000,key_file=<KEY_FILE>.json <BUCKET> <PATH>
-Permissions of your service account, to validate this you can go on the console to IAM & admin and verify that the service account being used has Storage Admin Role.

MongoDB Docker container: ERROR: Cannot write pid file to /tmp/tmp.aLmNg7ilAm: No space left on device

I started a MongoDB container like so:
docker run -d -p 27017:27017 --net=cdt-net --name cdt-mongo mongo
I saw that my MongoDB container exited:
0e35cf68a29c mongo "docker-entrypoint.s…" Less than a second ago Exited (1) 3 seconds ago cdt-mongo
I checked my Docker logs, I see:
$ docker logs 0e35cf68a29c
about to fork child process, waiting until server is ready for connections.
forked process: 21
2018-01-12T23:42:03.413+0000 I CONTROL [main] ***** SERVER RESTARTED *****
2018-01-12T23:42:03.417+0000 I CONTROL [main] ERROR: Cannot write pid file to /tmp/tmp.aLmNg7ilAm: No space left on device
ERROR: child process failed, exited with error number 1
Does anyone know what this error is about? Not enough space in the container?
I had to delete old Docker images to free up space, here are the commands I used:
# remove all unused / orphaned images
echo -e "Removing unused images..."
docker rmi -f $(docker images --no-trunc | grep "<none>" | awk "{print \$3}") 2>&1 | cat;
echo -e "Done removing unused images"
# clean up stuff -> using these instructions https://lebkowski.name/docker-volumes/
echo -e "Cleaning up old containers..."
docker ps --filter status=dead --filter status=exited -aq | xargs docker rm -v 2>&1 | cat;
echo -e "Cleaning up old volumes..."
docker volume ls -qf dangling=true | xargs docker volume rm 2>&1 | cat;
We've experienced this problem recently while using docker-compose with mongo and a bunch of other services. There are two fixes which have worked for us.
Clear down unused stuff
# close down all services
docker-compose down
# clear unused docker images
docker system prune
# press y
Increase the image memory available to docker - this will depend on your installation of docker. On Mac, for example, it defaults to 64Gb and we doubled it to 128Gb via the UI.
We've had this problem in both Windows and Mac and the above fixed it.

Boot2Docker (on Windows) running Mongo with shared folder (This file system is not supported)

I am trying to start a Mongo container using shared folders on Windows using Boot2Docker. When starting using run -it -v /c/Users/310145787/Desktop/mongo:/data/db mongo i get a warning message inside the container saying:
WARNING: This file system is not supported.
After starting mongo shutsdown immediately.
Any hints or tips on how to solve this?
Apparently, according to this gist and Sev (sevastos), mongo doesn't support mounted volume through the VirtualBox shared folder:
See mongoDB Productions Notes:
MongoDB requires a filesystem that supports fsync() on directories.
For example, HGFS and Virtual Box’s shared folders do not support this operation.
the easiest solutions of all and a proper way for data persistance is Data Volumes:
Assuming you have a container that has VOLUME ["/data"]
# Create a data volume
docker create -v /data --name yourData busybox true
# and use
docker run --volumes-from yourData ...
This isn't always ideal (but the following is for Mac, by Edward Chu (chuyik)):
I don't think it's a good solution, because the data just moved to another container right?
But it still inside the container rather than local system(mac disk).
I found another solution, that is to use sshfs to map data between boot2docker vm and your mac, which may be better since data is not stored inside linux container.
Create a directory to store data inside boot2docker:
boot2docker ssh
mkdir -p /mnt/sda1/dev
Use sshfs to link boot2docker and mac:
echo tcuser | sshfs docker#localhost:/mnt/sda1/dev <your mac dir path> -p 2022 -o password_stdin
Run image with mongo installed:
docker run -v /mnt/sda1/dev:/data/db <mongodb-image> mongod
The corresponding boot2docker issue points out to docker issue 12590 ( Problem with -v shared folders in 1.6 #12590), which points to the work around of using double-slash.
using a double slash seems to work. I checked it locally and it works.
docker run -d -v //c/Users/marco/Desktop/data:/data <image name>
it also works with
docker run -v /$(pwd):/data
As an workaround I just copy from a folder before mongo deamon starts. Also, in my case I don't care of journal files, so i only copy database files.
I've used this command on my docker-compose.yml
command: bash -c "(rm /data/db/*.lock && cd /prev && cp *.* /data/db) && mongod"
And everytime before stoping the container I use:
docker exec <container_name> bash -c 'cd /data/db && cp $(ls *.* | grep -v *.lock) /prev'
Note: /prev is set as a volume. path/to/your/prev:/prev
Another workaround is to use mongodump and mongorestore.
in docker-compose.yml: command: bash -c "(sleep 30; mongorestore
--quiet) & mongod"
in terminal: docker exec <container_name> mongodump
Note: I use sleep because I want to make sure that mongo started, and it takes a while.
I know this involves manual work etc, but I am happy that at least I got mongo with existing data running on my Windows 10 machine, and still can work on my Macbook when I want.
It's seems like you don't need the data directory for MongoDb, removing those lines from your docker-composer.yml should run without problems.
The data directory is only used by mongo for cache.

how to install busybox in android using adb

I am trying to install busybox on an android emulator.
I downloaded and compiled busybox and have the busybox binary on my pc.
i then did adb push busybox /data/local/tmp
then did adb shell, then #cd /data/local/tmp , then #chmod 777 busybox, then tried #./busybox --install it says busybox command not found.
I also copied the file to /system/busybox. but ./busybox --install says busybox command not found.
First do adb push busybox /data/local/busybox
to copy the busybox into the android phone system
then go to the android shell by doing adb shell.
Get the superuser by typing su
from you android phone grant superuser request
then back to the shell and type
cd /data/local
chmod 755 busybox
./busybox
mount -o remount,rw -t yaffs2 /dev/block/mtdblock4 /system
mkdir /system/xbin
cp /data/local/busybox /system/xbin
cd /system/xbin
busybox --install .
mount -o ro,remount -t yaffs2 /dev/block/mtdblock4 /system
sync
reboot
Note: /dev/block/mtdblock4 may not be the /system partition on every device or emulator. It's best to execute the 'mount' command without parameters first in the shell, and look which device or partition is mounted as /system.
On a rooted phone, install this apk: https://f-droid.org/en/packages/ru.meefik.busybox/
f-droid is a good option as it is open source and officially allows downloading APKs, unlike the play store, which may not be available on test devices.
That app also has a simple install GUI, but the most reliable way to install it is to do simply:
adb shell
cp /data/data/ru.meefik.busybox/files/bin/busybox /system/xbin/
busybox ls
There are a couple of small changes to gregko and hayder Jawad's answer to get this working on the Pixel 2 emulator.
You have to start the emulator using the -writable-system flag as per this answer, otherwise you won't be able to remount the /system directory with the rw flag.
On the Pixel 2 emulator, /system is mounted at /dev/block/vda and /system/xbin already exists.
Thus, assuming you've pushed the binary to /data/local/busybox as per the first half of the answer, the shell commands to install busybox into the Pixel 2 emulator are
su
cd /data/local
chmod 755 busybox
./busybox
mount -o rw,remount -t ext4 /dev/block/vda /system
cp /data/local/busybox /system/xbin
cd /system/xbin
busybox --install .
mount -o ro,remount -t ext4 /dev/block/vda /system
sync
reboot
The busybox download page might be a bit unclear for beginners (like me). For 32-bit x86 processors, you'll want to use the i686 binary file.
I did the following very simple steps:
Download busybox apk to my laptop from here
Install apk using: adb install <apk file path>
Run busybox shell: busybox ash
Once in shell you can use busybox commands.