21 Days of Docker-Day 4- Docker Container Under The Hood

Let’s discuss a few key things and then come back to these questions

Namespaces

Docker uses a technology called namespaces to provide the isolated workspace called the container. When you run a container, Docker creates a set of namespaces for that container.

These namespaces provide a layer of isolation. Each aspect of a container runs in a separate namespace and its access is limited to that namespace.

Docker Engine uses namespaces such as the following on Linux:

  • The pid namespace: Process isolation (PID: Process ID).
  • The net namespace: Managing network interfaces (NET: Networking).
  • The ipc namespace: Managing access to IPC resources (IPC: InterProcess Communication).
  • The mnt namespace: Managing filesystem mount points (MNT: Mount).
  • The uts namespace: Isolating kernel and version identifiers. (UTS: Unix Timesharing System).

Control groups

Docker Engine on Linux also relies on another technology called control groups (cgroups). A cgroup limits an application to a specific set of resources. Control groups allow Docker Engine to share available hardware resources to containers and optionally enforce limits and constraints. For example, you can limit the memory available to a specific container.

Union file systems

Union file systems, or UnionFS, are file systems that operate by creating layers, making them very lightweight and fast. Docker Engine uses UnionFS to provide the building blocks for containers. Docker Engine can use multiple UnionFS variants, including AUFS, btrfs, vfs, and DeviceMapper.

Container format

Docker Engine combines the namespaces, control groups, and UnionFS into a wrapper called a container format. The default container format is libcontainer.

Now with basics out of the way, let start with the first question

What is the Kernel version of my Docker container?

Host Operating System Kernel Version

$ uname -a
Linux plakhera.example.com 3.10.0-1062.1.1.el7.x86_64 #1 SMP Fri Sep 13 22:55:44 UTC 2019 x86_64 x86_64 x86_64 GNU/Linux

Docker Container Kernel Version

# uname -a
Linux 789f45a23f9f 3.10.0-1062.1.1.el7.x86_64 #1 SMP Fri Sep 13 22:55:44 UTC 2019 x86_64 GNU/Linux

Looking at the above output the kernel version of both host and Docker container look same. Is this possible?

Answer for the above question is Yes, as Docker uses host OS kernel, there is no custom or additional kernel inside the container. All containers which run on a machine are sharing this host kernel.

Docker uses resource isolation features of the Linux kernel such as cgroups and kernel namespaces to allow independent containers to run within a single Linux instance, avoiding the overhead of starting virtual machines.

https://www.docker.com/resources/what-container

Why the first process inside the Docker container run as PID 1?

[root@733c8448e2c8 /]# ps aux
USER       PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
root         1  0.1  0.0  12016  1920 pts/0    Ss+  22:33   0:00 bash
root        14  0.2  0.0  12016  2172 pts/1    Ss   22:34   0:00 bash
root        29  0.0  0.0  43936  1736 pts/1    R+   22:34   0:00 ps aux

In a traditional Unix system, PID 1 is usually the init/systemd process. When a container is started, the application becomes PID 1 in its assigned namespace. So the question that arises is, does it really matter which process becomes PID 1 inside a container ?. PID 1 usually has different roles to play.

A process running as PID 1 inside a container is treated specially by Linux: it ignores any signal with the default action. So, the process will not terminate on SIGINT or SIGTERM unless it is coded to do so.

This is the process responsible for keeping the container up and running, if you kill this process basically you are killing/stopping the container.

How much default memory is allocated to my Docker container?

Host Operating System

$ free -m
total        used        free      shared  buff/cache   available
Mem:           7719         696        6161          23         860        6763
Swap:          2047           0        2047

Docker Container

[root@733c8448e2c8 /]# free -m
total        used        free      shared  buff/cache   available
Mem:           7719         729        6128          23         860        6730
Swap:          2047           0        2047

The default is unlimited, aka whatever the OS gives it.

 Is there is any way to restrict how much amount of memory we can allocate to the container?

Answer to that question is yes by using

-m, — memory bytes Memory limit
  • Let see how to do it
$ docker container run --memory 512m --rm -it centos bash
  • But when I logged inside the container and check the memory used
# free -m
total        used        free      shared  buff/cache   available
Mem:           7719         741        6103          23         874        6717
Swap:          2047           0        2047
  • Look like — memory flag is not working OR is I am doing something wrong?
  • The memory limit is enforced via cgroups. To find out the memory limit of the given cgroup
# cat /sys/fs/cgroup/memory/memory.limit_in_bytes
536870912

OR

  • Use docker stats command
docker container stats <container id>
$ docker container stats e690da01568f
CONTAINER ID        NAME                CPU %               MEM USAGE / LIMIT   MEM %               NET I/O             BLOCK I/O           PIDS
e690da01568f        peaceful_fermi      0.00%               528KiB / 512MiB     0.10%               446B / 0B           5.48MB / 0B         1
  • Similar to memory you can limit CPU
$ docker run --cpus=1 --rm -dt centos bash

-c, — cpu-shares int CPU shares (relative weight)

Before wrap up, I just want to talk about Privileged Container

  • Running a container with the — privileged flag gives all the capabilities to the container
$ docker container run -it --privileged centos:centos7 bash
  • For full file system privilege, start the container as follows
docker run -it -v /:/home --privileged centos:centos7 bash

NOTE: Please make sure, you know what you are doing before running this command, as now you have full access to the host system.

This is a good place, to stop for Day 4

Please follow me with my Journey

This time to make learning more interactive, I am adding

  • Slack
  • Meetup

Please feel free to join this group.

Slack: 

https://100daysofdevops.slack.com/join/shared_invite/enQtNzg1MjUzMzQzMzgxLWM4Yjk0ZWJiMjY4ZWE3ODBjZjgyYTllZmUxNzFkNTgxZjQ4NDlmZjkzODAwNDczOTYwOTM2MzlhZDNkM2FkMDA

Meetup Group

If you are in the bay area, please join this meetup group https://www.meetup.com/100daysofdevops/

2 Replies to “21 Days of Docker-Day 4- Docker Container Under The Hood”

  1. I was wondering if you ever considered changing the structure of your blog? Its very well written; I love what youve got to say. But maybe you could a little more in the way of content so people could connect with it better. Youve got an awful lot of text for only having 1 or two pictures. Maybe you could space it out better?

    1. Thanks for the feedback, I will try to add more pics in the future blog but at the same time, I want thing to be more technical rather than story telling

Leave a Reply

Your email address will not be published.