L'azienda Qualys ha identificato tre vulnerabilità nell'utilità needrestart, progettata per riavviare i processi in background dopo l'aggiornamento delle librerie utilizzate dai processi interessati. A partire da Ubuntu 21.04, l'utilità needrestart è inclusa nell'ambiente di base di Ubuntu Server, dove viene eseguita con diritti di root alla fine di ogni transazione del gestore pacchetti APT, esamina i processi in esecuzione e riavvia quelli correlati ai file che sono stati modificati dopo l'aggiornamento dei pacchetti. Le vulnerabilità identificate consentono a un utente locale non privilegiato di ottenere diritti di root in Ubuntu Server nella configurazione predefinita.
Le vulnerabilità sono presenti in needrestart dalla versione 0.8 (2014) e sono state corrette nella versione 3.8 di needrestart. I problemi sono già stati risolti anche nelle distribuzioni Debian e Ubuntu. Come soluzione alternativa per bloccare l'exploitation della vulnerabilità, è possibile disabilitare la scansione degli interpreti specificando nel file di configurazione /etc/needrestart/needrestart.conf il parametro "$nrconf{interpscan} = 0".
Le vulnerabilità sono presenti nel codice che implementa la modalità di rilevamento dell'aggiornamento degli script eseguiti con interpreti. Problemi identificati:
- CVE-2024-48990 — un utente locale può ottenere l'esecuzione di codice con diritti di root creando condizioni per l'avvio dell'interprete Python con la variabile d'ambiente PYTHONPATH impostata dall'attaccante. Oltre all'uso di Python, l'attacco può essere condotto anche (CVE-2024-48992) attraverso l'avvio dell'interprete Ruby con la variabile d'ambiente RUBYLIB.
Le vulnerabilità sono causate dal fatto che, durante il riavvio di uno script modificato, l'utilità needrestart imposta la variabile d'ambiente PYTHONPATH in base al contenuto del file /proc/pid/environ, che utilizza anche per avviare il proprio codice Python. Di conseguenza, l'attaccante può attendere attività legate all'operato del gestore pacchetti APT, simulare la modifica del proprio script e impostare per esso la variabile d'ambiente PYTHONPATH, che sarà applicata anche durante l'esecuzione del codice Python integrato in needrestart ("import sys\n print(sys.path)") eseguito con diritti di root.
Ad esempio, per sfruttare la vulnerabilità è possibile avviare un processo Python che rimane in memoria, impostando per esso la variabile d'ambiente "PYTHONPATH=/home/test", e posizionare la libreria condivisa "/home/test/importlib/__init__.so", che verrà eseguita quando il codice Python con privilegi verrà eseguito in needrestart.
- CVE-2024-48991 — un utente locale può ottenere l'esecuzione di codice con diritti di root attraverso l'inizio di una condizione di gara (race condition), che porta needrestart ad avviare un interprete Python simulato fornito dall'attaccante, al posto dell'interprete Python di sistema. La sostanza della vulnerabilità è simile al problema precedentemente menzionato, con la sola differenza che needrestart determina il nome del processo Python (ad esempio, /usr/bin/python3) leggendo "proc/pid/exe".
Per sfruttare la vulnerabilità, è possibile creare un processo /home/test/race, che attenderà l'arrivo del momento in cui needrestart inizia a leggere il contenuto di /proc/pid/exe tramite il meccanismo inotify, e lancerà immediatamente tramite la funzione execve l'interprete Python di sistema. Poiché needrestart non verifica se questo sia realmente Python, considererà che /home/test/race sia l'interprete Python e lo avvierà per il proprio codice.
- CVE-2024-11003 — un utente locale può ottenere l'esecuzione di comandi shell arbitrari con diritti di root creando condizioni affinché needrestart elabori nomi di file nel formato "comando|", la cui trasmissione alla funzione Perl open() causerà l'esecuzione del comando. Di fatto, la vulnerabilità si manifesta nel modulo Perl ScanDeps (CVE-2024-10224), ma è causata dalla trasmissione a questo modulo di parametri esterni senza adeguata verifica.
L'attacco può essere effettuato eseguendo uno script Perl con il simbolo "|" nel nome, ad esempio, "/home/test/perl|". Durante l'esecuzione della funzione scan_deps() in needrestart, questo file verrà aperto tramite la funzione open(), che tratterà il simbolo "|" come un flag per avviare il programma "/home/test/perl" e utilizzare il flusso di uscita fornito da questo programma.
Fonte: opennet.ru
