LINUXOR.SK ... open source notes ...

Namespaces 11 - IPC namespace

category: learnz/namespaces · date: 2026-10-04 · author: LALA · theme: github

Linux Namespaces Learning · Previous: Connecting two network namespaces (ns1, ns2) - with two ports on a distributed OVS switch (openvswitch) · Next: USER namespace

IPC (interprocess communication) namespaces in Linux

1 Introduction

The IPC namespace isolates the interprocess communication objects that are not named by a path in the filesystem: the System V objects (message queues, semaphore arrays, shared memory segments) and the POSIX message queues. Each IPC namespace has its own set of System V identifiers and its own POSIX message queue filesystem. Processes in the same IPC namespace can reach each other's objects; processes in different IPC namespaces cannot.

IPC namespace
IPC namespace

In the picture, PID2 and PID3 share IPC namespace2 and can talk through these objects, and so can PID4 and PID5 in IPC namespace3. Between PID3 and PID4 there is no such channel, although all four run on the same kernel.

An IPC namespace does not cover anything that is a file. POSIX shared memory lives as files in /dev/shm, named POSIX semaphores too, and UNIX sockets and FIFOs have path names. Those follow the mount namespace and the file permissions.

The examples were run as an ordinary user on a 6.12 kernel with util-linux 2.40. They borrow --user --map-root-user from the next article, the USER namespace, so that no root is needed; as root the same commands work with unshare --ipc alone.

2 Working with IPC namespaces

2.1 IPC objects in the default namespace

Note the IPC namespace of the shell and create one object of each System V kind with ipcmk: a message queue, a shared memory segment of 4096 bytes and a semaphore array with one semaphore.

bash
$ readlink /proc/self/ns/ipc
$ ipc:[4026531839]
$ ipcmk -Q
$ Message queue id: 0
$ ipcmk -M 4096
$ Shared memory id: 2
$ ipcmk -S 1
$ Semaphore id: 4

ipcs lists them.

bash
$ ipcs
$ 
$ ------ Message Queues --------
$ key        msqid      owner      perms      used-bytes   messages
$ 0x3955e60c 0          user       644        0            0
$ 
$ ------ Shared Memory Segments --------
$ key        shmid      owner      perms      bytes      nattch     status
$ 0x4475c7b5 2          user       644        4096       0
$ 
$ ------ Semaphore Arrays --------
$ key        semid      owner      perms      nsems
$ 0x1d83be53 4          user       644        1
$ 

2.2 A new IPC namespace sees none of them

Run the same ipcs in a new IPC namespace. All three tables are empty.

bash
$ unshare --user --map-root-user --ipc ipcs
$ 
$ ------ Message Queues --------
$ key        msqid      owner      perms      used-bytes   messages
$ 
$ ------ Shared Memory Segments --------
$ key        shmid      owner      perms      bytes      nattch     status
$ 
$ ------ Semaphore Arrays --------
$ key        semid      owner      perms      nsems
$ 

2.3 Objects created inside vanish with the namespace

Create a message queue inside a new IPC namespace. The numbering starts again at 0, and the owner is the root of the user namespace.

bash
$ unshare --user --map-root-user --ipc sh -c "readlink /proc/self/ns/ipc; ipcmk -Q; ipcs -q"
$ ipc:[4026534271]
$ Message queue id: 0
$ 
$ ------ Message Queues --------
$ key        msqid      owner      perms      used-bytes   messages
$ 0x63216084 0          root       644        0            0
$ 

That namespace ended with its last process, and the queue went with it. A second new namespace is empty again, and the default namespace still has only its own queue from step 2.1. On the host a System V object stays until somebody removes it; in a namespace it cannot outlive the namespace.

bash
$ unshare --user --map-root-user --ipc ipcs -q
$ 
$ ------ Message Queues --------
$ key        msqid      owner      perms      used-bytes   messages
$ 
$ ipcs -q
$ 
$ ------ Message Queues --------
$ key        msqid      owner      perms      used-bytes   messages
$ 0x3955e60c 0          user       644        0            0
$ 

2.4 POSIX message queues

POSIX message queues are shown by a filesystem of type mqueue, usually mounted on /dev/mqueue, and their limits are in /proc/sys/fs/mqueue. Creating a file there creates a queue.

bash
$ findmnt /dev/mqueue
$ TARGET      SOURCE FSTYPE OPTIONS
$ /dev/mqueue mqueue mqueue rw,nosuid,nodev,noexec,relatime
$ touch /dev/mqueue/demo-queue
$ ls /dev/mqueue
$ demo-queue
$ cat /dev/mqueue/demo-queue
$ QSIZE:0          NOTIFY:0     SIGNO:0     NOTIFY_PID:0
$ cat /proc/sys/fs/mqueue/queues_max
$ 256

A new IPC namespace has its own, empty set of queues, but the directory /dev/mqueue you look at is still the mount that belongs to the old namespace, so the listing misleads:

bash
$ unshare --user --map-root-user --ipc ls /dev/mqueue
$ demo-queue

Add a mount namespace and mount the mqueue filesystem of the new IPC namespace. Now the host's queue is not there, a queue created inside is, and the limit in /proc/sys/fs/mqueue can be changed for this namespace alone.

bash
$ unshare --user --map-root-user --ipc --mount sh -c "mount -t mqueue mqueue /dev/mqueue && ls -l /dev/mqueue; touch /dev/mqueue/inside-queue; ls /dev/mqueue; cat /proc/sys/fs/mqueue/queues_max; echo 5 > /proc/sys/fs/mqueue/queues_max; cat /proc/sys/fs/mqueue/queues_max"
$ total 0
$ inside-queue
$ 256
$ 5

Back on the host nothing has changed.

bash
$ ls /dev/mqueue
$ demo-queue
$ cat /proc/sys/fs/mqueue/queues_max
$ 256

2.5 What is not isolated

A file in /dev/shm, which is what POSIX shared memory is, stays visible in a new IPC namespace.

bash
$ echo not-isolated > /dev/shm/demo-shm
$ unshare --user --map-root-user --ipc cat /dev/shm/demo-shm
$ not-isolated

To hide it you need a mount namespace with its own /dev/shm, which is what container engines set up.

2.6 Checking and entering an IPC namespace

In terminal 1, create a shared memory segment in a new IPC namespace and leave a process running there.

bash
$ unshare --user --map-root-user --ipc sh -c 'ipcmk -M 4096 >/dev/null; exec sleep 622'

In terminal 2, lsns -t ipc lists the IPC namespaces. On a desktop there are many: browsers put their sandboxed processes into IPC namespaces of their own.

bash
$ lsns -t ipc -p 1229931
$         NS TYPE NPROCS     PID USER COMMAND
$ 4026534273 ipc       1 1229931 user sleep 622
$ lsns -t ipc
$         NS TYPE NPROCS     PID USER COMMAND
$ 4026531839 ipc      10    4085 user catatonit -P
$ 4026532889 ipc       1   72596 user /usr/lib64/firefox/firefox -contentproc ...
$ ...
$ 4026534273 ipc       1 1229931 user sleep 622

nsenter with -i enters the IPC namespace of the process (and -U its user namespace). The segment seen there is not the one of the default namespace.

bash
$ nsenter -t 1229931 -U -i --preserve-credentials ipcs -m
$ 
$ ------ Shared Memory Segments --------
$ key        shmid      owner      perms      bytes      nattch     status
$ 0x9cc2ba80 0          root       644        4096       0
$ 
$ ipcs -m
$ 
$ ------ Shared Memory Segments --------
$ key        shmid      owner      perms      bytes      nattch     status
$ 0x4475c7b5 2          user       644        4096       0
$ 

2.7 Cleaning up

The objects made in the default namespace stay until they are removed. Remove them by id, and delete the queue and the file.

bash
$ ipcrm -q 0
$ ipcrm -m 2
$ ipcrm -s 4
$ rm /dev/mqueue/demo-queue /dev/shm/demo-shm

3 Check yourself

Answer these before you look at the answers:

Sources:

← learnz/namespaces