Introduce a new sub-option "verbose" to "iommu=", and hide most (debugging) messages when that option is not specified. Particularly messages printed after time management was initialized can, on sufficiently large systems and with a graphical console, lead to time management issues (therefore a call to process_pending_softirqs() also gets added in case the new sub-option is being used). While touching that code, also convert all improper uses of gdprintk() to dprintk(), and convert all boolean iommu config variables to bool_t residing in the .data.read_mostly section. Signed-off-by: Jan Beulich --- 2010-03-02.orig/xen/arch/x86/x86_64/mmconfig-shared.c 2010-03-16 14:11:32.000000000 +0100 +++ 2010-03-02/xen/arch/x86/x86_64/mmconfig-shared.c 2010-03-16 12:02:05.000000000 +0100 @@ -454,12 +454,7 @@ int pci_find_ext_capability(int seg, int * cap version and next pointer all being 0. */ if ( (header == 0) || (header == -1) ) - { - dprintk(XENLOG_INFO VTDPREFIX, - "next cap:%x:%x.%x: no extended config\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); return 0; - } while ( ttl-- > 0 ) { if ( PCI_EXT_CAP_ID(header) == cap ) --- 2010-03-02.orig/xen/drivers/passthrough/amd/iommu_init.c 2010-03-16 14:11:32.000000000 +0100 +++ 2010-03-02/xen/drivers/passthrough/amd/iommu_init.c 2010-03-16 13:30:07.000000000 +0100 @@ -355,7 +355,7 @@ static void iommu_msi_set_affinity(unsig dest = set_desc_affinity(desc, mask); if (dest == BAD_APICID){ - gdprintk(XENLOG_ERR, "Set iommu interrupt affinity error!\n"); + dprintk(XENLOG_ERR, "Set iommu interrupt affinity error!\n"); return; } @@ -531,7 +531,7 @@ static int set_iommu_interrupt_handler(s irq = create_irq(); if ( irq <= 0 ) { - gdprintk(XENLOG_ERR VTDPREFIX, "IOMMU: no irqs\n"); + dprintk(XENLOG_ERR, "IOMMU: no irqs\n"); return 0; } --- 2010-03-02.orig/xen/drivers/passthrough/io.c 2010-03-16 14:11:32.000000000 +0100 +++ 2010-03-02/xen/drivers/passthrough/io.c 2010-03-16 13:43:51.000000000 +0100 @@ -292,10 +292,12 @@ int pt_irq_create_bind_vtd( } } - gdprintk(XENLOG_INFO VTDPREFIX, - "VT-d irq bind: m_irq = %x device = %x intx = %x\n", - machine_gsi, device, intx); spin_unlock(&d->event_lock); + + if ( iommu_verbose ) + dprintk(VTDPREFIX, + "d%d: bind: m_gsi=%u g_gsi=%u device=%u intx=%u\n", + d->domain_id, machine_gsi, guest_gsi, device, intx); } return 0; } @@ -316,10 +318,11 @@ int pt_irq_destroy_bind_vtd( guest_gsi = hvm_pci_intx_gsi(device, intx); link = hvm_pci_intx_link(device, intx); - gdprintk(XENLOG_INFO, - "pt_irq_destroy_bind_vtd: machine_gsi=%d " - "guest_gsi=%d, device=%d, intx=%d.\n", - machine_gsi, guest_gsi, device, intx); + if ( iommu_verbose ) + dprintk(VTDPREFIX, + "d%d: unbind: m_gsi=%u g_gsi=%u device=%u intx=%u\n", + d->domain_id, machine_gsi, guest_gsi, device, intx); + spin_lock(&d->event_lock); hvm_irq_dpci = domain_get_irq_dpci(d); @@ -372,9 +375,11 @@ int pt_irq_destroy_bind_vtd( } } spin_unlock(&d->event_lock); - gdprintk(XENLOG_INFO, - "XEN_DOMCTL_irq_unmapping: m_irq = 0x%x device = 0x%x intx = 0x%x\n", - machine_gsi, device, intx); + + if ( iommu_verbose ) + dprintk(VTDPREFIX, + "d%d unmap: m_irq=%u device=%u intx=%u\n", + d->domain_id, machine_gsi, device, intx); return 0; } --- 2010-03-02.orig/xen/drivers/passthrough/iommu.c 2010-03-16 14:11:32.000000000 +0100 +++ 2010-03-02/xen/drivers/passthrough/iommu.c 2010-03-16 13:41:49.000000000 +0100 @@ -39,16 +39,17 @@ static int iommu_populate_page_table(str * no-intremap Disable VT-d Interrupt Remapping */ custom_param("iommu", parse_iommu_param); -int iommu_enabled = 1; -int iommu_pv_enabled; -int force_iommu; -int iommu_workaround_bios_bug; -int iommu_passthrough; -int iommu_snoop = 1; -int iommu_qinval = 1; -int iommu_intremap = 1; -int amd_iommu_debug; -int amd_iommu_perdev_intremap; +bool_t __read_mostly iommu_enabled = 1; +bool_t __read_mostly iommu_pv_enabled; +bool_t __read_mostly force_iommu; +bool_t __read_mostly iommu_verbose; +bool_t __read_mostly iommu_workaround_bios_bug; +bool_t __read_mostly iommu_passthrough; +bool_t __read_mostly iommu_snoop = 1; +bool_t __read_mostly iommu_qinval = 1; +bool_t __read_mostly iommu_intremap = 1; +bool_t __read_mostly amd_iommu_debug; +bool_t __read_mostly amd_iommu_perdev_intremap; static void __init parse_iommu_param(char *s) { @@ -72,6 +73,8 @@ static void __init parse_iommu_param(cha iommu_workaround_bios_bug = 1; else if ( !strcmp(s, "passthrough") ) iommu_passthrough = 1; + else if ( !strcmp(s, "verbose") ) + iommu_verbose = 1; else if ( !strcmp(s, "no-snoop") ) iommu_snoop = 0; else if ( !strcmp(s, "no-qinval") ) @@ -251,17 +254,17 @@ int deassign_device(struct domain *d, u8 if ( pdev->domain != d ) { - gdprintk(XENLOG_ERR VTDPREFIX, - "IOMMU: deassign a device not owned\n"); + dprintk(XENLOG_ERR VTDPREFIX, + "d%d: deassign a device not owned\n", d->domain_id); return -EINVAL; } ret = hd->platform_ops->reassign_device(d, dom0, bus, devfn); if ( ret ) { - gdprintk(XENLOG_ERR VTDPREFIX, - "Deassign device (%x:%x.%x) failed!\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); + dprintk(XENLOG_ERR VTDPREFIX, + "d%d: Deassign device (%x:%x.%x) failed!\n", + d->domain_id, bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); return ret; } --- 2010-03-02.orig/xen/drivers/passthrough/vtd/dmar.c 2010-02-12 08:48:15.000000000 +0100 +++ 2010-03-02/xen/drivers/passthrough/vtd/dmar.c 2010-03-16 14:23:56.000000000 +0100 @@ -313,27 +313,31 @@ static int __init acpi_parse_dev_scope(v bus, path->dev, path->fn, PCI_SECONDARY_BUS); sub_bus = pci_conf_read8( bus, path->dev, path->fn, PCI_SUBORDINATE_BUS); - dprintk(XENLOG_INFO VTDPREFIX, - " bridge: %x:%x.%x start = %x sec = %x sub = %x\n", - bus, path->dev, path->fn, - acpi_scope->start_bus, sec_bus, sub_bus); + if ( iommu_verbose ) + dprintk(VTDPREFIX, + " bridge: %x:%x.%x start = %x sec = %x sub = %x\n", + bus, path->dev, path->fn, + acpi_scope->start_bus, sec_bus, sub_bus); dmar_scope_add_buses(scope, sec_bus, sub_bus); break; case ACPI_DEV_MSI_HPET: - dprintk(XENLOG_INFO VTDPREFIX, " MSI HPET: %x:%x.%x\n", - bus, path->dev, path->fn); + if ( iommu_verbose ) + dprintk(VTDPREFIX, " MSI HPET: %x:%x.%x\n", + bus, path->dev, path->fn); break; case ACPI_DEV_ENDPOINT: - dprintk(XENLOG_INFO VTDPREFIX, " endpoint: %x:%x.%x\n", - bus, path->dev, path->fn); + if ( iommu_verbose ) + dprintk(VTDPREFIX, " endpoint: %x:%x.%x\n", + bus, path->dev, path->fn); break; case ACPI_DEV_IOAPIC: - dprintk(XENLOG_INFO VTDPREFIX, " IOAPIC: %x:%x.%x\n", - bus, path->dev, path->fn); + if ( iommu_verbose ) + dprintk(VTDPREFIX, " IOAPIC: %x:%x.%x\n", + bus, path->dev, path->fn); if ( type == DMAR_TYPE ) { @@ -375,8 +379,9 @@ acpi_parse_one_drhd(struct acpi_dmar_ent dmaru->address = drhd->address; dmaru->include_all = drhd->flags & 1; /* BIT0: INCLUDE_ALL */ INIT_LIST_HEAD(&dmaru->ioapic_list); - dprintk(XENLOG_INFO VTDPREFIX, " dmaru->address = %"PRIx64"\n", - dmaru->address); + if ( iommu_verbose ) + dprintk(VTDPREFIX, " dmaru->address = %"PRIx64"\n", + dmaru->address); addr = map_to_nocache_virt(0, drhd->address); dmaru->ecap = dmar_readq(addr, DMAR_ECAP_REG); @@ -388,7 +393,8 @@ acpi_parse_one_drhd(struct acpi_dmar_ent if ( dmaru->include_all ) { - dprintk(XENLOG_INFO VTDPREFIX, " flags: INCLUDE_ALL\n"); + if ( iommu_verbose ) + dprintk(VTDPREFIX, " flags: INCLUDE_ALL\n"); /* Only allow one INCLUDE_ALL */ if ( include_all ) { @@ -535,9 +541,11 @@ acpi_parse_one_rmrr(struct acpi_dmar_ent } else { - dprintk(XENLOG_INFO VTDPREFIX, - " RMRR region: base_addr %"PRIx64" end_address %"PRIx64"\n", - rmrru->base_address, rmrru->end_address); + if ( iommu_verbose ) + dprintk(VTDPREFIX, + " RMRR region: base_addr %"PRIx64 + " end_address %"PRIx64"\n", + rmrru->base_address, rmrru->end_address); acpi_register_rmrr_unit(rmrru); } } @@ -560,8 +568,9 @@ acpi_parse_one_atsr(struct acpi_dmar_ent memset(atsru, 0, sizeof(struct acpi_atsr_unit)); atsru->all_ports = atsr->flags & 1; /* BIT0: ALL_PORTS */ - dprintk(XENLOG_INFO VTDPREFIX, - " atsru->all_ports: %x\n", atsru->all_ports); + if ( iommu_verbose ) + dprintk(VTDPREFIX, + " atsru->all_ports: %x\n", atsru->all_ports); if ( !atsru->all_ports ) { dev_scope_start = (void *)(atsr + 1); @@ -571,7 +580,8 @@ acpi_parse_one_atsr(struct acpi_dmar_ent } else { - dprintk(XENLOG_INFO VTDPREFIX, " flags: ALL_PORTS\n"); + if ( iommu_verbose ) + dprintk(VTDPREFIX, " flags: ALL_PORTS\n"); /* Only allow one ALL_PORTS */ if ( all_ports ) { @@ -604,9 +614,11 @@ acpi_parse_one_rhsa(struct acpi_dmar_ent rhsau->address = rhsa->address; rhsau->proximity_domain = rhsa->proximity_domain; list_add_tail(&rhsau->list, &acpi_rhsa_units); - dprintk(XENLOG_INFO VTDPREFIX, - " rhsau->address: %"PRIx64" rhsau->proximity_domain: %"PRIx32"\n", - rhsau->address, rhsau->proximity_domain); + if ( iommu_verbose ) + dprintk(VTDPREFIX, + " rhsau->address: %"PRIx64 + " rhsau->proximity_domain: %"PRIx32"\n", + rhsau->address, rhsau->proximity_domain); return ret; } @@ -633,8 +645,9 @@ static int __init acpi_parse_dmar(struct } dmar_host_address_width = dmar->width + 1; - dprintk(XENLOG_INFO VTDPREFIX, "Host address width %d\n", - dmar_host_address_width); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "Host address width %d\n", + dmar_host_address_width); entry_header = (struct acpi_dmar_entry_header *)(dmar + 1); while ( ((unsigned long)entry_header) < @@ -643,23 +656,29 @@ static int __init acpi_parse_dmar(struct switch ( entry_header->type ) { case ACPI_DMAR_DRHD: - dprintk(XENLOG_INFO VTDPREFIX, "found ACPI_DMAR_DRHD:\n"); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "found ACPI_DMAR_DRHD:\n"); ret = acpi_parse_one_drhd(entry_header); break; case ACPI_DMAR_RMRR: - dprintk(XENLOG_INFO VTDPREFIX, "found ACPI_DMAR_RMRR:\n"); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "found ACPI_DMAR_RMRR:\n"); ret = acpi_parse_one_rmrr(entry_header); break; case ACPI_DMAR_ATSR: - dprintk(XENLOG_INFO VTDPREFIX, "found ACPI_DMAR_ATSR:\n"); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "found ACPI_DMAR_ATSR:\n"); ret = acpi_parse_one_atsr(entry_header); break; case ACPI_DMAR_RHSA: - dprintk(XENLOG_INFO VTDPREFIX, "found ACPI_DMAR_RHSA:\n"); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "found ACPI_DMAR_RHSA:\n"); ret = acpi_parse_one_rhsa(entry_header); break; default: - dprintk(XENLOG_WARNING VTDPREFIX, "Unknown DMAR structure type\n"); + dprintk(XENLOG_WARNING VTDPREFIX, + "Unknown DMAR structure type %x\n", + entry_header->type); ret = -EINVAL; break; } --- 2010-03-02.orig/xen/drivers/passthrough/vtd/intremap.c 2010-03-16 14:11:32.000000000 +0100 +++ 2010-03-02/xen/drivers/passthrough/vtd/intremap.c 2010-03-16 13:20:28.000000000 +0100 @@ -475,9 +475,9 @@ static void set_msi_source_id(struct pci break; default: - gdprintk(XENLOG_WARNING VTDPREFIX, - "set_msi_source_id: unknown type : bdf = %x:%x.%x\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); + dprintk(XENLOG_WARNING VTDPREFIX, "d%d: unknown(%u): bdf = %x:%x.%x\n", + pdev->domain->domain_id, type, + bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); break; } } --- 2010-03-02.orig/xen/drivers/passthrough/vtd/iommu.c 2010-03-16 14:11:32.000000000 +0100 +++ 2010-03-02/xen/drivers/passthrough/vtd/iommu.c 2010-03-16 15:19:21.000000000 +0100 @@ -63,9 +63,9 @@ static int domain_iommu_domid(struct dom i = find_next_bit(iommu->domid_bitmap, nr_dom, i+1); } - gdprintk(XENLOG_ERR VTDPREFIX, - "Cannot get valid iommu domid: domid=%d iommu->index=%d\n", - d->domain_id, iommu->index); + dprintk(XENLOG_ERR VTDPREFIX, + "Cannot get valid iommu domid: domid=%d iommu->index=%d\n", + d->domain_id, iommu->index); return -1; } @@ -97,7 +97,7 @@ static int context_set_domain_id(struct i = find_first_zero_bit(iommu->domid_bitmap, nr_dom); if ( i >= nr_dom ) { - gdprintk(XENLOG_ERR VTDPREFIX, "IOMMU: no free domain ids\n"); + dprintk(XENLOG_ERR VTDPREFIX, "IOMMU: no free domain ids\n"); return -EFAULT; } iommu->domid_map[i] = d->domain_id; @@ -690,8 +690,9 @@ static void iommu_enable_translation(str u32 sts; unsigned long flags; - dprintk(XENLOG_INFO VTDPREFIX, - "iommu_enable_translation: iommu->reg = %p\n", iommu->reg); + if ( iommu_verbose ) + dprintk(VTDPREFIX, + "iommu_enable_translation: iommu->reg = %p\n", iommu->reg); spin_lock_irqsave(&iommu->register_lock, flags); sts = dmar_readl(iommu->reg, DMAR_GSTS_REG); dmar_writel(iommu->reg, DMAR_GCMD_REG, sts | DMA_GCMD_TE); @@ -1070,11 +1071,14 @@ static int __init iommu_alloc(struct acp drhd->iommu = iommu; - dprintk(XENLOG_DEBUG VTDPREFIX, - "drhd->address = %"PRIx64" iommu->reg = %p\n", - drhd->address, iommu->reg); - dprintk(XENLOG_DEBUG VTDPREFIX, - "cap = %"PRIx64" ecap = %"PRIx64"\n", iommu->cap, iommu->ecap); + if ( iommu_verbose ) + { + dprintk(VTDPREFIX, + "drhd->address = %"PRIx64" iommu->reg = %p\n", + drhd->address, iommu->reg); + dprintk(VTDPREFIX, + "cap = %"PRIx64" ecap = %"PRIx64"\n", iommu->cap, iommu->ecap); + } if ( cap_fault_reg_offset(iommu->cap) + cap_num_fault_regs(iommu->cap) * PRIMARY_FAULT_REG_LEN >= PAGE_SIZE || ecap_iotlb_offset(iommu->ecap) >= PAGE_SIZE ) @@ -1316,16 +1320,16 @@ static int domain_context_mapping(struct break; case DEV_TYPE_PCIe_ENDPOINT: - gdprintk(XENLOG_INFO VTDPREFIX, - "domain_context_mapping:PCIe: bdf = %x:%x.%x\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "d%d:PCIe: map bdf = %x:%x.%x\n", + domain->domain_id, bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); ret = domain_context_mapping_one(domain, drhd->iommu, bus, devfn); break; case DEV_TYPE_PCI: - gdprintk(XENLOG_INFO VTDPREFIX, - "domain_context_mapping:PCI: bdf = %x:%x.%x\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "d%d:PCI: map bdf = %x:%x.%x\n", + domain->domain_id, bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); ret = domain_context_mapping_one(domain, drhd->iommu, bus, devfn); if ( ret ) @@ -1355,13 +1359,16 @@ static int domain_context_mapping(struct break; default: - gdprintk(XENLOG_ERR VTDPREFIX, - "domain_context_mapping:unknown type : bdf = %x:%x.%x\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); + dprintk(XENLOG_ERR VTDPREFIX, "d%d:unknown(%u): bdf = %x:%x.%x\n", + domain->domain_id, type, + bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); ret = -EINVAL; break; } + if ( iommu_verbose ) + process_pending_softirqs(); + return ret; } @@ -1442,16 +1449,16 @@ static int domain_context_unmap(struct d goto out; case DEV_TYPE_PCIe_ENDPOINT: - gdprintk(XENLOG_INFO VTDPREFIX, - "domain_context_unmap:PCIe: bdf = %x:%x.%x\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "d%d:PCIe: unmap bdf = %x:%x.%x\n", + domain->domain_id, bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); ret = domain_context_unmap_one(domain, iommu, bus, devfn); break; case DEV_TYPE_PCI: - gdprintk(XENLOG_INFO VTDPREFIX, - "domain_context_unmap:PCI: bdf = %x:%x.%x\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); + if ( iommu_verbose ) + dprintk(VTDPREFIX, "d%d:PCI: unmap bdf = %x:%x.%x\n", + domain->domain_id, bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); ret = domain_context_unmap_one(domain, iommu, bus, devfn); if ( ret ) break; @@ -1476,9 +1483,9 @@ static int domain_context_unmap(struct d break; default: - gdprintk(XENLOG_ERR VTDPREFIX, - "domain_context_unmap:unknown type: bdf = %x:%x.%x\n", - bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); + dprintk(XENLOG_ERR VTDPREFIX, "d%d:unknown(%u): bdf = %x:%x.%x\n", + domain->domain_id, type, + bus, PCI_SLOT(devfn), PCI_FUNC(devfn)); ret = -EINVAL; goto out; } @@ -1702,8 +1709,8 @@ static int intel_iommu_add_device(struct ret = domain_context_mapping(pdev->domain, pdev->bus, pdev->devfn); if ( ret ) { - gdprintk(XENLOG_ERR VTDPREFIX, - "intel_iommu_add_device: context mapping failed\n"); + dprintk(XENLOG_ERR VTDPREFIX, "d%d: context mapping failed\n", + pdev->domain->domain_id); return ret; } @@ -1713,8 +1720,8 @@ static int intel_iommu_add_device(struct { ret = rmrr_identity_mapping(pdev->domain, rmrr); if ( ret ) - gdprintk(XENLOG_ERR VTDPREFIX, - "intel_iommu_add_device: RMRR mapping failed\n"); + dprintk(XENLOG_ERR VTDPREFIX, "d%d: RMRR mapping failed\n", + pdev->domain->domain_id); } } @@ -2031,7 +2038,7 @@ static int intel_iommu_assign_device(str if (pdev->domain != dom0) { - gdprintk(XENLOG_ERR VTDPREFIX, + dprintk(XENLOG_ERR VTDPREFIX, "IOMMU: assign a assigned device\n"); return -EBUSY; } @@ -2057,8 +2064,8 @@ static int intel_iommu_assign_device(str ret = rmrr_identity_mapping(d, rmrr); if ( ret ) { - gdprintk(XENLOG_ERR VTDPREFIX, - "IOMMU: mapping reserved region failed\n"); + dprintk(XENLOG_ERR VTDPREFIX, + "IOMMU: mapping reserved region failed\n"); goto done; } } --- 2010-03-02.orig/xen/include/xen/iommu.h 2010-03-16 14:11:32.000000000 +0100 +++ 2010-03-02/xen/include/xen/iommu.h 2010-03-16 13:40:48.000000000 +0100 @@ -26,14 +26,10 @@ #include #include -extern int iommu_enabled; -extern int iommu_pv_enabled; -extern int force_iommu; -extern int iommu_workaround_bios_bug; -extern int iommu_passthrough; -extern int iommu_snoop; -extern int iommu_qinval; -extern int iommu_intremap; +extern bool_t iommu_enabled, iommu_pv_enabled; +extern bool_t force_iommu, iommu_verbose; +extern bool_t iommu_workaround_bios_bug, iommu_passthrough; +extern bool_t iommu_snoop, iommu_qinval, iommu_intremap; #define domain_hvm_iommu(d) (&d->arch.hvm_domain.hvm_iommu)