Containers are processes
A core benefit of using containers is that most of the time you don’t have to think about what’s happening under the hood. Tools like Docker and Kubernetes do a great job of hiding complexity from their users.
However, when you need to debug and secure containerized environments, it can be very helpful to understand how to interact with containers at a low level. Fortunately, because most containerization tools are built on Linux, you can use existing Linux tools to interact with and debug them.
When securing containerized environments, it’s also vital to understand how containers use layers of isolation—and how those layers can fail—so you can mitigate any risks.
This series will break down how containers work and walk through some practical ideas for securing and troubleshooting containerized environments. We’ll mainly focus on standard Docker-style containers throughout this series, but our examples will also apply to other container runtimes like Podman, containerd, and CRI-O.
In this tutorial, we'll demonstrate that containers are processes, use Linux tools to interact with containers, and explore what this means for securing container environments.
Containers are just processes
The first thing to understand about containers is that, from an operating system perspective, they’re processes—just like any other application that runs directly on the host. To demonstrate this, we can create a Linux virtual machine and install Docker on it. Note: if you’re interested in following along with the practical examples in this series, we recommend using a standard Linux VM instead of Docker for Windows/MacOS, as those tools add some complexity that makes it harder to see what’s happening.
Let's start by checking if there are any active processes named nginx on our tutorial playground. If you haven't already, click the "Start playground" button on the right. Then we can run the command below to look for nginx instances
ps -fC nginx
This should return an empty list, as we don’t have any NGINX web servers running at the moment.
Now, let's start a Docker container by using the nginx image from Docker Hub.
docker run --name webserver -d nginx:latest
Once the container is up, we'll run our ps
command again:
ps -fC nginx
This time, we get back something like the below, which shows us that several NGINX processes are now running on the machine. As far as our Linux machine is concerned, someone just ran NGINX on the host.

As we dig deeper into the notion that containers are processes, one initial question might be: how do you tell the difference between an NGINX server started from a Docker image and one that’s just been installed on a VM? There are a couple of ways to do that, but the first, easiest one is to check for running containers with docker ps
:

Alternatively, we could use Linux process tools to determine if the web server is running as a container for example with the --forest
option on ps
.
ps -ef --forest
This lets us see a hierarchy of processes. In this case, our NGINX processes have a parent process of containerd-shim-runc-v2
. You should see a shim process for each container running on the host. This shim process is part of containerd and is used by Docker to manage contained processes. The goal of this shim process is to allow containerd or the Docker daemon to be restarted without having to restart all the containers running on the host.

Interacting with a container as a process
We now know that containers are just processes—but what does that mean in terms of how we can interact with them? Being able to interact with them as processes is useful for both troubleshooting their operation and investigating changes in running containers (for example, in a forensic investigation). There are a couple of things to keep in mind here, but the first is that we can use the /proc
filesystem to get more information about our running containers.
The /proc
filesystem in Linux is a virtual or pseudo filesystem. It doesn’t contain real files—instead, it is populated with information about the running system. As long as a user has the right privileges on a host that runs Docker, they can use /proc
to access information about any container running on the host.
Let’s look at some information about the NGINX container we started up earlier. first we'll get a note of the PID of our nginx container, this time using docker inspect
which shows details of the running container
docker inspect --format '{{.State.Pid}}' webserver
Next we'll list the files in /proc
.
ls /proc
We will see a numbered directory for every process on the host including the PID that you got as output from the docker inspect
command. Each of these directories contains a variety of files and directories with information about that process, meaning that we can navigate into the directory for our container to find out more about our contained process.
It can also be helpful to use Linux tooling to work with containers that have been hardened to remove tools such as file editors or process monitors. Hardening container images is a common security recommendation, but it does make debugging trickier. You can edit files inside the container by accessing the container’s root filesystem from the /proc
directory on the host. Navigating to /proc/[PID]/root
will give you the directory listing of the contained process that has that PID.
You can run the command below, replacing [PID]
with the process ID of your container to see that output.
sudo ls /proc/[PID]/root
The result should look a lot like this.

We can confirm that this is the filesystem for our container, by creating a new file inside the container using docker exec
and then seeing the result in the proc filesystem
First run this docker exec
command to create a new file in the container
docker exec webserver touch /test_file
Then run the ls
command again, replacing [PID]
with the process ID of your container.
sudo ls /proc/[PID]/root
Conclusion
One of the first steps to understanding how containers work and how their security isolation is implemented, is realising that they're just processes.
Level up your Server Side game — Join 10,000 engineers who receive insightful learning materials straight to their inbox