]> pilppa.org Git - linux-2.6-omap-h63xx.git/blobdiff - arch/ia64/kernel/irq_ia64.c
[IA64] Fix wrong access to irq_desc[] in iosapic_register_intr().
[linux-2.6-omap-h63xx.git] / arch / ia64 / kernel / irq_ia64.c
index 158eafb5f1aac9be701642342964919afce221c8..c47c8acc96e37a270eeb8198fc8cf11b80cf9b09 100644 (file)
@@ -85,8 +85,8 @@ DEFINE_PER_CPU(int[IA64_NUM_VECTORS], vector_irq) = {
        [0 ... IA64_NUM_VECTORS - 1] = IA64_SPURIOUS_INT_VECTOR
 };
 
-static cpumask_t vector_table[IA64_MAX_DEVICE_VECTORS] = {
-       [0 ... IA64_MAX_DEVICE_VECTORS - 1] = CPU_MASK_NONE
+static cpumask_t vector_table[IA64_NUM_VECTORS] = {
+       [0 ... IA64_NUM_VECTORS - 1] = CPU_MASK_NONE
 };
 
 static int irq_status[NR_IRQS] = {
@@ -101,15 +101,6 @@ int check_irq_used(int irq)
        return -1;
 }
 
-static void reserve_irq(unsigned int irq)
-{
-       unsigned long flags;
-
-       spin_lock_irqsave(&vector_lock, flags);
-       irq_status[irq] = IRQ_RSVD;
-       spin_unlock_irqrestore(&vector_lock, flags);
-}
-
 static inline int find_unassigned_irq(void)
 {
        int irq;
@@ -123,17 +114,18 @@ static inline int find_unassigned_irq(void)
 static inline int find_unassigned_vector(cpumask_t domain)
 {
        cpumask_t mask;
-       int pos;
+       int pos, vector;
 
        cpus_and(mask, domain, cpu_online_map);
        if (cpus_empty(mask))
                return -EINVAL;
 
        for (pos = 0; pos < IA64_NUM_DEVICE_VECTORS; pos++) {
-               cpus_and(mask, domain, vector_table[pos]);
+               vector = IA64_FIRST_DEVICE_VECTOR + pos;
+               cpus_and(mask, domain, vector_table[vector]);
                if (!cpus_empty(mask))
                        continue;
-               return IA64_FIRST_DEVICE_VECTOR + pos;
+               return vector;
        }
        return -ENOSPC;
 }
@@ -141,9 +133,12 @@ static inline int find_unassigned_vector(cpumask_t domain)
 static int __bind_irq_vector(int irq, int vector, cpumask_t domain)
 {
        cpumask_t mask;
-       int cpu, pos;
+       int cpu;
        struct irq_cfg *cfg = &irq_cfg[irq];
 
+       BUG_ON((unsigned)irq >= NR_IRQS);
+       BUG_ON((unsigned)vector >= IA64_NUM_VECTORS);
+
        cpus_and(mask, domain, cpu_online_map);
        if (cpus_empty(mask))
                return -EINVAL;
@@ -156,8 +151,7 @@ static int __bind_irq_vector(int irq, int vector, cpumask_t domain)
        cfg->vector = vector;
        cfg->domain = domain;
        irq_status[irq] = IRQ_USED;
-       pos = vector - IA64_FIRST_DEVICE_VECTOR;
-       cpus_or(vector_table[pos], vector_table[pos], domain);
+       cpus_or(vector_table[vector], vector_table[vector], domain);
        return 0;
 }
 
@@ -174,7 +168,7 @@ int bind_irq_vector(int irq, int vector, cpumask_t domain)
 
 static void __clear_irq_vector(int irq)
 {
-       int vector, cpu, pos;
+       int vector, cpu;
        cpumask_t mask;
        cpumask_t domain;
        struct irq_cfg *cfg = &irq_cfg[irq];
@@ -189,8 +183,7 @@ static void __clear_irq_vector(int irq)
        cfg->vector = IRQ_VECTOR_UNASSIGNED;
        cfg->domain = CPU_MASK_NONE;
        irq_status[irq] = IRQ_UNUSED;
-       pos = vector - IA64_FIRST_DEVICE_VECTOR;
-       cpus_andnot(vector_table[pos], vector_table[pos], domain);
+       cpus_andnot(vector_table[vector], vector_table[vector], domain);
 }
 
 static void clear_irq_vector(int irq)
@@ -287,7 +280,7 @@ static int __init parse_vector_domain(char *arg)
                vector_domain_type = VECTOR_DOMAIN_PERCPU;
                no_int_routing = 1;
        }
-       return 1;
+       return 0;
 }
 early_param("vector", parse_vector_domain);
 #else
@@ -300,10 +293,14 @@ static cpumask_t vector_allocation_domain(int cpu)
 
 void destroy_and_reserve_irq(unsigned int irq)
 {
+       unsigned long flags;
+
        dynamic_irq_cleanup(irq);
 
-       clear_irq_vector(irq);
-       reserve_irq(irq);
+       spin_lock_irqsave(&vector_lock, flags);
+       __clear_irq_vector(irq);
+       irq_status[irq] = IRQ_RSVD;
+       spin_unlock_irqrestore(&vector_lock, flags);
 }
 
 static int __reassign_irq_vector(int irq, int cpu)