Cloud Native 14 min read

Unveiling Docker’s Overlay2: How Images Are Stored and Managed

This article explains Docker's OverlayFS/Overlay2 storage driver, detailing its layered image architecture, union‑mount mechanics, read/write behavior, metadata organization, and the roles of image, layer, and init layers within the container filesystem.

MaGe Linux Operations
MaGe Linux Operations
MaGe Linux Operations
Unveiling Docker’s Overlay2: How Images Are Stored and Managed

Overview

Docker images are built as a stack of layers, each stored under /var/lib/docker/<storage-driver>/. The storage driver may be AUFS, OverlayFS, VFS, Btrfs, etc. This article focuses on the OverlayFS driver (used on CentOS 7.1+), describing its storage principles and directory structure.

OverlayFS

Introduction

OverlayFS is a stacked file system that merges multiple lower (read‑only) directories with a single upper (read‑write) directory, presenting a unified view called the merged directory. Docker provides two drivers: overlay and overlay2. overlay2 improves inode utilization and requires Docker ≥ 17.06.02 on an ext4 or xfs host filesystem.

Union Mount

OverlayFS uses three directories: lowerdir (one or more read‑only layers), upperdir (the writable layer), and workdir (temporary work area). After mounting, the merged directory is what users see. The mount command syntax is:

mount -t overlay overlay -o lowerdir=lower1:lower2:lower3,upperdir=upper,workdir=work merged_dir

In the demonstration, three directories A, B, C are created as lower layers, a work directory is prepared, and the union is mounted to /tmp/test. The merged view shows files from all lower layers, with files from the uppermost layer taking precedence when names clash.

Running mount again reveals the mount options, confirming the union‑mount configuration.

Docker’s Overlay Driver

The Docker overlay driver implements the same three‑layer model. Docker stores the lower (read‑only image) layers, the upper (container) layer, and the merged view under /var/lib/docker/overlay2/ (or /var/lib/docker/overlay/ for the older driver). The lowerdir corresponds to the image’s rootfs, the upperdir holds all container writes (copy‑on‑write), and the merged directory is the container’s visible filesystem.

Demonstration

After launching a container, inspecting its overlay mount point shows the merged, lowerdir, upperdir, and workdir directories. Multiple lowerdirs are linked via symbolic links, and the upperdir records all modifications.

How It Works

Read : Docker first checks the upperdir; if the file is absent, it reads from the lowerdir.

Write :

On first write, Docker performs a copy_up operation, copying the file from the lowerdir to the upperdir (copy‑on‑write).

File or directory deletions create a whiteout file in the upperdir, hiding the original file in the lowerdir without actually removing it.

Notes

Copy‑up occurs only on the first write; subsequent writes modify the copy.

OverlayFS works with two layers (lower + upper) and is faster than AUFS.

Whiteout files only mask deletions; the underlying image layer remains unchanged, which explains why docker commit images grow even after container‑side deletions.

Overlay2 Image Storage Structure

Pulling an Ubuntu image yields four layers, stored under /var/lib/docker/overlay2/. A special l directory holds short‑link names to avoid command‑line length limits.

Each image layer directory contains a diff folder (the layer’s filesystem content) and a link file (the short name).

Image Metadata

Image metadata resides in

/var/lib/docker/image/<storage-driver>/imagedb/content/sha256/

, with JSON files named after the image ID. The JSON records the rootfs, creation time, history, entrypoint, CMD, etc. The diff_id entries map to the actual layer directories.

Layer Metadata

Layer metadata is stored under

/var/lib/docker/image/<storage-driver>/layerdb/sha256/<chainID>/

. Each chainID directory contains three files: cache-id: UUID linking to the corresponding directory in /var/lib/docker/overlay2/. diff: The layer’s diff_id (SHA‑256 of the layer content). size: Size of the layer.

The chainID is computed recursively: the base layer’s chainID equals its diffID; for other layers, chainID(n)=SHA256(chainID(n‑1) + " " + diffID(n)).

Mounted Layer Information

Mounted layer data (init‑id, mount‑id, parent chainID) is kept in

/var/lib/docker/image/<storage-driver>/layerdb/mounts/<container_id>/

. The init layer (named <uuid>-init) stores files such as /etc/hosts and /etc/resolv.conf that need to be mutable per container but are not part of the image.

Summary of Layers

Image layer (rootfs): read‑only base filesystem.

Init layer: mutable configuration files for the container.

Container (upper) layer: writable layer presented to the user via the merged view.

All three layers are combined through union‑mount to form the container’s final filesystem.

Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

DockerLinuxFilesystemoverlayfscontainer storageoverlay2
MaGe Linux Operations
Written by

MaGe Linux Operations

Founded in 2009, MaGe Education is a top Chinese high‑end IT training brand. Its graduates earn 12K+ RMB salaries, and the school has trained tens of thousands of students. It offers high‑pay courses in Linux cloud operations, Python full‑stack, automation, data analysis, AI, and Go high‑concurrency architecture. Thanks to quality courses and a solid reputation, it has talent partnerships with numerous internet firms.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.