direct-io.hg
changeset 7735:c405c0d1b49b
This patch fix some issue on masked interrupt:
1) check the mask setting on vmx_vioapic_do_irqs and
ioapic_get_highest_irq
2) Place mask info to a seperated data structure, and access it
atomically
Signed-off-by: Yunhong Jiang <yunhong.jiang@intel.com>
1) check the mask setting on vmx_vioapic_do_irqs and
ioapic_get_highest_irq
2) Place mask info to a seperated data structure, and access it
atomically
Signed-off-by: Yunhong Jiang <yunhong.jiang@intel.com>
author | kaf24@firebug.cl.cam.ac.uk |
---|---|
date | Thu Nov 10 12:12:00 2005 +0100 (2005-11-10) |
parents | bee09e2200ab |
children | d916497135ac |
files | xen/arch/x86/dm/vmx_vioapic.c xen/include/asm-x86/vmx_vioapic.h |
line diff
1.1 --- a/xen/arch/x86/dm/vmx_vioapic.c Thu Nov 10 12:11:39 2005 +0100 1.2 +++ b/xen/arch/x86/dm/vmx_vioapic.c Thu Nov 10 12:12:00 2005 +0100 1.3 @@ -158,6 +158,14 @@ static unsigned long vmx_vioapic_read(st 1.4 return result; 1.5 } 1.6 1.7 +static void vmx_vioapic_update_imr(struct vmx_vioapic *s, int index) 1.8 +{ 1.9 + if (s->redirtbl[index].RedirForm.mask) 1.10 + set_bit(index, &s->imr); 1.11 + else 1.12 + clear_bit(index, &s->imr); 1.13 +} 1.14 + 1.15 static void vmx_vioapic_write_indirect(struct vmx_vioapic *s, 1.16 unsigned long addr, 1.17 unsigned long length, 1.18 @@ -200,6 +208,7 @@ static void vmx_vioapic_write_indirect(s 1.19 redir_content = ((redir_content >> 32) << 32) | 1.20 (val & 0xffffffff); 1.21 s->redirtbl[redir_index].value = redir_content; 1.22 + vmx_vioapic_update_imr(s, redir_index); 1.23 } else { 1.24 printk("vmx_vioapic_write_indirect " 1.25 "error register %x\n", s->ioregsel); 1.26 @@ -264,8 +273,10 @@ static void vmx_vioapic_reset(vmx_vioapi 1.27 1.28 memset(s, 0, sizeof(vmx_vioapic_t)); 1.29 1.30 - for (i = 0; i < IOAPIC_NUM_PINS; i++) 1.31 + for (i = 0; i < IOAPIC_NUM_PINS; i++) { 1.32 s->redirtbl[i].RedirForm.mask = 0x1; 1.33 + vmx_vioapic_update_imr(s, i); 1.34 + } 1.35 } 1.36 1.37 static void ioapic_update_config(vmx_vioapic_t *s, 1.38 @@ -422,7 +433,13 @@ static void ioapic_deliver(vmx_vioapic_t 1.39 1.40 target = apic_round_robin( 1.41 s->domain, dest_mode, vector, deliver_bitmask); 1.42 - ioapic_inj_irq(s, target, vector, trig_mode, delivery_mode); 1.43 + if (target) 1.44 + ioapic_inj_irq(s, target, vector, trig_mode, delivery_mode); 1.45 + else{ 1.46 + VMX_DBG_LOG(DBG_LEVEL_IOAPIC, "ioapic deliver " 1.47 + "null round robin mask %x vector %x delivery_mode %x\n", 1.48 + deliver_bitmask, vector, deliver_bitmask); 1.49 + } 1.50 break; 1.51 } 1.52 1.53 @@ -457,7 +474,7 @@ static int ioapic_get_highest_irq(vmx_vi 1.54 1.55 ASSERT(s); 1.56 1.57 - irqs = s->irr & ~s->isr; 1.58 + irqs = s->irr & ~s->isr & ~s->imr; 1.59 return __fls(irqs); 1.60 } 1.61 1.62 @@ -471,7 +488,7 @@ static void service_ioapic(vmx_vioapic_t 1.63 VMX_DBG_LOG(DBG_LEVEL_IOAPIC, "service_ioapic " 1.64 "highest irqno %x\n", irqno); 1.65 1.66 - if (!s->redirtbl[irqno].RedirForm.mask) { 1.67 + if (!test_bit(irqno, &s->imr)) { 1.68 ioapic_deliver(s, irqno); 1.69 } 1.70 1.71 @@ -490,7 +507,7 @@ void vmx_vioapic_do_irqs(struct domain * 1.72 if (!vmx_apic_support(d)) 1.73 return; 1.74 1.75 - s->irr |= irqs; 1.76 + s->irr |= irqs & ~s->imr; 1.77 service_ioapic(s); 1.78 } 1.79 1.80 @@ -584,7 +601,9 @@ int vmx_vioapic_add_lapic(struct vlapic 1.81 domain_crash_synchronous(); 1.82 } 1.83 1.84 - s->lapic_info[s->lapic_count ++] = vlapic; 1.85 + /* update count later for race condition on interrupt */ 1.86 + s->lapic_info[s->lapic_count] = vlapic; 1.87 + s->lapic_count ++; 1.88 1.89 return s->lapic_count; 1.90 }
2.1 --- a/xen/include/asm-x86/vmx_vioapic.h Thu Nov 10 12:11:39 2005 +0100 2.2 +++ b/xen/include/asm-x86/vmx_vioapic.h Thu Nov 10 12:12:00 2005 +0100 2.3 @@ -92,9 +92,10 @@ typedef union RedirStatus 2.4 #define MAX_LAPIC_NUM 32 2.5 2.6 typedef struct vmx_vioapic { 2.7 - uint32_t ioregsel; 2.8 uint32_t irr; 2.9 uint32_t isr; /* This is used for level trigger */ 2.10 + uint32_t imr; 2.11 + uint32_t ioregsel; 2.12 uint32_t flags; 2.13 uint32_t lapic_count; 2.14 uint32_t id;