From 724834f96fcae096b8a2f51c76e0f0059dfa8871 Mon Sep 17 00:00:00 2001 From: Uri Lublin Date: Tue, 27 Nov 2007 20:56:20 +0200 Subject: Migration: save/load PCI-Bus irq related state. This irq state is being used to decide whether or not an interrupt should be passed to the guest or not. This state can be calculated from all the pci devices on that bus. This commit may be reverted if we decide to calculate the irq related state instead of save/load it. Signed-off-by: Uri Lublin Signed-off-by: Avi Kivity --- hw/pci.c | 36 ++++++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) diff --git a/hw/pci.c b/hw/pci.c index 774a8cf49..825b17b62 100644 --- a/hw/pci.c +++ b/hw/pci.c @@ -39,6 +39,7 @@ struct PCIBus { PCIBus *next; /* The bus IRQ state is the logical OR of the connected devices. Keep a count of the number of devices with raised IRQs. */ + int nirq; int irq_count[]; }; @@ -49,16 +50,51 @@ target_phys_addr_t pci_mem_base; static int pci_irq_index; static PCIBus *first_bus; +static void pcibus_save(QEMUFile *f, void *opaque) +{ + PCIBus *bus = (PCIBus *)opaque; + int i; + + qemu_put_be32s(f, &bus->nirq); + for (i=0; inirq; i++) + qemu_put_be32s(f, &bus->irq_count[i]); +} + +static int pcibus_load(QEMUFile *f, void *opaque, int version_id) +{ + PCIBus *bus = (PCIBus *)opaque; + int i, nirq; + + if (version_id != 1) + return -EINVAL; + + qemu_get_be32s(f, &nirq); + if (bus->nirq != nirq) { + fprintf(stderr, "pcibus_load: nirq mismatch: src=%d dst=%d\n", + nirq, bus->nirq); + return -EINVAL; + } + + for (i=0; iirq_count[i]); + + return 0; +} + PCIBus *pci_register_bus(pci_set_irq_fn set_irq, pci_map_irq_fn map_irq, qemu_irq *pic, int devfn_min, int nirq) { PCIBus *bus; + static int nbus = 0; + bus = qemu_mallocz(sizeof(PCIBus) + (nirq * sizeof(int))); bus->set_irq = set_irq; bus->map_irq = map_irq; bus->irq_opaque = pic; bus->devfn_min = devfn_min; + bus->nirq = nirq; first_bus = bus; + register_savevm("PCIBUS", nbus++, 1, pcibus_save, pcibus_load, bus); return bus; } -- cgit v1.2.3