How to check if process runs within a docker container (cgroup v2 linux host)
Asked Answered
M

1

9

How to check if a process is running from within a Docker container? I'd like a method that works reliably, and that is future-proof.

This was already asked and answered at How to determine if a process runs inside lxc/Docker?, however the answer is quite old, and it does not seem to work on a recent setup (Linux host with cgroups v2 enabled, Docker 20.10.x, kernel 5.10.x).

The top-rated answer (from the link above) suggests to check for the string docker in /proc/1/cgroup, however here's what I get:

# cat /proc/1/cgroup 
0::/

It seems to be due to the fact that cgroups v2 is enabled on my host (it used to work with cgroups v1).

Another answer suggests to check for the existence of the file /.dockerenv. It works:

# test -e /.dockerenv && echo ok
ok

However a comment from a Docker's maintainer (dated from 2016) suggests NOT to rely on this file (emphasis mine):

Originally, ".dockerenv" was for transmitting the environment variables of the container across the container boundary -- I would not recommend relying on its existence either (IIRC, that code you've linked to is the only reason it still exists). There's likely something incriminatory inside /sys/fs/cgroup, but I haven't checked recently.

-- https://github.com/moby/moby/issues/18355#issuecomment-220484748

So is there a better method than that? An answer from a Docker maintainer would be very much welcomed. Thanks!

Miniaturist answered 19/4, 2021 at 3:50 Comment(2)
I have the same exact problem. Did you find any solutions yet?Rosin
Just to be sure, you want to check if a process runs in a docker container or from within, because those are two very different things.Hawkinson
P
0

If proc/1/cgroup is / you are basically guaranteed to be in a containerlike system (however note that if cgroupns=host that you'll get the host view in your container, so be sure to check that case too). In most linux OS systemd is the init system so /proc/1/cgroup will be /init.scope, so if it is not equal to /init.scope you are probably in a container of some sorts, and I believe this should work for cgroupns=private as well as cgroupns=host. Edit: tested in a --priviliged container with systemd as init, and cgroupns=private, and that will also show up as /init.scope unfortunately, however so just checking /proc/1/cgroup seems like it is only a best-effort guess. However I believe only the host-level /sys/fs/cgroup.procs is allowed to contain procs, any other container should have /sys/fs/cgroup.procs contain 0 entries when in a container. So it seems checking if /sys/fs/cgroup.procs is empty -> container, if it is not empty you can still be cgroupns=host, but in that case you can check if /proc/1/cgroup is in a containerpath. Edit2: According to https://systemd.io/CONTAINER_INTERFACE/: If you write software that wants to detect whether it is run in a container, please check /proc/1/environ and look for the container= environment variable. This does require being root.

Papp answered 10/5, 2023 at 12:0 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.