How to remount the /proc filesystem in a docker as a r/w system?
If the goal is to set sysctl settings, docker has realized the issue and in 1.12+ you can use the --sysctl flag when running a docker container (or in your compose file) which will set the values inside the container before it is run.
This is sadly not (yet) integrated yet in the dockerfile syntax.
https://docs.docker.com/engine/reference/commandline/run/#configure-namespaced-kernel-parameters-sysctls-at-runtime
docker run --sysctl kernel.shmmax=1073741824 yourimage
Example docker-compose.yml (must use version 2.1):
version: '2.1'
services:
app:
sysctls:
- kernel.shmmax=1073741824
Access to full /proc in Docker container
This was already implemented in Docker 3 years ago for version 19.03, the solution is
--security-opt systempaths=unconfined
Unfortunately, it remains undocumented so far.
Note that it does not only allow access to unrestricted /proc
but also to some more directories, e.g., /sys/firmware
. But it should still be more restrictive than --privileged
.
docker with no volume running, where does container system file store?
The container's storage is composed of different layers, different layers will finally form a merged layer.
Let's make a small experiment next:
1. Start a container & setup a new file:
# docker run -idt --name trial debian /bin/bash
# docker exec -it trial /bin/bash
root@e6c2b6336753:/# echo "helloworld" > test.txt
root@e6c2b6336753:/# cat test.txt
helloworld
2. Find the merged storage layer id:
# docker inspect --format=" {{ .GraphDriver.Data.MergedDir }} " trial
/var/lib/docker/overlay2/8f2e14d33448cb83e581b2950a69faa827a012904051c845abf550273196f90f/merged
Here, 8f2e14d33448cb83e581b2950a69faa827a012904051c845abf550273196f90f
is the layer id.
3. Check layer:
# cd /var/lib/docker/overlay2/8f2e14d33448cb83e581b2950a69faa827a012904051c845abf550273196f90f/merged
root@shlava:/var/lib/docker/overlay2/8f2e14d33448cb83e581b2950a69faa827a012904051c845abf550273196f90f/merged# ls
bin boot dev etc home lib lib64 media mnt opt proc root run sbin srv sys test.txt tmp usr var
root@shlava:/var/lib/docker/overlay2/8f2e14d33448cb83e581b2950a69faa827a012904051c845abf550273196f90f/merged# cat test.txt
helloworld
So, as a conclusion, you could see from above, the file system contents could be found in /var/lib/docker/overlay2/
with layer id as folder, you could check the disk there.
Exploring Docker container's file system
Here are a couple different methods...
A) Use docker exec (easiest)
Docker version 1.3 or newer supports the command exec
that behave similar to nsenter
. This command can run new process in already running container (container must have PID 1 process running already). You can run /bin/bash
to explore container state:
docker exec -t -i mycontainer /bin/bash
see Docker command line documentation
B) Use Snapshotting
You can evaluate container filesystem this way:
# find ID of your running container:
docker ps
# create image (snapshot) from container filesystem
docker commit 12345678904b5 mysnapshot
# explore this filesystem using bash (for example)
docker run -t -i mysnapshot /bin/bash
This way, you can evaluate filesystem of the running container in the precise time moment. Container is still running, no future changes are included.
You can later delete snapshot using (filesystem of the running container is not affected!):
docker rmi mysnapshot
C) Use ssh
If you need continuous access, you can install sshd to your container and run the sshd daemon:
docker run -d -p 22 mysnapshot /usr/sbin/sshd -D
# you need to find out which port to connect:
docker ps
This way, you can run your app using ssh (connect and execute what you want).
D) Use nsenter
Use nsenter
, see Why you don't need to run SSHd in your Docker containers
The short version is: with nsenter, you can get a shell into an
existing container, even if that container doesn’t run SSH or any kind
of special-purpose daemon
how to redirect ps command in linux to look into other folder than /proc
the /proc
path is hardcoded in the source tree of the /bin/ps
binary file.
Thus, you need to recompile /bin/ps
Follow these steps to recompile /bin/ps
inside a container that mounts the host /proc
and use this new ps
to display the process list of the docker host from the container:
In this example, I do not use /host/proc
but /prod
, to avoid modifying the path length to the mount point of the procfs filesystem (increasing the path length could trigger runtime errors in some situations). I also use a container based on OpenSUSE Leap 42.1, since you have not described the base image you are using.
1- on the docker host, first download the /bin/ps sources:
fenyo@myhost# mkdir /root/git
fenyo@myhost# cd /root/git
fenyo@myhost# git clone https://gitlab.com/procps-ng/procps.git
fenyo@myhost# cd procps
2- replace any occurence of "/proc
by "/prod
in **/*.c
3- run your docker container, mounting procfs on /prod
in the container
fenyo@myhost# docker run -v /proc:/prod -v /root/git/procps:/root/git/procps -t -i --rm opensuse:42.1 bash
4- inside the docker container, recompile /bin/ps
bash-4.2# cd /root/git/procps
bash-4.2# zypper install -y gettext gettext-tools autoconf libtool pkg-config gcc make
bash-4.2# ./autogen.sh
bash-4.2# ./configure --without-ncurses
bash-4.2# make
Now, you can use /root/git/procps/ps/pscommand
as a replacement for /bin/ps
, in order to use /prod
instead of /proc
. With pscommand
, you will get a process list from the host, not from the container:
bash-4.2# ps -auxgww
USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
root 1 0.0 0.0 20064 3076 ? Ss 23:20 0:00 bash
root 5199 0.0 0.0 33340 2996 ? R+ 23:24 0:00 ps -auxgww
bash-4.2# /root/git/procps/ps/pscommand -auxgww
USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
root 1 0.0 0.0 33620 3956 ? Ss Jul03 1:13 /usr/lib/systemd/systemd --switched-root --system --deserialize 21
root 2 0.0 0.0 0 0 ? S Jul03 0:01 [kthreadd]
root 3 0.0 0.0 0 0 ? R Jul03 4:44 [ksoftirqd/0]
root 5 0.0 0.0 0 0 ? S< Jul03 0:01 [kworker/0:0H]
root 7 0.0 0.0 0 0 ? S Jul03 15:27 [rcu_preempt]
root 8 0.0 0.0 0 0 ? S Jul03 0:00 [rcu_sched]
root 9 0.0 0.0 0 0 ? S Jul03 0:00 [rcu_bh]
root 10 0.0 0.0 0 0 ? S Jul03 10:02 [rcuop/0]
root 11 0.0 0.0 0 0 ? S Jul03 0:00 [rcuos/0]
root 12 0.0 0.0 0 0 ? S Jul03 0:00 [rcuob/0]
root 13 0.0 0.0 0 0 ? S Jul03 0:06 [migration/0]
root 14 0.0 0.0 0 0 ? S Jul03 0:07 [watchdog/0]
root 15 0.0 0.0 0 0 ? S Jul03 0:06 [watchdog/1]
root 16 0.0 0.0 0 0 ? S Jul03 0:04 [migration/1]
root 17 0.0 0.0 0 0 ? S Jul03 1:07 [ksoftirqd/1]
root 19 0.0 0.0 0 0 ? S< Jul03 0:00 [kworker/1:0H]
root 20 0.0 0.0 0 0 ? S Jul03 2:42 [rcuop/1]
root 21 0.0 0.0 0 0 ? S Jul03 0:00 [rcuos/1]
root 22 0.0 0.0 0 0 ? S Jul03 0:00 [rcuob/1]
root 23 0.0 0.0 0 0 ? S Jul03 0:05 [watchdog/2]
root 24 0.0 0.0 0 0 ? S Jul03 0:06 [migration/2]
root 25 0.0 0.0 0 0 ? S Jul03 0:48 [ksoftirqd/2]
root 27 0.0 0.0 0 0 ? S< Jul03 0:00 [kworker/2:0H]
root 28 0.0 0.0 0 0 ? S Jul03 7:32 [rcuop/2]
root 29 0.0 0.0 0 0 ? S Jul03 0:00 [rcuos/2]
root 30 0.0 0.0 0 0 ? S Jul03 0:00 [rcuob/2]
root 31 0.0 0.0 0 0 ? S Jul03 0:05 [watchdog/3]
root 32 0.0 0.0 0 0 ? S Jul03 0:05 [migration/3]
root 33 0.0 0.0 0 0 ? S Jul03 0:37 [ksoftirqd/3]
[...]
Related Topics
"Must Be Connected to a Terminal Error" with Screen -X Command on a Linux Container
Graphing The Dag Generated by Make
Difference Between "Machine Hardware" and "Hardware Platform"
Grep for Text with Wild Card in Between
Set Environment Variables in an Aws Instance
Using Output of Previous Commands in Bash
Docker Run Hello-World Still Fails, Permission Denied
Fork() and Stdout/Stderr to The Console from Child Processes
Do_Install Error While Running Custom Bitbake in Poky Build
How to Get The System Home Directory in Cmake on Linux
Tar Error: Unexpected Eof in Archive
Rpm Installation Fails Due to Depencency /Bin/Sh Not Found
What's The Meaning of 'Blacklisted' on Gstreamer
In a Bash Script, What Would $'\0' Evaluate to and Why
How to Convert Fixed Size Dimension to Unlimited in a Netcdf File