Merge branch 'core-objtool-for-linus' of git://git.kernel.org/pub/scm/linux/kernel...
[linux-block.git] / kernel / irq / manage.c
index 7eee98c38f25ca20047ed75c268fae4550949bdd..fe40c658f86f851bb175ff1c374e7c808007b04f 100644 (file)
@@ -323,7 +323,11 @@ int irq_set_affinity_locked(struct irq_data *data, const struct cpumask *mask,
 
        if (desc->affinity_notify) {
                kref_get(&desc->affinity_notify->kref);
-               schedule_work(&desc->affinity_notify->work);
+               if (!schedule_work(&desc->affinity_notify->work)) {
+                       /* Work was already scheduled, drop our extra ref */
+                       kref_put(&desc->affinity_notify->kref,
+                                desc->affinity_notify->release);
+               }
        }
        irqd_set(data, IRQD_AFFINITY_SET);
 
@@ -423,7 +427,10 @@ irq_set_affinity_notifier(unsigned int irq, struct irq_affinity_notify *notify)
        raw_spin_unlock_irqrestore(&desc->lock, flags);
 
        if (old_notify) {
-               cancel_work_sync(&old_notify->work);
+               if (cancel_work_sync(&old_notify->work)) {
+                       /* Pending work had a ref, put that one too */
+                       kref_put(&old_notify->kref, old_notify->release);
+               }
                kref_put(&old_notify->kref, old_notify->release);
        }