In apic_send_msi(), set msi_redir_hint to 0x1 when RH=1 in the MSI Address Register.
Added an argument for msi_redir_hint to apic_deliver_irq(), and changed calls to the function accordingly (using 0 as a default value for non-MSI interrupts). Signed-off-by: James Sullivan <sullivan.jame...@gmail.com> --- Changes in v2: * Corrected use of MSI data register => addr register when setting msi_redir_hint in apic_send_msi(). hw/intc/apic.c | 10 ++++++---- hw/intc/ioapic.c | 2 +- include/hw/i386/apic.h | 3 ++- trace-events | 2 +- 4 files changed, 10 insertions(+), 7 deletions(-) diff --git a/hw/intc/apic.c b/hw/intc/apic.c index c49eb26..f3ec2c8 100644 --- a/hw/intc/apic.c +++ b/hw/intc/apic.c @@ -318,12 +318,13 @@ static void apic_bus_deliver(const uint32_t *deliver_bitmask, } void apic_deliver_irq(uint8_t dest, uint8_t dest_mode, uint8_t delivery_mode, - uint8_t vector_num, uint8_t trigger_mode) + uint8_t vector_num, uint8_t trigger_mode, + uint8_t msi_redir_hint) { uint32_t deliver_bitmask[MAX_APIC_WORDS]; trace_apic_deliver_irq(dest, dest_mode, delivery_mode, vector_num, - trigger_mode); + trigger_mode, msi_redir_hint); apic_get_delivery_bitmask(deliver_bitmask, dest, dest_mode); apic_bus_deliver(deliver_bitmask, delivery_mode, vector_num, trigger_mode); @@ -808,8 +809,9 @@ static void apic_send_msi(hwaddr addr, uint32_t data) uint8_t dest_mode = (addr >> MSI_ADDR_DEST_MODE_SHIFT) & 0x1; uint8_t trigger_mode = (data >> MSI_DATA_TRIGGER_SHIFT) & 0x1; uint8_t delivery = (data >> MSI_DATA_DELIVERY_MODE_SHIFT) & 0x7; - /* XXX: Ignore redirection hint. */ - apic_deliver_irq(dest, dest_mode, delivery, vector, trigger_mode); + uint8_t msi_redir_hint = (addr >> MSI_ADDR_REDIRECTION_SHIFT) & 0x1; + apic_deliver_irq(dest, dest_mode, delivery, vector, trigger_mode, + msi_redir_hint); } static void apic_mem_writel(void *opaque, hwaddr addr, uint32_t val) diff --git a/hw/intc/ioapic.c b/hw/intc/ioapic.c index b527932..e69aa18 100644 --- a/hw/intc/ioapic.c +++ b/hw/intc/ioapic.c @@ -71,7 +71,7 @@ static void ioapic_service(IOAPICCommonState *s) vector = entry & IOAPIC_VECTOR_MASK; } apic_deliver_irq(dest, dest_mode, delivery_mode, - vector, trig_mode); + vector, trig_mode, 0); } } } diff --git a/include/hw/i386/apic.h b/include/hw/i386/apic.h index 51eb6d3..9d7c0a4 100644 --- a/include/hw/i386/apic.h +++ b/include/hw/i386/apic.h @@ -5,7 +5,8 @@ /* apic.c */ void apic_deliver_irq(uint8_t dest, uint8_t dest_mode, uint8_t delivery_mode, - uint8_t vector_num, uint8_t trigger_mode); + uint8_t vector_num, uint8_t trigger_mode, + uint8_t msi_redir_hint); int apic_accept_pic_intr(DeviceState *s); void apic_deliver_pic_intr(DeviceState *s, int level); void apic_deliver_nmi(DeviceState *d); diff --git a/trace-events b/trace-events index 30eba92..b430cf9 100644 --- a/trace-events +++ b/trace-events @@ -158,7 +158,7 @@ apic_get_irq_delivered(int apic_irq_delivered) "returning coalescing %d" # hw/intc/apic.c apic_local_deliver(int vector, uint32_t lvt) "vector %d delivery mode %d" -apic_deliver_irq(uint8_t dest, uint8_t dest_mode, uint8_t delivery_mode, uint8_t vector_num, uint8_t trigger_mode) "dest %d dest_mode %d delivery_mode %d vector %d trigger_mode %d" +apic_deliver_irq(uint8_t dest, uint8_t dest_mode, uint8_t delivery_mode, uint8_t vector_num, uint8_t trigger_mode, uint8_t msi_redir_hint) "dest %d dest_mode %d delivery_mode %d vector %d trigger_mode %d msi_redir_hint %d" apic_mem_readl(uint64_t addr, uint32_t val) "%"PRIx64" = %08x" apic_mem_writel(uint64_t addr, uint32_t val) "%"PRIx64" = %08x" -- 2.3.4