Skip to content

Commit

Permalink
Merge branch 'irq-core-for-linus' of git://git.kernel.org/pub/scm/lin…
Browse files Browse the repository at this point in the history
…ux/kernel/git/tip/tip

Pull IRQ changes from Ingo Molnar:
 "The only change in this cycle is a CPU hotplug related spurious
  warning fix"

* 'irq-core-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
  x86/irq: Fix kbuild warning in smp_irq_move_cleanup_interrupt()
  x86/irq: Fix do_IRQ() interrupt warning for cpu hotplug retriggered irqs
  • Loading branch information
torvalds committed Jan 20, 2014
2 parents ad3ab30 + c7a730f commit 2cc3f16
Show file tree
Hide file tree
Showing 4 changed files with 28 additions and 18 deletions.
3 changes: 3 additions & 0 deletions arch/x86/include/asm/hw_irq.h
Original file line number Diff line number Diff line change
Expand Up @@ -191,6 +191,9 @@ extern void (*__initconst interrupt[NR_VECTORS-FIRST_EXTERNAL_VECTOR])(void);
#define trace_interrupt interrupt
#endif

#define VECTOR_UNDEFINED -1
#define VECTOR_RETRIGGERED -2

typedef int vector_irq_t[NR_VECTORS];
DECLARE_PER_CPU(vector_irq_t, vector_irq);
extern void setup_vector_irq(int cpu);
Expand Down
20 changes: 10 additions & 10 deletions arch/x86/kernel/apic/io_apic.c
Original file line number Diff line number Diff line change
Expand Up @@ -1142,9 +1142,10 @@ __assign_irq_vector(int irq, struct irq_cfg *cfg, const struct cpumask *mask)
if (test_bit(vector, used_vectors))
goto next;

for_each_cpu_and(new_cpu, tmp_mask, cpu_online_mask)
if (per_cpu(vector_irq, new_cpu)[vector] != -1)
for_each_cpu_and(new_cpu, tmp_mask, cpu_online_mask) {
if (per_cpu(vector_irq, new_cpu)[vector] > VECTOR_UNDEFINED)
goto next;
}
/* Found one! */
current_vector = vector;
current_offset = offset;
Expand Down Expand Up @@ -1183,19 +1184,18 @@ static void __clear_irq_vector(int irq, struct irq_cfg *cfg)

vector = cfg->vector;
for_each_cpu_and(cpu, cfg->domain, cpu_online_mask)
per_cpu(vector_irq, cpu)[vector] = -1;
per_cpu(vector_irq, cpu)[vector] = VECTOR_UNDEFINED;

cfg->vector = 0;
cpumask_clear(cfg->domain);

if (likely(!cfg->move_in_progress))
return;
for_each_cpu_and(cpu, cfg->old_domain, cpu_online_mask) {
for (vector = FIRST_EXTERNAL_VECTOR; vector < NR_VECTORS;
vector++) {
for (vector = FIRST_EXTERNAL_VECTOR; vector < NR_VECTORS; vector++) {
if (per_cpu(vector_irq, cpu)[vector] != irq)
continue;
per_cpu(vector_irq, cpu)[vector] = -1;
per_cpu(vector_irq, cpu)[vector] = VECTOR_UNDEFINED;
break;
}
}
Expand Down Expand Up @@ -1228,12 +1228,12 @@ void __setup_vector_irq(int cpu)
/* Mark the free vectors */
for (vector = 0; vector < NR_VECTORS; ++vector) {
irq = per_cpu(vector_irq, cpu)[vector];
if (irq < 0)
if (irq <= VECTOR_UNDEFINED)
continue;

cfg = irq_cfg(irq);
if (!cpumask_test_cpu(cpu, cfg->domain))
per_cpu(vector_irq, cpu)[vector] = -1;
per_cpu(vector_irq, cpu)[vector] = VECTOR_UNDEFINED;
}
raw_spin_unlock(&vector_lock);
}
Expand Down Expand Up @@ -2202,13 +2202,13 @@ asmlinkage void smp_irq_move_cleanup_interrupt(void)

me = smp_processor_id();
for (vector = FIRST_EXTERNAL_VECTOR; vector < NR_VECTORS; vector++) {
unsigned int irq;
int irq;
unsigned int irr;
struct irq_desc *desc;
struct irq_cfg *cfg;
irq = __this_cpu_read(vector_irq[vector]);

if (irq == -1)
if (irq <= VECTOR_UNDEFINED)
continue;

desc = irq_to_desc(irq);
Expand Down
19 changes: 13 additions & 6 deletions arch/x86/kernel/irq.c
Original file line number Diff line number Diff line change
Expand Up @@ -193,9 +193,13 @@ __visible unsigned int __irq_entry do_IRQ(struct pt_regs *regs)
if (!handle_irq(irq, regs)) {
ack_APIC_irq();

if (printk_ratelimit())
pr_emerg("%s: %d.%d No irq handler for vector (irq %d)\n",
__func__, smp_processor_id(), vector, irq);
if (irq != VECTOR_RETRIGGERED) {
pr_emerg_ratelimited("%s: %d.%d No irq handler for vector (irq %d)\n",
__func__, smp_processor_id(),
vector, irq);
} else {
__this_cpu_write(vector_irq[vector], VECTOR_UNDEFINED);
}
}

irq_exit();
Expand Down Expand Up @@ -344,7 +348,7 @@ void fixup_irqs(void)
for (vector = FIRST_EXTERNAL_VECTOR; vector < NR_VECTORS; vector++) {
unsigned int irr;

if (__this_cpu_read(vector_irq[vector]) < 0)
if (__this_cpu_read(vector_irq[vector]) <= VECTOR_UNDEFINED)
continue;

irr = apic_read(APIC_IRR + (vector / 32 * 0x10));
Expand All @@ -355,11 +359,14 @@ void fixup_irqs(void)
data = irq_desc_get_irq_data(desc);
chip = irq_data_get_irq_chip(data);
raw_spin_lock(&desc->lock);
if (chip->irq_retrigger)
if (chip->irq_retrigger) {
chip->irq_retrigger(data);
__this_cpu_write(vector_irq[vector], VECTOR_RETRIGGERED);
}
raw_spin_unlock(&desc->lock);
}
__this_cpu_write(vector_irq[vector], -1);
if (__this_cpu_read(vector_irq[vector]) != VECTOR_RETRIGGERED)
__this_cpu_write(vector_irq[vector], VECTOR_UNDEFINED);
}
}
#endif
4 changes: 2 additions & 2 deletions arch/x86/kernel/irqinit.c
Original file line number Diff line number Diff line change
Expand Up @@ -52,15 +52,15 @@ static struct irqaction irq2 = {
};

DEFINE_PER_CPU(vector_irq_t, vector_irq) = {
[0 ... NR_VECTORS - 1] = -1,
[0 ... NR_VECTORS - 1] = VECTOR_UNDEFINED,
};

int vector_used_by_percpu_irq(unsigned int vector)
{
int cpu;

for_each_online_cpu(cpu) {
if (per_cpu(vector_irq, cpu)[vector] != -1)
if (per_cpu(vector_irq, cpu)[vector] > VECTOR_UNDEFINED)
return 1;
}

Expand Down

0 comments on commit 2cc3f16

Please sign in to comment.