Patch "x86/irq: Clear move_in_progress before sending cleanup IPI" has been added to the 4.4-stable tree
Subsystems (2)
This is a note to let you know that I've just added the patch titled
x86/irq: Clear move_in_progress before sending cleanup IPI
to the 4.4-stable tree which can be found at:
http://www.kernel.org/git/?p=linux/kernel/git/stable/stable-queue.git;a=summary
The filename of the patch is:
x86-irq-clear-move_in_progress-before-sending-cleanup-ipi.patch
and it can be found in the queue-4.4 subdirectory.
If you, or anyone else, feels it should not be added to the stable tree, please let <[email protected]> know about it.
Quoted 1 line
From
c1684f5035b60e9f98566493e869496fb5de1d89Mon Sep 17 00:00:00 2001
From: Thomas Gleixner <[email protected]>
Date: Thu, 31 Dec 2015 16:30:51 +0000
Subject: x86/irq: Clear move_in_progress before sending cleanup IPI
From: Thomas Gleixner <[email protected]>
commit c1684f5035b60e9f98566493e869496fb5de1d89 upstream.
send_cleanup_vector() fiddles with the old_domain mask unprotected because it relies on the protection by the move_in_progress flag. But this is fatal, as the flag is reset after the IPI has been sent. So a cpu which receives the IPI can still see the flag set and therefor ignores the cleanup request. If no other cleanup request happens then the vector stays stale on that cpu and in case of an irq removal the vector still persists. That can lead to use after free when the next cleanup IPI happens.
Protect the code with vector_lock and clear move_in_progress before sending the IPI.
This does not plug the race which Joe reported because:
CPU0 CPU1 CPU2lock_vector()
data->move_in_progress=0sendIPI()unlock_vector()
set_affinity()
assign_irq_vector()
lock_vector() handle_IPI
move_in_progress = 1 lock_vector()
unlock_vector()
move_in_progress == 1
The full fix comes with a later patch.
--- arch/x86/kernel/apic/vector.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
arch/x86/kernel/apic/vector.c +3 -1
@@ -530,6 +530,8 @@ static void __send_cleanup_vector(struct {cpumask_var_t cleanup_mask; +raw_spin_lock (&vector_lock); + data->move_in_progress =0 ;if (unlikely (!alloc_cpumask_var (&cleanup_mask,GFP_ATOMIC ))) {unsigned int i;
@@ -541,7 +543,7 @@ static void __send_cleanup_vector(struct apic->send_IPI_mask (cleanup_mask,IRQ_MOVE_CLEANUP_VECTOR );free_cpumask_var (cleanup_mask); } - data->move_in_progress =0 ; +raw_spin_unlock (&vector_lock); }void send_cleanup_vector (struct irq_cfg *cfg)
Patches currently in stable-queue which might be from [email protected] are
queue-4.4/x86-irq-validate-that-irq-descriptor-is-still-active.patch queue-4.4/x86-irq-remove-outgoing-cpu-from-vector-cleanup-mask.patch queue-4.4/x86-irq-get-rid-of-code-duplication.patch queue-4.4/x86-entry-compat-add-missing-clac-to-entry_int80_32.patch queue-4.4/tick-nohz-set-the-correct-expiry-when-switching-to-nohz-lowres-mode.patch queue-4.4/irqchip-mxs-add-missing-set_handle_irq.patch queue-4.4/genirq-validate-action-before-dereferencing-it-in-handle_irq_event_percpu.patch queue-4.4/x86-irq-remove-offline-cpus-from-vector-cleanup.patch queue-4.4/posix-clock-fix-return-code-on-the-poll-method-s-error-path.patch queue-4.4/x86-irq-reorganize-the-return-path-in-assign_irq_vector.patch queue-4.4/cputime-prevent-32bit-overflow-in-time_to_cputime.patch queue-4.4/x86-irq-copy-vectormask-instead-of-an-and-operation.patch queue-4.4/x86-irq-call-irq_force_move_complete-with-irq-descriptor.patch queue-4.4/x86-irq-call-chip-irq_set_affinity-in-proper-context.patch queue-4.4/x86-irq-plug-vector-cleanup-race.patch queue-4.4/x86-irq-do-not-use-apic_chip_data.old_domain-as-temporary-buffer.patch queue-4.4/clockevents-tcb_clksrc-prevent-disabling-an-already-disabled-clock.patch queue-4.4/x86-irq-reorganize-the-search-in-assign_irq_vector.patch queue-4.4/x86-irq-remove-the-cpumask-allocation-from-send_cleanup_vector.patch queue-4.4/x86-irq-fix-a-race-in-x86_vector_free_irqs.patch queue-4.4/x86-irq-check-vector-allocation-early.patch queue-4.4/irqchip-omap-intc-add-support-for-spurious-irq-handling.patch queue-4.4/x86-irq-clear-move_in_progress-before-sending-cleanup-ipi.patch queue-4.4/x86-mpx-fix-off-by-one-comparison-with-nr_registers.patch queue-4.4/irqchip-atmel-aic-fix-wrong-bit-operation-for-irq-priority.patch queue-4.4/revert-workqueue-make-sure-delayed-work-run-in-local-cpu.patch