Abusing Roles/ClusterRoles in Kubernetes
Last updated
Last updated
Learn & practice AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE) Learn & practice GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Ovde možete pronaći neke potencijalno opasne konfiguracije Roles i ClusterRoles.
Zapamtite da možete dobiti sve podržane resurse sa kubectl api-resources
Odnosi se na veštinu dobijanja pristupa različitom principalu unutar klastera sa različitim privilegijama (unutar kubernetes klastera ili na eksternim cloud-ovima) od onih koje već imate, u Kubernetes-u postoje osnovno 4 glavne tehnike za povećanje privilegija:
Možete pretvarati se u druge korisnike/grupe/SAs sa boljim privilegijama unutar kubernetes klastera ili na eksternim cloud-ovima
Možete kreirati/patch/exec pods gde možete pronaći ili priključiti SAs sa boljim privilegijama unutar kubernetes klastera ili na eksternim cloud-ovima
Možete čitati tajne jer su SAs tokeni pohranjeni kao tajne
Možete pobeći na čvor iz kontejnera, gde možete ukrasti sve tajne kontejnera koji se izvršavaju na čvoru, kredencijale čvora i dozvole čvora unutar clouda u kojem se izvršava (ako ih ima)
Peta tehnika koja zaslužuje pominjanje je sposobnost da pokrenete port-forward u podu, jer možda možete pristupiti zanimljivim resursima unutar tog poda.
wildcard (*) daje dozvolu za bilo koji resurs sa bilo kojim glagolom. Koriste ga administratori. Unutar ClusterRole to znači da bi napadač mogao zloupotrebiti bilo koji namespace u klasteru.
U RBAC-u, određene dozvole predstavljaju značajne rizike:
create
: Daje mogućnost kreiranja bilo kog klasterskog resursa, što može dovesti do eskalacije privilegija.
list
: Omogućava listanje svih resursa, potencijalno otkrivajući osetljive podatke.
get
: Dozvoljava pristup tajnama iz servisnih naloga, što predstavlja bezbednosnu pretnju.
Napadač sa dozvolama za kreiranje poda može da prikači privilegovani servisni nalog u pod i ukrade token da bi se pretvarao da je taj servisni nalog. Efektivno povećavajući privilegije.
Primer poda koji će ukrasti token servisnog naloga bootstrap-signer
i poslati ga napadaču:
Sledeće ukazuje na sve privilegije koje kontejner može imati:
Privilegovan pristup (onemogućavanje zaštita i postavljanje sposobnosti)
Onemogućavanje namespaces hostIPC i hostPid koji mogu pomoći u eskalaciji privilegija
Onemogućavanje hostNetwork namespace-a, dajući pristup za krađu privilegija čvora u oblaku i bolji pristup mrežama
Montiranje hostova / unutar kontejnera
Kreirajte pod sa:
Jedan red iz ovog tvita i sa nekim dodacima:
Sada kada možete da pobegnete na čvor, proverite tehnike post-eksploatacije u:
Verovatno želite da budete diskretniji, na sledećim stranicama možete videti šta biste mogli da pristupite ako kreirate pod omogućavajući samo neka od pomenutih privilegija u prethodnom šablonu:
Privileged + hostPID
Privileged only
hostPath
hostPID
hostNetwork
hostIPC
Možete pronaći primer kako da kreirate/iskoristite prethodne privilegovane konfiguracije podova u https://github.com/BishopFox/badPods
Ako možete da kreirate pod (i opcionalno service account) možda ćete moći da dobijete privilegije u cloud okruženju dodeljujući cloud roles podu ili service account i zatim mu pristupite. Štaviše, ako možete da kreirate pod sa host network namespace možete ukrasti IAM ulogu node instance.
Za više informacija proverite:
Pod Escape PrivilegesMoguće je iskoristiti ove dozvole da kreirate novi pod i uspostavite privilegije kao u prethodnom primeru.
Sledeći yaml kreira daemonset i exfiltrira token SA unutar poda:
pods/exec
je resurs u kubernetes-u koji se koristi za izvršavanje komandi u shell-u unutar poda. Ovo omogućava izvršavanje komandi unutar kontejnera ili dobijanje shell-a unutar.
Stoga, moguće je ući u pod i ukrasti token SA, ili ući u privilegovani pod, pobjeći na čvor i ukrasti sve tokene podova na čvoru i (zlo)upotrebiti čvor:
Ova dozvola omogućava prosleđivanje jednog lokalnog porta na jedan port u specificiranom podu. Ovo je namenjeno da se olakša debagovanje aplikacija koje se izvršavaju unutar poda, ali napadač bi to mogao zloupotrebiti da dobije pristup zanimljivim (kao što su DB-ovi) ili ranjivim aplikacijama (web?) unutar poda:
Kao što je naznačeno u ovom istraživanju, ako možete pristupiti ili kreirati pod sa montiranim direktorijumom /var/log/
na njemu, možete pobeći iz kontejnera.
To je u suštini zato što kada Kube-API pokušava da dobije logove kontejnera (koristeći kubectl logs <pod>
), zahteva 0.log
datoteku poda koristeći /logs/
endpoint Kubelet servisa.
Kubelet servis izlaže /logs/
endpoint koji u suštini izlaže /var/log
datotečni sistem kontejnera.
Stoga, napadač sa pristupom za pisanje u /var/log/ folder kontejnera mogao bi da zloupotrebi ovo ponašanje na 2 načina:
Modifikovanjem 0.log
datoteke svog kontejnera (obično smeštene u /var/logs/pods/namespace_pod_uid/container/0.log
) da bude simbolička veza koja pokazuje na /etc/shadow
na primer. Tada ćete moći da exfiltrirate hosts shadow datoteku radeći:
Ako napadač kontroliše bilo koji entitet sa dozvolama za čitanje nodes/log
, može jednostavno da kreira symlink u /host-mounted/var/log/sym
ka /
i kada pristupi https://<gateway>:10250/logs/sym/
prikazaće korenski fajl sistem hosta (promena symlinka može omogućiti pristup fajlovima).
Laboratorija i automatizovani eksploat mogu se naći na https://blog.aquasec.com/kubernetes-security-pod-escape-log-mounts
Ako imate sreće i visoko privilegovana sposobnost CAP_SYS_ADMIN
je dostupna, možete jednostavno ponovo montirati folder kao rw:
Kao što je navedeno u ovoj studiji, moguće je zaobići zaštitu:
Što je trebalo da spreči eskape poput prethodnih, tako što će umesto korišćenja hostPath montaže, koristiti PersistentVolume i PersistentVolumeClaim za montiranje foldera domaćina u kontejner sa pristupom za pisanje:
Sa privilegijom imitacije korisnika, napadač može imitirati privilegovan nalog.
Jednostavno koristite parametar --as=<username>
u kubectl
komandi da biste imitirali korisnika, ili --as-group=<group>
da biste imitirali grupu:
Ili koristite REST API:
Dozvola da prikazuje tajne može omogućiti napadaču da zapravo pročita tajne pristupajući REST API kraju:
Dok napadač u posedu tokena sa pravima za čitanje zahteva tačno ime tajne da bi je koristio, za razliku od šireg privilegija listing secrets, i dalje postoje ranjivosti. Podrazumevani servisni nalozi u sistemu mogu se enumerisati, svaki povezan sa tajnom. Ove tajne imaju strukturu imena: statički prefiks praćen nasumičnim alfanumeričkim tokenom od pet karaktera (izuzimajući određene karaktere) prema izvornom kodu.
Token se generiše iz ograničenog skupa od 27 karaktera (bcdfghjklmnpqrstvwxz2456789
), umesto iz punog alfanumeričkog opsega. Ova ograničenja smanjuju ukupan broj mogućih kombinacija na 14,348,907 (27^5). Kao rezultat, napadač bi mogao izvesti brute-force napad da bi dedukovao token u roku od nekoliko sati, što bi potencijalno moglo dovesti do eskalacije privilegija pristupom osetljivim servisnim nalozima.
Ako imate glagole create
u resursu certificatesigningrequests
(ili barem u certificatesigningrequests/nodeClient
). Možete napraviti novi CeSR za novi čvor.
Prema dokumentaciji, moguće je automatski odobriti ove zahteve, tako da u tom slučaju ne trebate dodatne dozvole. Ako ne, morali biste biti u mogućnosti da odobrite zahtev, što znači ažuriranje u certificatesigningrequests/approval
i approve
u signers
sa resourceName <signerNameDomain>/<signerNamePath>
ili <signerNameDomain>/*
Primer uloge sa svim potrebnim dozvolama je:
Dakle, sa odobrenim novim CSR-om čvora, možete iskoristiti posebne dozvole čvorova da ukradete tajne i povećate privilegije.
U ovom postu i ovom GKE K8s TLS Bootstrap konfiguracija je podešena sa automatskim potpisivanjem i koristi se za generisanje kredencijala novog K8s čvora, a zatim se ti kredencijali koriste za povećanje privilegija ukradanjem tajni. Ako imate pomenute privilegije, mogli biste uraditi istu stvar. Imajte na umu da prvi primer zaobilazi grešku koja sprečava novi čvor da pristupi tajnama unutar kontejnera jer čvor može pristupiti samo tajnama kontejnera koji su montirani na njemu.
Način da se to zaobiđe je jednostavno napraviti kredencijale čvora za ime čvora gde je kontejner sa zanimljivim tajnama montiran (ali samo proverite kako to uraditi u prvom postu):
Principali koji mogu da modifikuju configmaps
u kube-system imenskom prostoru na EKS (moraju biti u AWS) klasterima mogu dobiti privilegije klaster admina prepisivanjem aws-auth configmap-a.
Potrebni glagoli su update
i patch
, ili create
ako configmap nije kreiran:
Možete koristiti aws-auth
za perzistenciju dajući pristup korisnicima iz drugih naloga.
Međutim, aws --profile other_account eks update-kubeconfig --name <cluster-name>
ne funkcioniše iz drugog naloga. Ali zapravo aws --profile other_account eks get-token --cluster-name arn:aws:eks:us-east-1:123456789098:cluster/Testing
funkcioniše ako stavite ARN klastera umesto samo imena.
Da bi kubectl
radio, samo se pobrinite da konfigurišete kubeconfig žrtve i u aws exec args dodajte --profile other_account_role
tako da kubectl koristi profil drugog naloga za dobijanje tokena i kontaktiranje AWS-a.
Postoje 2 načina da se dodele K8s dozvole GCP principima. U svakom slučaju, princip takođe treba dozvolu container.clusters.get
da bi mogao da prikupi kredencijale za pristup klasteru, ili ćete morati da generišete svoj vlastiti kubectl config fajl (pratite sledeći link).
Kada komunicirate sa K8s API krajnjom tačkom, GCP auth token će biti poslat. Tada će GCP, preko K8s API krajnje tačke, prvo proveriti da li princip (prema emailu) ima bilo kakav pristup unutar klastera, zatim će proveriti da li ima bilo kakav pristup putem GCP IAM. Ako je bilo koja od ovih tačna, biće mu odgovoreno. Ako nije, biće data greška koja sugeriše da se dozvole dodele putem GCP IAM.
Prvi metod je korišćenje GCP IAM, K8s dozvole imaju svoje ekvivalentne GCP IAM dozvole, i ako princip to ima, moći će da ga koristi.
GCP - Container PrivescDrugi metod je dodeljivanje K8s dozvola unutar klastera identifikovanjem korisnika prema njegovom emailu (uključujući GCP servisne naloge).
Principi koji mogu kreirati TokenRequests (serviceaccounts/token
) kada komuniciraju sa K8s API krajnjom tačkom SAs (informacije iz ovde).
Principi koji mogu update
ili patch
pods/ephemeralcontainers
mogu dobiti izvršavanje koda na drugim podovima, i potencijalno pobeći na njihov čvor dodavanjem ephemernog kontejnera sa privilegovanim securityContext.
Principi sa bilo kojim od glagola create
, update
ili patch
nad validatingwebhookconfigurations
ili mutatingwebhookconfigurations
mogli bi biti u mogućnosti da kreiraju jednu od takvih webhook konfiguracija kako bi mogli da eskaliraju privilegije.
Za mutatingwebhookconfigurations
primer proverite ovu sekciju ovog posta.
Kao što možete pročitati u sledećoj sekciji: Ugrađena prevencija eskalacije privilegija, princip ne može da ažurira niti kreira uloge ili klaster uloge bez da sam ima te nove dozvole. Osim ako ima glagol escalate
nad roles
ili clusterroles
.
Tada može ažurirati/kreati nove uloge, klaster uloge sa boljim dozvolama od onih koje ima.
Principi sa pristupom do nodes/proxy
podresursa mogu izvršavati kod na podovima putem Kubelet API (prema ovome). Više informacija o Kubelet autentifikaciji na ovoj stranici:
Imate primer kako dobiti RCE razgovarajući autorizovano sa Kubelet API ovde.
Principi koji mogu brisati podove (delete
glagol nad pods
resursom), ili izbaciti podove (create
glagol nad pods/eviction
resursom), ili promeniti status poda (pristup pods/status
) i mogu učiniti druge čvorove neschedule-ovanim (pristup nodes/status
) ili brisati čvorove (delete
glagol nad nodes
resursom) i imaju kontrolu nad podom, mogli bi ukrasti podove sa drugih čvorova tako da se izvršavaju na kompromitovanom čvoru i napadač može ukrasti tokene iz tih podova.
Principali koji mogu modifikovati services/status
mogu postaviti polje status.loadBalancer.ingress.ip
da iskoriste neispravljeni CVE-2020-8554 i pokrenu MiTM napade protiv klastera. Većina mera za ublažavanje CVE-2020-8554 samo sprečava ExternalIP usluge (prema ovome).
Principali sa update
ili patch
dozvolama nad nodes/status
ili pods/status
, mogli bi modifikovati oznake kako bi uticali na ograničenja raspoređivanja.
Kubernetes ima ugrađeni mehanizam za sprečavanje eskalacije privilegija.
Ovaj sistem osigurava da korisnici ne mogu povećati svoje privilegije modifikovanjem uloga ili veza uloga. Sprovođenje ovog pravila se dešava na API nivou, pružajući zaštitu čak i kada je RBAC autorizer neaktivan.
Pravilo stipulira da korisnik može kreirati ili ažurirati ulogu samo ako poseduje sve dozvole koje uloga obuhvata. Štaviše, opseg postojećih dozvola korisnika mora se poklapati sa onim uloge koju pokušava da kreira ili modifikuje: ili na nivou klastera za ClusterRoles ili ograničeno na istu namespace (ili na nivou klastera) za Roles.
Postoji izuzetak od prethodnog pravila. Ako neki principal ima glagol escalate
nad roles
ili clusterroles
, može povećati privilegije uloga i clusterroles čak i bez da ih sam poseduje.
Očigledno je da je ova tehnika ranije radila, ali prema mojim testovima više ne funkcioniše iz istog razloga objašnjenog u prethodnom odeljku. Ne možete kreirati/modifikovati rolebinding da biste sebi ili drugom SA dali neke privilegije ako ih već nemate.
Privilegija za kreiranje Rolebindings omogućava korisniku da veže uloge za servisni nalog. Ova privilegija može potencijalno dovesti do eskalacije privilegija jer omogućava korisniku da veže admin privilegije za kompromitovani servisni nalog.
Po defaultu, ne postoji nikakva enkripcija u komunikaciji između podova. Uzajamna autentifikacija, dvosmerna, pod do poda.
Kreirajte svoj .yaml
Izmenite svoj .yaml i dodajte nekomentarisane linije:
Pogledajte logove proksija:
Više informacija na: https://kubernetes.io/docs/tasks/configure-pod-container/security-context/
Admission controller presreće zahteve ka Kubernetes API serveru pre nego što dođe do trajanja objekta, ali nakon što je zahtev autentifikovan i autorizovan.
Ako napadač nekako uspe da ubaci Mutationg Admission Controller, moći će da modifikuje već autentifikovane zahteve. Biće u mogućnosti da potencijalno izvrši privesc, i obično da se zadrži u klasteru.
Primer sa https://blog.rewanthtammana.com/creating-malicious-admission-controllers:
Proverite status da vidite da li je spremno:
Zatim implementirajte novi pod:
Kada možete videti grešku ErrImagePull
, proverite ime slike sa bilo kojim od upita:
Kao što možete videti na gornjoj slici, pokušali smo da pokrenemo sliku nginx
, ali je konačno izvršena slika rewanthtammana/malicious-image
. Šta se upravo desilo!!?
Skript ./deploy.sh
uspostavlja mutirajući webhook admission controller, koji modifikuje zahteve za Kubernetes API prema specifikacijama u svojim konfiguracionim linijama, utičući na posmatrane rezultate:
The above snippet replaces the first container image in every pod with rewanthtammana/malicious-image
.
Podovi i servisni nalozi: Podovi po defaultu montiraju token servisnog naloga. Da bi se poboljšala sigurnost, Kubernetes omogućava onemogućavanje ove automount funkcije.
Kako primeniti: Postavite automountServiceAccountToken: false
u konfiguraciji servisnih naloga ili podova počevši od Kubernetes verzije 1.6.
Selektivno uključivanje: Osigurajte da su samo neophodni korisnici uključeni u RoleBindings ili ClusterRoleBindings. Redovno vršite reviziju i uklanjajte irelevantne korisnike kako biste održali visoku sigurnost.
Uloge vs. ClusterRoles: Preferirajte korišćenje Uloga i RoleBindings za dozvole specifične za namespace umesto ClusterRoles i ClusterRoleBindings, koje se primenjuju na nivou klastera. Ovaj pristup nudi finiju kontrolu i ograničava opseg dozvola.
Learn & practice AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE) Learn & practice GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)