aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86/kernel/apic
diff options
context:
space:
mode:
authorGary Hade <garyhade@us.ibm.com>2009-04-08 17:07:25 -0400
committerIngo Molnar <mingo@elte.hu>2009-04-08 23:13:57 -0400
commite85abf8f432bb2a13733ab7609fbb8e1500af51d (patch)
tree428d78759a0a6b4782a18cf07182a1cb3a1d001b /arch/x86/kernel/apic
parent02421f98ec55c3ff118f358740ff640f096c7ad6 (diff)
x86: consolidate SMP code in io_apic.c
Impact: Cleanup Reorganizes the code in arch/x86/kernel/io_apic.c by combining two '#ifdef CONFIG_SMP' regions. In addition to making the code easier to understand the first '#ifdef CONFIG_SMP' region is moved to a location later in the file which will reduce the need for function forward declarations when the code subsequently revised. The only changes other than relocating code to a different position in the file were the removal of the assign_irq_vector() forward declaration which was no longer needed and some line length reduction formatting changes. Signed-off-by: Gary Hade <garyhade@us.ibm.com> Cc: lcm@us.ibm.com LKML-Reference: <20090408210725.GC11159@us.ibm.com> Signed-off-by: Ingo Molnar <mingo@elte.hu>
Diffstat (limited to 'arch/x86/kernel/apic')
-rw-r--r--arch/x86/kernel/apic/io_apic.c223
1 files changed, 109 insertions, 114 deletions
diff --git a/arch/x86/kernel/apic/io_apic.c b/arch/x86/kernel/apic/io_apic.c
index 767fe7e46d68..7c9d045ac834 100644
--- a/arch/x86/kernel/apic/io_apic.c
+++ b/arch/x86/kernel/apic/io_apic.c
@@ -518,120 +518,6 @@ static void ioapic_mask_entry(int apic, int pin)
518 spin_unlock_irqrestore(&ioapic_lock, flags); 518 spin_unlock_irqrestore(&ioapic_lock, flags);
519} 519}
520 520
521#ifdef CONFIG_SMP
522static void send_cleanup_vector(struct irq_cfg *cfg)
523{
524 cpumask_var_t cleanup_mask;
525
526 if (unlikely(!alloc_cpumask_var(&cleanup_mask, GFP_ATOMIC))) {
527 unsigned int i;
528 cfg->move_cleanup_count = 0;
529 for_each_cpu_and(i, cfg->old_domain, cpu_online_mask)
530 cfg->move_cleanup_count++;
531 for_each_cpu_and(i, cfg->old_domain, cpu_online_mask)
532 apic->send_IPI_mask(cpumask_of(i), IRQ_MOVE_CLEANUP_VECTOR);
533 } else {
534 cpumask_and(cleanup_mask, cfg->old_domain, cpu_online_mask);
535 cfg->move_cleanup_count = cpumask_weight(cleanup_mask);
536 apic->send_IPI_mask(cleanup_mask, IRQ_MOVE_CLEANUP_VECTOR);
537 free_cpumask_var(cleanup_mask);
538 }
539 cfg->move_in_progress = 0;
540}
541
542static void __target_IO_APIC_irq(unsigned int irq, unsigned int dest, struct irq_cfg *cfg)
543{
544 int apic, pin;
545 struct irq_pin_list *entry;
546 u8 vector = cfg->vector;
547
548 entry = cfg->irq_2_pin;
549 for (;;) {
550 unsigned int reg;
551
552 if (!entry)
553 break;
554
555 apic = entry->apic;
556 pin = entry->pin;
557 /*
558 * With interrupt-remapping, destination information comes
559 * from interrupt-remapping table entry.
560 */
561 if (!irq_remapped(irq))
562 io_apic_write(apic, 0x11 + pin*2, dest);
563 reg = io_apic_read(apic, 0x10 + pin*2);
564 reg &= ~IO_APIC_REDIR_VECTOR_MASK;
565 reg |= vector;
566 io_apic_modify(apic, 0x10 + pin*2, reg);
567 if (!entry->next)
568 break;
569 entry = entry->next;
570 }
571}
572
573static int
574assign_irq_vector(int irq, struct irq_cfg *cfg, const struct cpumask *mask);
575
576/*
577 * Either sets desc->affinity to a valid value, and returns
578 * ->cpu_mask_to_apicid of that, or returns BAD_APICID and
579 * leaves desc->affinity untouched.
580 */
581static unsigned int
582set_desc_affinity(struct irq_desc *desc, const struct cpumask *mask)
583{
584 struct irq_cfg *cfg;
585 unsigned int irq;
586
587 if (!cpumask_intersects(mask, cpu_online_mask))
588 return BAD_APICID;
589
590 irq = desc->irq;
591 cfg = desc->chip_data;
592 if (assign_irq_vector(irq, cfg, mask))
593 return BAD_APICID;
594
595 /* check that before desc->addinity get updated */
596 set_extra_move_desc(desc, mask);
597
598 cpumask_copy(desc->affinity, mask);
599
600 return apic->cpu_mask_to_apicid_and(desc->affinity, cfg->domain);
601}
602
603static void
604set_ioapic_affinity_irq_desc(struct irq_desc *desc, const struct cpumask *mask)
605{
606 struct irq_cfg *cfg;
607 unsigned long flags;
608 unsigned int dest;
609 unsigned int irq;
610
611 irq = desc->irq;
612 cfg = desc->chip_data;
613
614 spin_lock_irqsave(&ioapic_lock, flags);
615 dest = set_desc_affinity(desc, mask);
616 if (dest != BAD_APICID) {
617 /* Only the high 8 bits are valid. */
618 dest = SET_APIC_LOGICAL_ID(dest);
619 __target_IO_APIC_irq(irq, dest, cfg);
620 }
621 spin_unlock_irqrestore(&ioapic_lock, flags);
622}
623
624static void
625set_ioapic_affinity_irq(unsigned int irq, const struct cpumask *mask)
626{
627 struct irq_desc *desc;
628
629 desc = irq_to_desc(irq);
630
631 set_ioapic_affinity_irq_desc(desc, mask);
632}
633#endif /* CONFIG_SMP */
634
635/* 521/*
636 * The common case is 1:1 IRQ<->pin mappings. Sometimes there are 522 * The common case is 1:1 IRQ<->pin mappings. Sometimes there are
637 * shared ISA-space IRQs, so we have to support them. We are super 523 * shared ISA-space IRQs, so we have to support them. We are super
@@ -2360,6 +2246,115 @@ static int ioapic_retrigger_irq(unsigned int irq)
2360 */ 2246 */
2361 2247
2362#ifdef CONFIG_SMP 2248#ifdef CONFIG_SMP
2249static void send_cleanup_vector(struct irq_cfg *cfg)
2250{
2251 cpumask_var_t cleanup_mask;
2252
2253 if (unlikely(!alloc_cpumask_var(&cleanup_mask, GFP_ATOMIC))) {
2254 unsigned int i;
2255 cfg->move_cleanup_count = 0;
2256 for_each_cpu_and(i, cfg->old_domain, cpu_online_mask)
2257 cfg->move_cleanup_count++;
2258 for_each_cpu_and(i, cfg->old_domain, cpu_online_mask)
2259 apic->send_IPI_mask(cpumask_of(i), IRQ_MOVE_CLEANUP_VECTOR);
2260 } else {
2261 cpumask_and(cleanup_mask, cfg->old_domain, cpu_online_mask);
2262 cfg->move_cleanup_count = cpumask_weight(cleanup_mask);
2263 apic->send_IPI_mask(cleanup_mask, IRQ_MOVE_CLEANUP_VECTOR);
2264 free_cpumask_var(cleanup_mask);
2265 }
2266 cfg->move_in_progress = 0;
2267}
2268
2269static void
2270__target_IO_APIC_irq(unsigned int irq, unsigned int dest, struct irq_cfg *cfg)
2271{
2272 int apic, pin;
2273 struct irq_pin_list *entry;
2274 u8 vector = cfg->vector;
2275
2276 entry = cfg->irq_2_pin;
2277 for (;;) {
2278 unsigned int reg;
2279
2280 if (!entry)
2281 break;
2282
2283 apic = entry->apic;
2284 pin = entry->pin;
2285 /*
2286 * With interrupt-remapping, destination information comes
2287 * from interrupt-remapping table entry.
2288 */
2289 if (!irq_remapped(irq))
2290 io_apic_write(apic, 0x11 + pin*2, dest);
2291 reg = io_apic_read(apic, 0x10 + pin*2);
2292 reg &= ~IO_APIC_REDIR_VECTOR_MASK;
2293 reg |= vector;
2294 io_apic_modify(apic, 0x10 + pin*2, reg);
2295 if (!entry->next)
2296 break;
2297 entry = entry->next;
2298 }
2299}
2300
2301/*
2302 * Either sets desc->affinity to a valid value, and returns
2303 * ->cpu_mask_to_apicid of that, or returns BAD_APICID and
2304 * leaves desc->affinity untouched.
2305 */
2306static unsigned int
2307set_desc_affinity(struct irq_desc *desc, const struct cpumask *mask)
2308{
2309 struct irq_cfg *cfg;
2310 unsigned int irq;
2311
2312 if (!cpumask_intersects(mask, cpu_online_mask))
2313 return BAD_APICID;
2314
2315 irq = desc->irq;
2316 cfg = desc->chip_data;
2317 if (assign_irq_vector(irq, cfg, mask))
2318 return BAD_APICID;
2319
2320 /* check that before desc->addinity get updated */
2321 set_extra_move_desc(desc, mask);
2322
2323 cpumask_copy(desc->affinity, mask);
2324
2325 return apic->cpu_mask_to_apicid_and(desc->affinity, cfg->domain);
2326}
2327
2328static void
2329set_ioapic_affinity_irq_desc(struct irq_desc *desc, const struct cpumask *mask)
2330{
2331 struct irq_cfg *cfg;
2332 unsigned long flags;
2333 unsigned int dest;
2334 unsigned int irq;
2335
2336 irq = desc->irq;
2337 cfg = desc->chip_data;
2338
2339 spin_lock_irqsave(&ioapic_lock, flags);
2340 dest = set_desc_affinity(desc, mask);
2341 if (dest != BAD_APICID) {
2342 /* Only the high 8 bits are valid. */
2343 dest = SET_APIC_LOGICAL_ID(dest);
2344 __target_IO_APIC_irq(irq, dest, cfg);
2345 }
2346 spin_unlock_irqrestore(&ioapic_lock, flags);
2347}
2348
2349static void
2350set_ioapic_affinity_irq(unsigned int irq, const struct cpumask *mask)
2351{
2352 struct irq_desc *desc;
2353
2354 desc = irq_to_desc(irq);
2355
2356 set_ioapic_affinity_irq_desc(desc, mask);
2357}
2363 2358
2364#ifdef CONFIG_INTR_REMAP 2359#ifdef CONFIG_INTR_REMAP
2365 2360