Commit c7ab48d2acaf959e4d59c3f55d12fdb7ca9afd7c

Authored by David Woodhouse
1 parent b213203e47

intel-iommu: Clean up identity mapping code, remove CONFIG_DMAR_GFX_WA

There's no need for the GFX workaround now we have 'iommu=pt' for the
cases where people really care about performance. There's no need to
have a special case for just one type of device.

This also speeds up the iommu=pt path and reduces memory usage by
setting up the si_domain _once_ and then using it for all devices,
rather than giving each device its own private page tables.

Signed-off-by: David Woodhouse <David.Woodhouse@intel.com>

Showing 2 changed files with 34 additions and 88 deletions Side-by-side Diff

... ... @@ -1913,25 +1913,14 @@
1913 1913 recommended you say N here while the DMAR code remains
1914 1914 experimental.
1915 1915  
1916   -config 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   -
1927 1916 config DMAR_FLOPPY_WA
1928 1917 def_bool y
1929 1918 depends on DMAR
1930 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 1921 thereby failing to work when IOMMU is enabled. This
1933 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  
1936 1925 config INTR_REMAP
1937 1926 bool "Support for Interrupt Remapping (EXPERIMENTAL)"
drivers/pci/intel-iommu.c
... ... @@ -1889,11 +1889,7 @@
1889 1889 "IOMMU: Setting identity map for device %s [0x%Lx - 0x%Lx]\n",
1890 1890 pci_name(pdev), start, end);
1891 1891  
1892   - if (iommu_identity_mapping)
1893   - domain = si_domain;
1894   - else
1895   - /* page table init */
1896   - domain = get_domain_for_dev(pdev, DEFAULT_DOMAIN_ADDRESS_WIDTH);
  1892 + domain = get_domain_for_dev(pdev, DEFAULT_DOMAIN_ADDRESS_WIDTH);
1897 1893 if (!domain)
1898 1894 return -ENOMEM;
1899 1895  
... ... @@ -1922,64 +1918,6 @@
1922 1918 rmrr->end_address + 1);
1923 1919 }
1924 1920  
1925   -struct iommu_prepare_data {
1926   - struct pci_dev *pdev;
1927   - int ret;
1928   -};
1929   -
1930   -static 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   -
1943   -static 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
1960   -static 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 */
1977   -static inline void iommu_prepare_gfx_mapping(void)
1978   -{
1979   - return;
1980   -}
1981   -#endif
1982   -
1983 1921 #ifdef CONFIG_DMAR_FLOPPY_WA
1984 1922 static inline void iommu_prepare_isa(void)
1985 1923 {
1986 1924  
... ... @@ -1990,12 +1928,12 @@
1990 1928 if (!pdev)
1991 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 1932 ret = iommu_prepare_identity_map(pdev, 0, 16*1024*1024);
1995 1933  
1996 1934 if (ret)
1997   - printk(KERN_ERR "IOMMU: Failed to create 0-64M identity map, "
1998   - "floppy might not work\n");
  1935 + printk(KERN_ERR "IOMMU: Failed to create 0-16MiB identity map; "
  1936 + "floppy might not work\n");
1999 1937  
2000 1938 }
2001 1939 #else
2002 1940  
2003 1941  
... ... @@ -2023,16 +1961,30 @@
2023 1961 }
2024 1962  
2025 1963 static int md_domain_init(struct dmar_domain *domain, int guest_width);
  1964 +
  1965 +static 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 +
2026 1977 static int si_domain_init(void)
2027 1978 {
2028 1979 struct dmar_drhd_unit *drhd;
2029 1980 struct intel_iommu *iommu;
2030   - int ret = 0;
  1981 + int nid, ret = 0;
2031 1982  
2032 1983 si_domain = alloc_domain();
2033 1984 if (!si_domain)
2034 1985 return -EFAULT;
2035 1986  
  1987 + pr_debug("Identity mapping domain is domain %d\n", si_domain->id);
2036 1988  
2037 1989 for_each_active_iommu(iommu, drhd) {
2038 1990 ret = iommu_attach_domain(si_domain, iommu);
... ... @@ -2049,6 +2001,12 @@
2049 2001  
2050 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 2010 return 0;
2053 2011 }
2054 2012  
2055 2013  
... ... @@ -2102,13 +2060,14 @@
2102 2060 if (ret)
2103 2061 return -EFAULT;
2104 2062  
2105   - printk(KERN_INFO "IOMMU: Setting identity map:\n");
2106 2063 for_each_pci_dev(pdev) {
2107   - ret = iommu_prepare_with_active_regions(pdev);
2108   - if (ret) {
2109   - printk(KERN_INFO "1:1 mapping to one domain failed.\n");
2110   - return -EFAULT;
2111   - }
  2064 + printk(KERN_INFO "IOMMU: identity mapping for device %s\n",
  2065 + pci_name(pdev));
  2066 +
  2067 + ret = domain_context_mapping(si_domain, pdev,
  2068 + CONTEXT_TT_MULTI_LEVEL);
  2069 + if (ret)
  2070 + return ret;
2112 2071 ret = domain_add_dev_info(si_domain, pdev);
2113 2072 if (ret)
2114 2073 return ret;
... ... @@ -2298,8 +2257,6 @@
2298 2257 "IOMMU: mapping reserved region failed\n");
2299 2258 }
2300 2259 }
2301   -
2302   - iommu_prepare_gfx_mapping();
2303 2260  
2304 2261 iommu_prepare_isa();
2305 2262 }