diff options
author | Jiang Liu <jiang.liu@linux.intel.com> | 2014-02-19 14:07:33 +0800 |
---|---|---|
committer | Joerg Roedel <joro@8bytes.org> | 2014-03-04 17:51:05 +0100 |
commit | 3a5670e8ac932c10a3e50d9dc0ab1da4cc3041d7 (patch) | |
tree | 83a870c5951c2deafcf7eef4fc2212bb937f1b6e /include/linux/dmar.h | |
parent | b683b230a244c3b2b3f6f3292e59d4a63298528b (diff) | |
download | blackbird-op-linux-3a5670e8ac932c10a3e50d9dc0ab1da4cc3041d7.tar.gz blackbird-op-linux-3a5670e8ac932c10a3e50d9dc0ab1da4cc3041d7.zip |
iommu/vt-d: Introduce a rwsem to protect global data structures
Introduce a global rwsem dmar_global_lock, which will be used to
protect DMAR related global data structures from DMAR/PCI/memory
device hotplug operations in process context.
DMA and interrupt remapping related data structures are read most,
and only change when memory/PCI/DMAR hotplug event happens.
So a global rwsem solution is adopted for balance between simplicity
and performance.
For interrupt remapping driver, function intel_irq_remapping_supported(),
dmar_table_init(), intel_enable_irq_remapping(), disable_irq_remapping(),
reenable_irq_remapping() and enable_drhd_fault_handling() etc
are called during booting, suspending and resuming with interrupt
disabled, so no need to take the global lock.
For interrupt remapping entry allocation, the locking model is:
down_read(&dmar_global_lock);
/* Find corresponding iommu */
iommu = map_hpet_to_ir(id);
if (iommu)
/*
* Allocate remapping entry and mark entry busy,
* the IOMMU won't be hot-removed until the
* allocated entry has been released.
*/
index = alloc_irte(iommu, irq, 1);
up_read(&dmar_global_lock);
For DMA remmaping driver, we only uses the dmar_global_lock rwsem to
protect functions which are only called in process context. For any
function which may be called in interrupt context, we will use RCU
to protect them in following patches.
Signed-off-by: Jiang Liu <jiang.liu@linux.intel.com>
Signed-off-by: Joerg Roedel <joro@8bytes.org>
Diffstat (limited to 'include/linux/dmar.h')
-rw-r--r-- | include/linux/dmar.h | 2 |
1 files changed, 2 insertions, 0 deletions
diff --git a/include/linux/dmar.h b/include/linux/dmar.h index 4b77fd8fde76..8f06a0135a84 100644 --- a/include/linux/dmar.h +++ b/include/linux/dmar.h @@ -25,6 +25,7 @@ #include <linux/types.h> #include <linux/msi.h> #include <linux/irqreturn.h> +#include <linux/rwsem.h> struct acpi_dmar_header; @@ -48,6 +49,7 @@ struct dmar_drhd_unit { struct intel_iommu *iommu; }; +extern struct rw_semaphore dmar_global_lock; extern struct list_head dmar_drhd_units; #define for_each_drhd_unit(drhd) \ |