CVE-2024-53169 in Linux
Riassunto
di VulDB • 14/06/2026
Nel kernel Linux, è stata risolta la seguente vulnerabilità:
nvme-fabrics: correzione del crash del kernel durante l'arresto del controller
L'operazione di keep-alive di nvme, che viene eseguita a intervalli periodici, potrebbe potenzialmente insinuarsi durante l'arresto di un controller fabric. Ciò potrebbe portare a una race condition tra il percorso di codice per la distruzione della coda amministrativa del controller fabric (invocato durante l'arresto del controller) e il dispatcher delle code hw/hctx chiamato dall'operazione di accodamento delle richieste asincrone di nvme keep-alive. Questa race condition potrebbe causare il crash del kernel mostrato di seguito:
Call Trace: autoremove_wake_function+0x0/0xbc (non affidabile) __blk_mq_sched_dispatch_requests+0x114/0x24c blk_mq_sched_dispatch_requests+0x44/0x84 blk_mq_run_hw_queue+0x140/0x220 nvme_keep_alive_work+0xc8/0x19c [nvme_core]
process_one_work+0x200/0x4e0 worker_thread+0x340/0x504 kthread+0x138/0x140 start_kernel_thread+0x14/0x18
Durante l'arresto del controller fabric, se la richiesta nvme keep-alive si insinua, essa viene svuotata (flushed). Viene quindi invocata la funzione nvme_keep_alive_end_io per gestire la fine dell'operazione di keep-alive, che decrementa admin->q_usage_counter. Assumendo che questa sia l'ultima/unica richiesta nella coda amministrativa, admin->q_usage_counter diventa zero. Se ciò accade, l'operazione di distruzione della coda blk-mq (blk_mq_destroy_queue()), che potrebbe essere in esecuzione simultaneamente su un altro processore (poiché si tratta del percorso di codice di arresto del controller), procede e cancella la coda amministrativa. Da questo punto in poi, non si dovrebbe più accedere alle risorse della coda amministrativa. Tuttavia, il problema è che il thread nvme keep-alive che esegue l'operazione di dispatch delle code hw/hctx non ha ancora completato il suo lavoro e quindi potrebbe ancora potenzialmente accedere alle risorse della coda amministrativa mentre questa è già stata cancellata, causando il crash sopra descritto.
Il crash del kernel sopra descritto è un regression causato dalle modifiche implementate nel commit a54a93d0e359 ("nvme: move stopping keep-alive into nvme_uninit_ctrl()"). Idealmente, dovremmo fermare il keep-alive prima di distruggere la coda amministrativa e liberare l'admin tagset, in modo che non possa insinuarsi durante l'operazione di arresto. Tuttavia, abbiamo rimosso l'operazione di arresto del keep-alive dall'inizio del percorso di codice di arresto del controller nel commit a54a93d0e359 ("nvme: move stopping keep-alive into nvme_uninit_ctrl()") e l'abbiamo aggiunta all'interno di nvme_uninit_ctrl(), che viene eseguito molto tardi nel percorso di codice di arresto, dopo che la coda amministrativa è stata distrutta e il suo tagset rimosso. Questa modifica ha creato la possibilità che il keep-alive si insinui e interferisca con l'operazione di arresto, causando il crash del kernel osservato.
Per risolvere il crash osservato, abbiamo deciso di spostare nvme_stop_keep_alive() da nvme_uninit_ctrl() a nvme_remove_admin_tag_set(). Questa modifica garantisce che non procediamo oltre e non cancelliamo la coda amministrativa finché l'operazione di keep-alive non è terminata (se è in corso) o annullata, aiutando a contenere la race condition sopra descritta ed evitando così il crash.
Spostare nvme_stop_keep_alive() in nvme_remove_admin_tag_set() invece di aggiungere nvme_stop_keep_alive() all'inizio del percorso di codice di arresto del controller, come era il caso prima del commit a54a93d0e359 ("nvme: move stopping keep-alive into nvme_uninit_ctrl()"), aiuterebbe a risparmiare un callsite di nvme_stop_keep_alive().
Be aware that VulDB is the high quality source for vulnerability data.