aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/x86/Kconfig15
-rw-r--r--drivers/pci/intel-iommu.c107
2 files changed, 34 insertions, 88 deletions
diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
index d1430ef6b4f9..c07f72205909 100644
--- a/arch/x86/Kconfig
+++ b/arch/x86/Kconfig
@@ -1913,25 +1913,14 @@ config DMAR_DEFAULT_ON
1913 recommended you say N here while the DMAR code remains 1913 recommended you say N here while the DMAR code remains
1914 experimental. 1914 experimental.
1915 1915
1916config DMAR_GFX_WA
1917 def_bool y
1918 prompt "Support for Graphics workaround"
1919 depends on DMAR
1920 ---help---
1921 Current Graphics drivers tend to use physical address
1922 for DMA and avoid using DMA APIs. Setting this config
1923 option permits the IOMMU driver to set a unity map for
1924 all the OS-visible memory. Hence the driver can continue
1925 to use physical addresses for DMA.
1926
1927config DMAR_FLOPPY_WA 1916config DMAR_FLOPPY_WA
1928 def_bool y 1917 def_bool y
1929 depends on DMAR 1918 depends on DMAR
1930 ---help--- 1919 ---help---
1931 Floppy disk drivers are know to bypass DMA API calls 1920 Floppy disk drivers are known to bypass DMA API calls
1932 thereby failing to work when IOMMU is enabled. This 1921 thereby failing to work when IOMMU is enabled. This
1933 workaround will setup a 1:1 mapping for the first 1922 workaround will setup a 1:1 mapping for the first
1934 16M to make floppy (an ISA device) work. 1923 16MiB to make floppy (an ISA device) work.
1935 1924
1936config INTR_REMAP 1925config INTR_REMAP
1937 bool "Support for Interrupt Remapping (EXPERIMENTAL)" 1926 bool "Support for Interrupt Remapping (EXPERIMENTAL)"
diff --git a/drivers/pci/intel-iommu.c b/drivers/pci/intel-iommu.c
index 3a4f347e2f88..fc121967cb5b 100644
--- a/drivers/pci/intel-iommu.c
+++ b/drivers/pci/intel-iommu.c
@@ -1889,11 +1889,7 @@ static int iommu_prepare_identity_map(struct pci_dev *pdev,
1889 "IOMMU: Setting identity map for device %s [0x%Lx - 0x%Lx]\n", 1889 "IOMMU: Setting identity map for device %s [0x%Lx - 0x%Lx]\n",
1890 pci_name(pdev), start, end); 1890 pci_name(pdev), start, end);
1891 1891
1892 if (iommu_identity_mapping) 1892 domain = get_domain_for_dev(pdev, DEFAULT_DOMAIN_ADDRESS_WIDTH);
1893 domain = si_domain;
1894 else
1895 /* page table init */
1896 domain = get_domain_for_dev(pdev, DEFAULT_DOMAIN_ADDRESS_WIDTH);
1897 if (!domain) 1893 if (!domain)
1898 return -ENOMEM; 1894 return -ENOMEM;
1899 1895
@@ -1922,64 +1918,6 @@ static inline int iommu_prepare_rmrr_dev(struct dmar_rmrr_unit *rmrr,
1922 rmrr->end_address + 1); 1918 rmrr->end_address + 1);
1923} 1919}
1924 1920
1925struct iommu_prepare_data {
1926 struct pci_dev *pdev;
1927 int ret;
1928};
1929
1930static int __init iommu_prepare_work_fn(unsigned long start_pfn,
1931 unsigned long end_pfn, void *datax)
1932{
1933 struct iommu_prepare_data *data;
1934
1935 data = (struct iommu_prepare_data *)datax;
1936
1937 data->ret = iommu_prepare_identity_map(data->pdev,
1938 start_pfn<<PAGE_SHIFT, end_pfn<<PAGE_SHIFT);
1939 return data->ret;
1940
1941}
1942
1943static int __init iommu_prepare_with_active_regions(struct pci_dev *pdev)
1944{
1945 int nid;
1946 struct iommu_prepare_data data;
1947
1948 data.pdev = pdev;
1949 data.ret = 0;
1950
1951 for_each_online_node(nid) {
1952 work_with_active_regions(nid, iommu_prepare_work_fn, &data);
1953 if (data.ret)
1954 return data.ret;
1955 }
1956 return data.ret;
1957}
1958
1959#ifdef CONFIG_DMAR_GFX_WA
1960static void __init iommu_prepare_gfx_mapping(void)
1961{
1962 struct pci_dev *pdev = NULL;
1963 int ret;
1964
1965 for_each_pci_dev(pdev) {
1966 if (pdev->dev.archdata.iommu == DUMMY_DEVICE_DOMAIN_INFO ||
1967 !IS_GFX_DEVICE(pdev))
1968 continue;
1969 printk(KERN_INFO "IOMMU: gfx device %s 1-1 mapping\n",
1970 pci_name(pdev));
1971 ret = iommu_prepare_with_active_regions(pdev);
1972 if (ret)
1973 printk(KERN_ERR "IOMMU: mapping reserved region failed\n");
1974 }
1975}
1976#else /* !CONFIG_DMAR_GFX_WA */
1977static inline void iommu_prepare_gfx_mapping(void)
1978{
1979 return;
1980}
1981#endif
1982
1983#ifdef CONFIG_DMAR_FLOPPY_WA 1921#ifdef CONFIG_DMAR_FLOPPY_WA
1984static inline void iommu_prepare_isa(void) 1922static inline void iommu_prepare_isa(void)
1985{ 1923{
@@ -1990,12 +1928,12 @@ static inline void iommu_prepare_isa(void)
1990 if (!pdev) 1928 if (!pdev)
1991 return; 1929 return;
1992 1930
1993 printk(KERN_INFO "IOMMU: Prepare 0-16M unity mapping for LPC\n"); 1931 printk(KERN_INFO "IOMMU: Prepare 0-16MiB unity mapping for LPC\n");
1994 ret = iommu_prepare_identity_map(pdev, 0, 16*1024*1024); 1932 ret = iommu_prepare_identity_map(pdev, 0, 16*1024*1024);
1995 1933
1996 if (ret) 1934 if (ret)
1997 printk(KERN_ERR "IOMMU: Failed to create 0-64M identity map, " 1935 printk(KERN_ERR "IOMMU: Failed to create 0-16MiB identity map; "
1998 "floppy might not work\n"); 1936 "floppy might not work\n");
1999 1937
2000} 1938}
2001#else 1939#else
@@ -2023,16 +1961,30 @@ static int __init init_context_pass_through(void)
2023} 1961}
2024 1962
2025static int md_domain_init(struct dmar_domain *domain, int guest_width); 1963static int md_domain_init(struct dmar_domain *domain, int guest_width);
1964
1965static int __init si_domain_work_fn(unsigned long start_pfn,
1966 unsigned long end_pfn, void *datax)
1967{
1968 int *ret = datax;
1969
1970 *ret = iommu_domain_identity_map(si_domain,
1971 (uint64_t)start_pfn << PAGE_SHIFT,
1972 (uint64_t)end_pfn << PAGE_SHIFT);
1973 return *ret;
1974
1975}
1976
2026static int si_domain_init(void) 1977static int si_domain_init(void)
2027{ 1978{
2028 struct dmar_drhd_unit *drhd; 1979 struct dmar_drhd_unit *drhd;
2029 struct intel_iommu *iommu; 1980 struct intel_iommu *iommu;
2030 int ret = 0; 1981 int nid, ret = 0;
2031 1982
2032 si_domain = alloc_domain(); 1983 si_domain = alloc_domain();
2033 if (!si_domain) 1984 if (!si_domain)
2034 return -EFAULT; 1985 return -EFAULT;
2035 1986
1987 pr_debug("Identity mapping domain is domain %d\n", si_domain->id);
2036 1988
2037 for_each_active_iommu(iommu, drhd) { 1989 for_each_active_iommu(iommu, drhd) {
2038 ret = iommu_attach_domain(si_domain, iommu); 1990 ret = iommu_attach_domain(si_domain, iommu);
@@ -2049,6 +2001,12 @@ static int si_domain_init(void)
2049 2001
2050 si_domain->flags = DOMAIN_FLAG_STATIC_IDENTITY; 2002 si_domain->flags = DOMAIN_FLAG_STATIC_IDENTITY;
2051 2003
2004 for_each_online_node(nid) {
2005 work_with_active_regions(nid, si_domain_work_fn, &ret);
2006 if (ret)
2007 return ret;
2008 }
2009
2052 return 0; 2010 return 0;
2053} 2011}
2054 2012
@@ -2102,13 +2060,14 @@ static int iommu_prepare_static_identity_mapping(void)
2102 if (ret) 2060 if (ret)
2103 return -EFAULT; 2061 return -EFAULT;
2104 2062
2105 printk(KERN_INFO "IOMMU: Setting identity map:\n");
2106 for_each_pci_dev(pdev) { 2063 for_each_pci_dev(pdev) {
2107 ret = iommu_prepare_with_active_regions(pdev); 2064 printk(KERN_INFO "IOMMU: identity mapping for device %s\n",
2108 if (ret) { 2065 pci_name(pdev));
2109 printk(KERN_INFO "1:1 mapping to one domain failed.\n"); 2066
2110 return -EFAULT; 2067 ret = domain_context_mapping(si_domain, pdev,
2111 } 2068 CONTEXT_TT_MULTI_LEVEL);
2069 if (ret)
2070 return ret;
2112 ret = domain_add_dev_info(si_domain, pdev); 2071 ret = domain_add_dev_info(si_domain, pdev);
2113 if (ret) 2072 if (ret)
2114 return ret; 2073 return ret;
@@ -2299,8 +2258,6 @@ int __init init_dmars(void)
2299 } 2258 }
2300 } 2259 }
2301 2260
2302 iommu_prepare_gfx_mapping();
2303
2304 iommu_prepare_isa(); 2261 iommu_prepare_isa();
2305 } 2262 }
2306 2263