CVE-2026-99207
Gravedad:
Pendiente de análisis
Tipo:
No Disponible / Otro tipo
Fecha de publicación:
28/10/2026
Última modificación:
28/10/2026
Descripción
*** Pendiente de traducción *** In the Linux kernel, the following vulnerability has been resolved:<br />
<br />
scsi: target: Disable interrupts while holding delayed_cmd_lock<br />
<br />
target_do_delayed_work() takes dev->delayed_cmd_lock with a plain<br />
spin_lock(). It runs from system_percpu_wq, so interrupts stay enabled<br />
while the lock is held. Every other acquisition of that lock uses<br />
spin_lock_irqsave(): target_handle_task_attr() and<br />
transport_complete_ordered_sync() in target_core_transport.c, and<br />
target_non_ordered_release() in target_core_device.c.<br />
<br />
That was safe while every caller of transport_complete_task_attr() ran<br />
in process context: target_complete_ok_work() from target_completion_wq,<br />
transport_complete_qf() from dev->qf_work_queue, and<br />
transport_generic_request_failure() from the submit and execute paths.<br />
<br />
Since commit 06933066d88a ("scsi: target: Add support for completing<br />
commands from backend context") that is no longer true. With<br />
complete_type=1 on a fabric that sets direct_compl_supp,<br />
target_complete() runs target_complete_ok_work() inline in the backend&#39;s<br />
completion context, which target_complete_cmd_with_sense() documents as<br />
"May be called from interrupt context". For iblock that is the bio<br />
end_io.<br />
<br />
target_complete_ok_work() starts with transport_complete_task_attr(),<br />
which takes delayed_cmd_lock in two ways:<br />
<br />
- Every ORDERED command is put on dev->delayed_cmd_list by<br />
target_handle_task_attr() and dispatched from there by<br />
target_do_delayed_work(), which marks it SCF_TASK_ORDERED_SYNC. Its<br />
completion therefore goes through transport_complete_ordered_sync().<br />
<br />
- A SIMPLE command that completes while an ORDERED command is pending<br />
drops the last reference to the killed dev->non_ordered, and<br />
percpu_ref_put() then runs target_non_ordered_release() in the<br />
completing context.<br />
<br />
Both take the lock and, if commands are waiting, call<br />
schedule_work(&dev->delayed_cmd_work), which queues on system_percpu_wq,<br />
i.e. on the CPU that took the completion. Further completions for the<br />
same queue are typically delivered there too, so one arriving while the<br />
work holds the lock spins on it forever.<br />
<br />
Reaching this needs complete_type=1, which is not the default<br />
(vhost-scsi, the only fabric with direct_compl_supp, defaults to<br />
TARGET_QUEUE_COMPL), a backend whose I/O completes from interrupt<br />
context, and ORDERED commands from the initiator. Linux virtio_scsi<br />
guests send only VIRTIO_SCSI_S_SIMPLE and never take the ordered path;<br />
any guest that uses the ORDERED task attribute, which vhost-scsi<br />
accepts, does.<br />
<br />
target_do_delayed_work() is a work item and always runs in process<br />
context, so spin_lock_irq() is sufficient.<br />
<br />
Found by inspection; no runtime report. A single ORDERED command goes<br />
through both acquisitions, so with CONFIG_PROVE_LOCKING the first one<br />
completed through direct completion should produce an inconsistent lock<br />
state report on delayed_cmd_lock (hardirq or softirq, depending on where<br />
the backend completes).


