This episode breaks down the security core of unprivileged containers: the /etc/subuid and /etc/subgid files, UID/GID mapping configuration via lxc.idmap, lxc-usernet network quotas, and best practices for mapping the 0-65536 range in trusted environments.

In episode 5 we introduced unprivileged containers in general. Now we break down the mechanism that makes them safe: user namespaces and ID mapping (idmap). This is why root inside the container isn't dangerous on the host — and it's what you need to understand when a bind-mount feels "odd", or when you want to adjust the mapping to share files with the host. In episode 15 we go into the details.
Inside an unprivileged container, UID 0 (root) is only a local view. On the host, that UID is actually mapped to a large number (e.g. 100000) belonging to a regular user. Because of this mapping, "root" in the container has no host-root power — it works with a regular user's rights when touching host resources.
The mapping goes one way: container UID → host UID. This range is defined twice: once in /etc/subuid//etc/subgid (the system's allocation for the user), and once in the container config via lxc.idmap.
These files determine the sub-UID and sub-GID allocations for each user — the ranges of numbers allowed for unprivileged containers:
root:100000:65536
devnull:165536:65536The format is: <user>:<base>:<count>. The line devnull:165536:65536 means user devnull may use UIDs 165536 through 165536+65536-1 for their containers. Each container owned by that user uses a slice of this range.
Check your allocation:
grep "$USER" /etc/subuid
grep "$USER" /etc/subgidWarning
If /etc/subuid and /etc/subgid are empty for your user, unprivileged containers can't be created — or are created but fail to start with an idmap error. Add the lines (e.g. sudo usermod --add-subuids 100000-165535 $USER) before starting. This is the number one cause of unprivileged failures on fresh installs.
The mapping inside the container config is written with lxc.idmap. The format is: lxc.idmap = <ttype> <nsid> <hostid> <range>.
ttype — u for UID, g for GID.nsid — UID/GID inside the container namespace.hostid — UID/GID on the host.range — the number of consecutively mapped IDs.A typical unprivileged container (modern template) uses two lines for UID and two for GID:
lxc.idmap = u 0 100000 65536
lxc.idmap = g 0 100000 65536Meaning: container UIDs 0-65535 map to host UIDs 100000-165535. Same for GIDs. With this mapping, container UID 0 = host UID 100000, container UID 1000 = host UID 101000.
To share a directory with a host user (e.g. host user UID 1000 wants files inside the container as UID 1000), you can add a mapping:
lxc.idmap = u 0 100000 1000
lxc.idmap = g 0 100000 1000
lxc.idmap = u 1000 1000 1
lxc.idmap = g 1000 1000 1
lxc.idmap = u 1001 101001 64535
lxc.idmap = g 1001 101001 64535With this pattern, container UID 1000 maps one-to-one to host UID 1000 — so files owned by host user 1000 can be read/written directly from inside the container. This trick is used together with bind-mounts (episode 11) to share data between host and container.
Tip
Check the active mapping from inside the container: lxc-attach -n c1 -- cat /proc/self/uid_map. A line 0 100000 65536 shows the mapping currently in effect. This is the fastest way to verify your lxc.idmap configuration.
In episode 6 we touched lxc-usernet. Now its role becomes clear: a regular user isn't allowed to create veths attached to a host bridge. The /etc/lxc/lxc-usernet file grants that permission explicitly — it's the "network allocation" for unprivileged users.
# <user> <type> <link> <parent bridge> <count>
devnull veth lxcbr0 10Meaning: user devnull may create up to 10 veths connected to lxcbr0. Without this entry, lxc-start of an unprivileged container fails with "Operation not permitted" when creating the network.
grep "$USER" /etc/subuid
grep "$USER" /etc/subgid
lxc-attach -n c1 -- cat /proc/self/uid_map
grep "$USER" /etc/lxc/lxc-usernetKey takeaways:
/etc/subuid and /etc/subgid grant ID range allocations for unprivileged containers.lxc.idmap maps container UID/GID to the host: u 0 100000 65536.lxc-usernet grants network (veth) quotas to regular users.In the next episode 16 we'll cover security & CVEs — the fact of the CVE-2026-39402 fix in LXC 7.0, the importance of routine patching, host-container isolation, and the threat model: unprivileged + AppArmor + seccomp + latest kernel.