*(.proc.info)
__proc_info_end = .;
-#if defined(CONFIG_HAS_VPCI) && defined(CONFIG_LATE_HWDOM)
+#ifdef CONFIG_HAS_VPCI
. = ALIGN(POINTER_ALIGN);
__start_vpci_array = .;
*(SORT(.data.vpci.*))
*(.init_array)
*(SORT(.init_array.*))
__ctors_end = .;
-
-#if defined(CONFIG_HAS_VPCI) && !defined(CONFIG_LATE_HWDOM)
- . = ALIGN(POINTER_ALIGN);
- __start_vpci_array = .;
- *(SORT(.data.vpci.*))
- __end_vpci_array = .;
-#endif
} :text
__init_end_efi = .;
. = ALIGN(STACK_SIZE);
*(.ex_table.pre)
__stop___pre_ex_table = .;
-#if defined(CONFIG_HAS_VPCI) && defined(CONFIG_LATE_HWDOM)
+#ifdef CONFIG_HAS_VPCI
. = ALIGN(POINTER_ALIGN);
__start_vpci_array = .;
*(SORT(.data.vpci.*))
*(.init_array)
*(SORT(.init_array.*))
__ctors_end = .;
-
-#if defined(CONFIG_HAS_VPCI) && !defined(CONFIG_LATE_HWDOM)
- . = ALIGN(POINTER_ALIGN);
- __start_vpci_array = .;
- *(SORT(.data.vpci.*))
- __end_vpci_array = .;
-#endif
} PHDR(text)
. = ALIGN(SECTION_ALIGN);
if ( !pdev->domain )
{
pdev->domain = hardware_domain;
-#ifdef CONFIG_ARM
+ list_add(&pdev->domain_list, &hardware_domain->pdev_list);
+
/*
- * On ARM PCI devices discovery will be done by Dom0. Add vpci handler
- * when Dom0 inform XEN to add the PCI devices in XEN.
+ * For devices not discovered by Xen during boot, add vPCI handlers
+ * when Dom0 first informs Xen about such devices.
*/
ret = vpci_add_handlers(pdev);
if ( ret )
{
printk(XENLOG_ERR "Setup of vPCI failed: %d\n", ret);
+ list_del(&pdev->domain_list);
pdev->domain = NULL;
goto out;
}
-#endif
ret = iommu_add_device(pdev);
if ( ret )
{
+ vpci_remove_device(pdev);
+ list_del(&pdev->domain_list);
pdev->domain = NULL;
goto out;
}
-
- list_add(&pdev->domain_list, &hardware_domain->pdev_list);
}
else
iommu_enable_device(pdev);
list_for_each_entry ( pdev, &pseg->alldevs_list, alldevs_list )
if ( pdev->bus == bus && pdev->devfn == devfn )
{
+ vpci_remove_device(pdev);
pci_cleanup_msi(pdev);
ret = iommu_remove_device(pdev);
if ( pdev->domain )
void vpci_remove_device(struct pci_dev *pdev)
{
+ if ( !has_vpci(pdev->domain) )
+ return;
+
spin_lock(&pdev->vpci->lock);
while ( !list_empty(&pdev->vpci->handlers) )
{
pdev->vpci = NULL;
}
-int __hwdom_init vpci_add_handlers(struct pci_dev *pdev)
+int vpci_add_handlers(struct pci_dev *pdev)
{
unsigned int i;
int rc = 0;
if ( !has_vpci(pdev->domain) )
return 0;
+ /* We should not get here twice for the same device. */
+ ASSERT(!pdev->vpci);
+
pdev->vpci = xzalloc(struct vpci);
if ( !pdev->vpci )
return -ENOMEM;
return 0;
}
+static inline void vpci_remove_device(struct pci_dev *pdev) { }
+
static inline void vpci_dump_msi(void) { }
static inline uint32_t vpci_read(pci_sbdf_t sbdf, unsigned int reg,