Mount Namespace

Apprenez le piratage AWS de zéro à héros avec htARTE (HackTricks AWS Red Team Expert)!

Autres façons de soutenir HackTricks :

Informations de base

Un espace de noms de montage est une fonctionnalité du noyau Linux qui isole les points de montage du système de fichiers vus par un groupe de processus. Chaque espace de noms de montage a son propre ensemble de points de montage du système de fichiers, et les modifications apportées aux points de montage dans un espace de noms ne affectent pas les autres espaces de noms. Cela signifie que les processus s'exécutant dans différents espaces de noms de montage peuvent avoir des vues différentes de la hiérarchie du système de fichiers.

Les espaces de noms de montage sont particulièrement utiles dans la conteneurisation, où chaque conteneur doit avoir son propre système de fichiers et sa propre configuration, isolés des autres conteneurs et du système hôte.

Comment cela fonctionne :

  1. Lorsqu'un nouvel espace de noms de montage est créé, il est initialisé avec une copie des points de montage de son espace de noms parent. Cela signifie qu'à sa création, le nouvel espace de noms partage la même vue du système de fichiers que son parent. Cependant, toute modification ultérieure des points de montage à l'intérieur de l'espace de noms n'affectera pas le parent ou les autres espaces de noms.

  2. Lorsqu'un processus modifie un point de montage à l'intérieur de son espace de noms, tel que le montage ou le démontage d'un système de fichiers, le changement est local à cet espace de noms et n'affecte pas les autres espaces de noms. Cela permet à chaque espace de noms d'avoir sa propre hiérarchie de système de fichiers indépendante.

  3. Les processus peuvent se déplacer entre les espaces de noms en utilisant l'appel système setns(), ou créer de nouveaux espaces de noms en utilisant les appels système unshare() ou clone() avec le drapeau CLONE_NEWNS. Lorsqu'un processus se déplace vers un nouvel espace de noms ou en crée un, il commencera à utiliser les points de montage associés à cet espace de noms.

  4. Les descripteurs de fichiers et les inodes sont partagés entre les espaces de noms, ce qui signifie que si un processus dans un espace de noms a un descripteur de fichier ouvert pointant vers un fichier, il peut transmettre ce descripteur de fichier à un processus dans un autre espace de noms, et les deux processus accéderont au même fichier. Cependant, le chemin du fichier peut ne pas être le même dans les deux espaces de noms en raison de différences dans les points de montage.

Laboratoire :

Créer différents espaces de noms

CLI

sudo unshare -m [--mount-proc] /bin/bash

En montant une nouvelle instance du système de fichiers /proc en utilisant le paramètre --mount-proc, vous vous assurez que le nouveau namespace de montage a une vue précise et isolée des informations de processus spécifiques à ce namespace.

Erreur : bash: fork: Impossible d'allouer de la mémoire

Lorsque unshare est exécuté sans l'option -f, une erreur est rencontrée en raison de la manière dont Linux gère les nouveaux espaces de noms PID (Process ID). Les détails clés et la solution sont décrits ci-dessous :

  1. Explication du Problème :

  • Le noyau Linux permet à un processus de créer de nouveaux espaces de noms en utilisant l'appel système unshare. Cependant, le processus qui initie la création d'un nouveau namespace PID (appelé processus "unshare") n'entre pas dans le nouveau namespace ; seuls ses processus enfants le font.

  • L'exécution de %unshare -p /bin/bash% démarre /bin/bash dans le même processus que unshare. Par conséquent, /bin/bash et ses processus enfants se trouvent dans le namespace PID d'origine.

  • Le premier processus enfant de /bin/bash dans le nouveau namespace devient le PID 1. Lorsque ce processus se termine, il déclenche le nettoyage du namespace s'il n'y a pas d'autres processus, car le PID 1 a le rôle spécial d'adopter les processus orphelins. Le noyau Linux désactive alors l'allocation de PID dans ce namespace.

  1. Conséquence :

  • La sortie du PID 1 dans un nouveau namespace entraîne le nettoyage du drapeau PIDNS_HASH_ADDING. Cela entraîne l'échec de la fonction alloc_pid pour allouer un nouveau PID lors de la création d'un nouveau processus, produisant l'erreur "Impossible d'allouer de la mémoire".

  1. Solution :

  • Le problème peut être résolu en utilisant l'option -f avec unshare. Cette option fait en sorte que unshare fork un nouveau processus après la création du nouveau namespace PID.

  • L'exécution de %unshare -fp /bin/bash% garantit que la commande unshare elle-même devient le PID 1 dans le nouveau namespace. /bin/bash et ses processus enfants sont alors en sécurité dans ce nouveau namespace, empêchant la sortie prématurée du PID 1 et permettant une allocation normale des PID.

En veillant à ce que unshare s'exécute avec le drapeau -f, le nouveau namespace PID est correctement maintenu, permettant à /bin/bash et à ses sous-processus de fonctionner sans rencontrer l'erreur d'allocation de mémoire.

Docker

docker run -ti --name ubuntu1 -v /usr:/ubuntu1 ubuntu bash

Vérifier dans quel espace de nom se trouve votre processus

ls -l /proc/self/ns/mnt
lrwxrwxrwx 1 root root 0 Apr  4 20:30 /proc/self/ns/mnt -> 'mnt:[4026531841]'

Trouver tous les espaces de noms de montage

sudo find /proc -maxdepth 3 -type l -name mnt -exec readlink {} \; 2>/dev/null | sort -u
# Find the processes with an specific namespace
sudo find /proc -maxdepth 3 -type l -name mnt -exec ls -l  {} \; 2>/dev/null | grep <ns-number>

Entrer dans un espace de noms de montage

nsenter -m TARGET_PID --pid /bin/bash

De plus, vous ne pouvez entrer dans un autre espace de processus que si vous êtes root. Et vous ne pouvez pas entrer dans un autre espace sans un descripteur pointant vers celui-ci (comme /proc/self/ns/mnt).

Étant donné que les nouveaux montages ne sont accessibles que dans l'espace de noms, il est possible qu'un espace de noms contienne des informations sensibles qui ne peuvent être accessibles que depuis cet espace.

Monter quelque chose

# Generate new mount ns
unshare -m /bin/bash
mkdir /tmp/mount_ns_example
mount -t tmpfs tmpfs /tmp/mount_ns_example
mount | grep tmpfs # "tmpfs on /tmp/mount_ns_example"
echo test > /tmp/mount_ns_example/test
ls /tmp/mount_ns_example/test # Exists

# From the host
mount | grep tmpfs # Cannot see "tmpfs on /tmp/mount_ns_example"
ls /tmp/mount_ns_example/test # Doesn't exist

Références

Apprenez le piratage AWS de zéro à héros avec htARTE (Expert en équipe rouge AWS de HackTricks)!

Autres façons de soutenir HackTricks:

Last updated