Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'ntb-5.8' of git://github.com/jonmason/ntb

Pull NTB updates from Jon Mason:
"Intel Icelake NTB support, Intel driver bug fixes, and lots of bug
fixes for ntb tests"

* tag 'ntb-5.8' of git://github.com/jonmason/ntb:
NTB: ntb_test: Fix bug when counting remote files
NTB: perf: Fix race condition when run with ntb_test
NTB: perf: Fix support for hardware that doesn't have port numbers
NTB: perf: Don't require one more memory window than number of peers
NTB: ntb_pingpong: Choose doorbells based on port number
NTB: Fix the default port and peer numbers for legacy drivers
NTB: Revert the change to use the NTB device dev for DMA allocations
NTB: ntb_tool: reading the link file should not end in a NULL byte
ntb_perf: avoid false dma unmap of destination address
ntb_perf: increase sleep time from one milli sec to one sec
ntb_tool: pass correct struct device to dma_alloc_coherent
ntb_perf: pass correct struct device to dma_alloc_coherent
ntb: hw: remove the code that sets the DMA mask
NTB: correct ntb_peer_spad_addr and ntb_peer_spad_read comment typos
ntb: intel: fix static declaration
ntb: intel: add hw workaround for NTB BAR alignment
ntb: intel: Add Icelake (gen4) support for Intel NTB
NTB: Fix static check warning in perf_clear_test
include/ntb: Fix typo in ntb_unregister_device description

+751 -85
+2 -7
drivers/ntb/core.c
··· 214 214 case NTB_TOPO_B2B_DSD: 215 215 return NTB_PORT_SEC_DSD; 216 216 default: 217 - break; 217 + return 0; 218 218 } 219 - 220 - return -EINVAL; 221 219 } 222 220 EXPORT_SYMBOL(ntb_default_port_number); 223 221 ··· 238 240 case NTB_TOPO_B2B_DSD: 239 241 return NTB_PORT_PRI_USD; 240 242 default: 241 - break; 243 + return 0; 242 244 } 243 - 244 - return -EINVAL; 245 245 } 246 246 EXPORT_SYMBOL(ntb_default_peer_port_number); 247 247 ··· 311 315 bus_unregister(&ntb_bus); 312 316 } 313 317 module_exit(ntb_driver_exit); 314 -
-4
drivers/ntb/hw/amd/ntb_hw_amd.c
··· 1191 1191 goto err_dma_mask; 1192 1192 dev_warn(&pdev->dev, "Cannot DMA consistent highmem\n"); 1193 1193 } 1194 - rc = dma_coerce_mask_and_coherent(&ndev->ntb.dev, 1195 - dma_get_mask(&pdev->dev)); 1196 - if (rc) 1197 - goto err_dma_mask; 1198 1194 1199 1195 ndev->self_mmio = pci_iomap(pdev, 0, 0); 1200 1196 if (!ndev->self_mmio) {
-6
drivers/ntb/hw/idt/ntb_hw_idt.c
··· 2660 2660 dev_warn(&pdev->dev, 2661 2661 "Cannot set consistent DMA highmem bit mask\n"); 2662 2662 } 2663 - ret = dma_coerce_mask_and_coherent(&ndev->ntb.dev, 2664 - dma_get_mask(&pdev->dev)); 2665 - if (ret != 0) { 2666 - dev_err(&pdev->dev, "Failed to set NTB device DMA bit mask\n"); 2667 - return ret; 2668 - } 2669 2663 2670 2664 /* 2671 2665 * Enable the device advanced error reporting. It's not critical to
+1 -1
drivers/ntb/hw/intel/Makefile
··· 1 1 # SPDX-License-Identifier: GPL-2.0-only 2 2 obj-$(CONFIG_NTB_INTEL) += ntb_hw_intel.o 3 - ntb_hw_intel-y := ntb_hw_gen1.o ntb_hw_gen3.o 3 + ntb_hw_intel-y := ntb_hw_gen1.o ntb_hw_gen3.o ntb_hw_gen4.o
+26 -23
drivers/ntb/hw/intel/ntb_hw_gen1.c
··· 60 60 #include "ntb_hw_intel.h" 61 61 #include "ntb_hw_gen1.h" 62 62 #include "ntb_hw_gen3.h" 63 + #include "ntb_hw_gen4.h" 63 64 64 65 #define NTB_NAME "ntb_hw_intel" 65 66 #define NTB_DESC "Intel(R) PCI-E Non-Transparent Bridge Driver" ··· 763 762 return ndev_ntb_debugfs_read(filp, ubuf, count, offp); 764 763 else if (pdev_is_gen3(ndev->ntb.pdev)) 765 764 return ndev_ntb3_debugfs_read(filp, ubuf, count, offp); 765 + else if (pdev_is_gen4(ndev->ntb.pdev)) 766 + return ndev_ntb4_debugfs_read(filp, ubuf, count, offp); 766 767 767 768 return -ENXIO; 768 769 } ··· 1786 1783 goto err_dma_mask; 1787 1784 dev_warn(&pdev->dev, "Cannot DMA consistent highmem\n"); 1788 1785 } 1789 - rc = dma_coerce_mask_and_coherent(&ndev->ntb.dev, 1790 - dma_get_mask(&pdev->dev)); 1791 - if (rc) 1792 - goto err_dma_mask; 1793 1786 1794 1787 ndev->self_mmio = pci_iomap(pdev, 0, 0); 1795 1788 if (!ndev->self_mmio) { ··· 1857 1858 int rc, node; 1858 1859 1859 1860 node = dev_to_node(&pdev->dev); 1861 + ndev = kzalloc_node(sizeof(*ndev), GFP_KERNEL, node); 1862 + if (!ndev) { 1863 + rc = -ENOMEM; 1864 + goto err_ndev; 1865 + } 1866 + 1867 + ndev_init_struct(ndev, pdev); 1860 1868 1861 1869 if (pdev_is_gen1(pdev)) { 1862 - ndev = kzalloc_node(sizeof(*ndev), GFP_KERNEL, node); 1863 - if (!ndev) { 1864 - rc = -ENOMEM; 1865 - goto err_ndev; 1866 - } 1867 - 1868 - ndev_init_struct(ndev, pdev); 1869 - 1870 1870 rc = intel_ntb_init_pci(ndev, pdev); 1871 1871 if (rc) 1872 1872 goto err_init_pci; ··· 1873 1875 rc = xeon_init_dev(ndev); 1874 1876 if (rc) 1875 1877 goto err_init_dev; 1876 - 1877 1878 } else if (pdev_is_gen3(pdev)) { 1878 - ndev = kzalloc_node(sizeof(*ndev), GFP_KERNEL, node); 1879 - if (!ndev) { 1880 - rc = -ENOMEM; 1881 - goto err_ndev; 1882 - } 1883 - 1884 - ndev_init_struct(ndev, pdev); 1885 1879 ndev->ntb.ops = &intel_ntb3_ops; 1886 - 1887 1880 rc = intel_ntb_init_pci(ndev, pdev); 1888 1881 if (rc) 1889 1882 goto err_init_pci; ··· 1882 1893 rc = gen3_init_dev(ndev); 1883 1894 if (rc) 1884 1895 goto err_init_dev; 1896 + } else if (pdev_is_gen4(pdev)) { 1897 + ndev->ntb.ops = &intel_ntb4_ops; 1898 + rc = intel_ntb_init_pci(ndev, pdev); 1899 + if (rc) 1900 + goto err_init_pci; 1885 1901 1902 + rc = gen4_init_dev(ndev); 1903 + if (rc) 1904 + goto err_init_dev; 1886 1905 } else { 1887 1906 rc = -EINVAL; 1888 1907 goto err_ndev; ··· 1912 1915 1913 1916 err_register: 1914 1917 ndev_deinit_debugfs(ndev); 1915 - if (pdev_is_gen1(pdev) || pdev_is_gen3(pdev)) 1918 + if (pdev_is_gen1(pdev) || pdev_is_gen3(pdev) || pdev_is_gen4(pdev)) 1916 1919 xeon_deinit_dev(ndev); 1917 1920 err_init_dev: 1918 1921 intel_ntb_deinit_pci(ndev); ··· 1928 1931 1929 1932 ntb_unregister_device(&ndev->ntb); 1930 1933 ndev_deinit_debugfs(ndev); 1931 - if (pdev_is_gen1(pdev) || pdev_is_gen3(pdev)) 1934 + if (pdev_is_gen1(pdev) || pdev_is_gen3(pdev) || pdev_is_gen4(pdev)) 1932 1935 xeon_deinit_dev(ndev); 1933 1936 intel_ntb_deinit_pci(ndev); 1934 1937 kfree(ndev); ··· 2033 2036 }; 2034 2037 2035 2038 static const struct pci_device_id intel_ntb_pci_tbl[] = { 2039 + /* GEN1 */ 2036 2040 {PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_NTB_B2B_JSF)}, 2037 2041 {PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_NTB_B2B_SNB)}, 2038 2042 {PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_NTB_B2B_IVT)}, ··· 2049 2051 {PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_NTB_SS_IVT)}, 2050 2052 {PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_NTB_SS_HSX)}, 2051 2053 {PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_NTB_SS_BDX)}, 2054 + 2055 + /* GEN3 */ 2052 2056 {PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_NTB_B2B_SKX)}, 2057 + 2058 + /* GEN4 */ 2059 + {PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_NTB_B2B_ICX)}, 2053 2060 {0} 2054 2061 }; 2055 2062 MODULE_DEVICE_TABLE(pci, intel_ntb_pci_tbl);
+1
drivers/ntb/hw/intel/ntb_hw_gen1.h
··· 140 140 #define NTB_HWERR_SB01BASE_LOCKUP BIT_ULL(1) 141 141 #define NTB_HWERR_B2BDOORBELL_BIT14 BIT_ULL(2) 142 142 #define NTB_HWERR_MSIX_VECTOR32_BAD BIT_ULL(3) 143 + #define NTB_HWERR_BAR_ALIGN BIT_ULL(4) 143 144 144 145 extern struct intel_b2b_addr xeon_b2b_usd_addr; 145 146 extern struct intel_b2b_addr xeon_b2b_dsd_addr;
+6 -7
drivers/ntb/hw/intel/ntb_hw_gen3.c
··· 415 415 return ret; 416 416 } 417 417 418 - static int intel_ntb3_link_enable(struct ntb_dev *ntb, 419 - enum ntb_speed max_speed, 420 - enum ntb_width max_width) 418 + int intel_ntb3_link_enable(struct ntb_dev *ntb, enum ntb_speed max_speed, 419 + enum ntb_width max_width) 421 420 { 422 421 struct intel_ntb_dev *ndev; 423 422 u32 ntb_ctl; ··· 531 532 return 0; 532 533 } 533 534 534 - static int intel_ntb3_peer_db_addr(struct ntb_dev *ntb, phys_addr_t *db_addr, 535 + int intel_ntb3_peer_db_addr(struct ntb_dev *ntb, phys_addr_t *db_addr, 535 536 resource_size_t *db_size, 536 537 u64 *db_data, int db_bit) 537 538 { ··· 562 563 return 0; 563 564 } 564 565 565 - static int intel_ntb3_peer_db_set(struct ntb_dev *ntb, u64 db_bits) 566 + int intel_ntb3_peer_db_set(struct ntb_dev *ntb, u64 db_bits) 566 567 { 567 568 struct intel_ntb_dev *ndev = ntb_ndev(ntb); 568 569 int bit; ··· 580 581 return 0; 581 582 } 582 583 583 - static u64 intel_ntb3_db_read(struct ntb_dev *ntb) 584 + u64 intel_ntb3_db_read(struct ntb_dev *ntb) 584 585 { 585 586 struct intel_ntb_dev *ndev = ntb_ndev(ntb); 586 587 ··· 589 590 ndev->self_reg->db_clear); 590 591 } 591 592 592 - static int intel_ntb3_db_clear(struct ntb_dev *ntb, u64 db_bits) 593 + int intel_ntb3_db_clear(struct ntb_dev *ntb, u64 db_bits) 593 594 { 594 595 struct intel_ntb_dev *ndev = ntb_ndev(ntb); 595 596
+8
drivers/ntb/hw/intel/ntb_hw_gen3.h
··· 104 104 ssize_t ndev_ntb3_debugfs_read(struct file *filp, char __user *ubuf, 105 105 size_t count, loff_t *offp); 106 106 int gen3_init_dev(struct intel_ntb_dev *ndev); 107 + int intel_ntb3_link_enable(struct ntb_dev *ntb, enum ntb_speed max_speed, 108 + enum ntb_width max_width); 109 + u64 intel_ntb3_db_read(struct ntb_dev *ntb); 110 + int intel_ntb3_db_clear(struct ntb_dev *ntb, u64 db_bits); 111 + int intel_ntb3_peer_db_set(struct ntb_dev *ntb, u64 db_bits); 112 + int intel_ntb3_peer_db_addr(struct ntb_dev *ntb, phys_addr_t *db_addr, 113 + resource_size_t *db_size, 114 + u64 *db_data, int db_bit); 107 115 108 116 extern const struct ntb_dev_ops intel_ntb3_ops; 109 117
+552
drivers/ntb/hw/intel/ntb_hw_gen4.c
··· 1 + // SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause) 2 + /* Copyright(c) 2020 Intel Corporation. All rights reserved. */ 3 + #include <linux/debugfs.h> 4 + #include <linux/delay.h> 5 + #include <linux/init.h> 6 + #include <linux/interrupt.h> 7 + #include <linux/module.h> 8 + #include <linux/pci.h> 9 + #include <linux/random.h> 10 + #include <linux/slab.h> 11 + #include <linux/ntb.h> 12 + #include <linux/log2.h> 13 + 14 + #include "ntb_hw_intel.h" 15 + #include "ntb_hw_gen1.h" 16 + #include "ntb_hw_gen3.h" 17 + #include "ntb_hw_gen4.h" 18 + 19 + static int gen4_poll_link(struct intel_ntb_dev *ndev); 20 + static int gen4_link_is_up(struct intel_ntb_dev *ndev); 21 + 22 + static const struct intel_ntb_reg gen4_reg = { 23 + .poll_link = gen4_poll_link, 24 + .link_is_up = gen4_link_is_up, 25 + .db_ioread = gen3_db_ioread, 26 + .db_iowrite = gen3_db_iowrite, 27 + .db_size = sizeof(u32), 28 + .ntb_ctl = GEN4_NTBCNTL_OFFSET, 29 + .mw_bar = {2, 4}, 30 + }; 31 + 32 + static const struct intel_ntb_alt_reg gen4_pri_reg = { 33 + .db_clear = GEN4_IM_INT_STATUS_OFFSET, 34 + .db_mask = GEN4_IM_INT_DISABLE_OFFSET, 35 + .spad = GEN4_IM_SPAD_OFFSET, 36 + }; 37 + 38 + static const struct intel_ntb_xlat_reg gen4_sec_xlat = { 39 + .bar2_limit = GEN4_IM23XLMT_OFFSET, 40 + .bar2_xlat = GEN4_IM23XBASE_OFFSET, 41 + .bar2_idx = GEN4_IM23XBASEIDX_OFFSET, 42 + }; 43 + 44 + static const struct intel_ntb_alt_reg gen4_b2b_reg = { 45 + .db_bell = GEN4_IM_DOORBELL_OFFSET, 46 + .spad = GEN4_EM_SPAD_OFFSET, 47 + }; 48 + 49 + static int gen4_poll_link(struct intel_ntb_dev *ndev) 50 + { 51 + u16 reg_val; 52 + 53 + /* 54 + * We need to write to DLLSCS bit in the SLOTSTS before we 55 + * can clear the hardware link interrupt on ICX NTB. 56 + */ 57 + iowrite16(GEN4_SLOTSTS_DLLSCS, ndev->self_mmio + GEN4_SLOTSTS); 58 + ndev->reg->db_iowrite(ndev->db_link_mask, 59 + ndev->self_mmio + 60 + ndev->self_reg->db_clear); 61 + 62 + reg_val = ioread16(ndev->self_mmio + GEN4_LINK_STATUS_OFFSET); 63 + if (reg_val == ndev->lnk_sta) 64 + return 0; 65 + 66 + ndev->lnk_sta = reg_val; 67 + 68 + return 1; 69 + } 70 + 71 + static int gen4_link_is_up(struct intel_ntb_dev *ndev) 72 + { 73 + return NTB_LNK_STA_ACTIVE(ndev->lnk_sta); 74 + } 75 + 76 + static int gen4_init_isr(struct intel_ntb_dev *ndev) 77 + { 78 + int i; 79 + 80 + /* 81 + * The MSIX vectors and the interrupt status bits are not lined up 82 + * on Gen3 (Skylake) and Gen4. By default the link status bit is bit 83 + * 32, however it is by default MSIX vector0. We need to fixup to 84 + * line them up. The vectors at reset is 1-32,0. We need to reprogram 85 + * to 0-32. 86 + */ 87 + for (i = 0; i < GEN4_DB_MSIX_VECTOR_COUNT; i++) 88 + iowrite8(i, ndev->self_mmio + GEN4_INTVEC_OFFSET + i); 89 + 90 + return ndev_init_isr(ndev, GEN4_DB_MSIX_VECTOR_COUNT, 91 + GEN4_DB_MSIX_VECTOR_COUNT, 92 + GEN4_DB_MSIX_VECTOR_SHIFT, 93 + GEN4_DB_TOTAL_SHIFT); 94 + } 95 + 96 + static int gen4_setup_b2b_mw(struct intel_ntb_dev *ndev, 97 + const struct intel_b2b_addr *addr, 98 + const struct intel_b2b_addr *peer_addr) 99 + { 100 + struct pci_dev *pdev; 101 + void __iomem *mmio; 102 + phys_addr_t bar_addr; 103 + 104 + pdev = ndev->ntb.pdev; 105 + mmio = ndev->self_mmio; 106 + 107 + /* setup incoming bar limits == base addrs (zero length windows) */ 108 + bar_addr = addr->bar2_addr64; 109 + iowrite64(bar_addr, mmio + GEN4_IM23XLMT_OFFSET); 110 + bar_addr = ioread64(mmio + GEN4_IM23XLMT_OFFSET); 111 + dev_dbg(&pdev->dev, "IM23XLMT %#018llx\n", bar_addr); 112 + 113 + bar_addr = addr->bar4_addr64; 114 + iowrite64(bar_addr, mmio + GEN4_IM45XLMT_OFFSET); 115 + bar_addr = ioread64(mmio + GEN4_IM45XLMT_OFFSET); 116 + dev_dbg(&pdev->dev, "IM45XLMT %#018llx\n", bar_addr); 117 + 118 + /* zero incoming translation addrs */ 119 + iowrite64(0, mmio + GEN4_IM23XBASE_OFFSET); 120 + iowrite64(0, mmio + GEN4_IM45XBASE_OFFSET); 121 + 122 + ndev->peer_mmio = ndev->self_mmio; 123 + 124 + return 0; 125 + } 126 + 127 + static int gen4_init_ntb(struct intel_ntb_dev *ndev) 128 + { 129 + int rc; 130 + 131 + 132 + ndev->mw_count = XEON_MW_COUNT; 133 + ndev->spad_count = GEN4_SPAD_COUNT; 134 + ndev->db_count = GEN4_DB_COUNT; 135 + ndev->db_link_mask = GEN4_DB_LINK_BIT; 136 + 137 + ndev->self_reg = &gen4_pri_reg; 138 + ndev->xlat_reg = &gen4_sec_xlat; 139 + ndev->peer_reg = &gen4_b2b_reg; 140 + 141 + if (ndev->ntb.topo == NTB_TOPO_B2B_USD) 142 + rc = gen4_setup_b2b_mw(ndev, &xeon_b2b_dsd_addr, 143 + &xeon_b2b_usd_addr); 144 + else 145 + rc = gen4_setup_b2b_mw(ndev, &xeon_b2b_usd_addr, 146 + &xeon_b2b_dsd_addr); 147 + if (rc) 148 + return rc; 149 + 150 + ndev->db_valid_mask = BIT_ULL(ndev->db_count) - 1; 151 + 152 + ndev->reg->db_iowrite(ndev->db_valid_mask, 153 + ndev->self_mmio + 154 + ndev->self_reg->db_mask); 155 + 156 + return 0; 157 + } 158 + 159 + static enum ntb_topo gen4_ppd_topo(struct intel_ntb_dev *ndev, u32 ppd) 160 + { 161 + switch (ppd & GEN4_PPD_TOPO_MASK) { 162 + case GEN4_PPD_TOPO_B2B_USD: 163 + return NTB_TOPO_B2B_USD; 164 + case GEN4_PPD_TOPO_B2B_DSD: 165 + return NTB_TOPO_B2B_DSD; 166 + } 167 + 168 + return NTB_TOPO_NONE; 169 + } 170 + 171 + int gen4_init_dev(struct intel_ntb_dev *ndev) 172 + { 173 + struct pci_dev *pdev = ndev->ntb.pdev; 174 + u32 ppd1/*, ppd0*/; 175 + u16 lnkctl; 176 + int rc; 177 + 178 + ndev->reg = &gen4_reg; 179 + 180 + if (pdev_is_ICX(pdev)) 181 + ndev->hwerr_flags |= NTB_HWERR_BAR_ALIGN; 182 + 183 + ppd1 = ioread32(ndev->self_mmio + GEN4_PPD1_OFFSET); 184 + ndev->ntb.topo = gen4_ppd_topo(ndev, ppd1); 185 + dev_dbg(&pdev->dev, "ppd %#x topo %s\n", ppd1, 186 + ntb_topo_string(ndev->ntb.topo)); 187 + if (ndev->ntb.topo == NTB_TOPO_NONE) 188 + return -EINVAL; 189 + 190 + rc = gen4_init_ntb(ndev); 191 + if (rc) 192 + return rc; 193 + 194 + /* init link setup */ 195 + lnkctl = ioread16(ndev->self_mmio + GEN4_LINK_CTRL_OFFSET); 196 + lnkctl |= GEN4_LINK_CTRL_LINK_DISABLE; 197 + iowrite16(lnkctl, ndev->self_mmio + GEN4_LINK_CTRL_OFFSET); 198 + 199 + return gen4_init_isr(ndev); 200 + } 201 + 202 + ssize_t ndev_ntb4_debugfs_read(struct file *filp, char __user *ubuf, 203 + size_t count, loff_t *offp) 204 + { 205 + struct intel_ntb_dev *ndev; 206 + void __iomem *mmio; 207 + char *buf; 208 + size_t buf_size; 209 + ssize_t ret, off; 210 + union { u64 v64; u32 v32; u16 v16; } u; 211 + 212 + ndev = filp->private_data; 213 + mmio = ndev->self_mmio; 214 + 215 + buf_size = min(count, 0x800ul); 216 + 217 + buf = kmalloc(buf_size, GFP_KERNEL); 218 + if (!buf) 219 + return -ENOMEM; 220 + 221 + off = 0; 222 + 223 + off += scnprintf(buf + off, buf_size - off, 224 + "NTB Device Information:\n"); 225 + 226 + off += scnprintf(buf + off, buf_size - off, 227 + "Connection Topology -\t%s\n", 228 + ntb_topo_string(ndev->ntb.topo)); 229 + 230 + off += scnprintf(buf + off, buf_size - off, 231 + "NTB CTL -\t\t%#06x\n", ndev->ntb_ctl); 232 + off += scnprintf(buf + off, buf_size - off, 233 + "LNK STA (cached) -\t\t%#06x\n", ndev->lnk_sta); 234 + 235 + if (!ndev->reg->link_is_up(ndev)) 236 + off += scnprintf(buf + off, buf_size - off, 237 + "Link Status -\t\tDown\n"); 238 + else { 239 + off += scnprintf(buf + off, buf_size - off, 240 + "Link Status -\t\tUp\n"); 241 + off += scnprintf(buf + off, buf_size - off, 242 + "Link Speed -\t\tPCI-E Gen %u\n", 243 + NTB_LNK_STA_SPEED(ndev->lnk_sta)); 244 + off += scnprintf(buf + off, buf_size - off, 245 + "Link Width -\t\tx%u\n", 246 + NTB_LNK_STA_WIDTH(ndev->lnk_sta)); 247 + } 248 + 249 + off += scnprintf(buf + off, buf_size - off, 250 + "Memory Window Count -\t%u\n", ndev->mw_count); 251 + off += scnprintf(buf + off, buf_size - off, 252 + "Scratchpad Count -\t%u\n", ndev->spad_count); 253 + off += scnprintf(buf + off, buf_size - off, 254 + "Doorbell Count -\t%u\n", ndev->db_count); 255 + off += scnprintf(buf + off, buf_size - off, 256 + "Doorbell Vector Count -\t%u\n", ndev->db_vec_count); 257 + off += scnprintf(buf + off, buf_size - off, 258 + "Doorbell Vector Shift -\t%u\n", ndev->db_vec_shift); 259 + 260 + off += scnprintf(buf + off, buf_size - off, 261 + "Doorbell Valid Mask -\t%#llx\n", ndev->db_valid_mask); 262 + off += scnprintf(buf + off, buf_size - off, 263 + "Doorbell Link Mask -\t%#llx\n", ndev->db_link_mask); 264 + off += scnprintf(buf + off, buf_size - off, 265 + "Doorbell Mask Cached -\t%#llx\n", ndev->db_mask); 266 + 267 + u.v64 = ndev_db_read(ndev, mmio + ndev->self_reg->db_mask); 268 + off += scnprintf(buf + off, buf_size - off, 269 + "Doorbell Mask -\t\t%#llx\n", u.v64); 270 + 271 + off += scnprintf(buf + off, buf_size - off, 272 + "\nNTB Incoming XLAT:\n"); 273 + 274 + u.v64 = ioread64(mmio + GEN4_IM23XBASE_OFFSET); 275 + off += scnprintf(buf + off, buf_size - off, 276 + "IM23XBASE -\t\t%#018llx\n", u.v64); 277 + 278 + u.v64 = ioread64(mmio + GEN4_IM45XBASE_OFFSET); 279 + off += scnprintf(buf + off, buf_size - off, 280 + "IM45XBASE -\t\t%#018llx\n", u.v64); 281 + 282 + u.v64 = ioread64(mmio + GEN4_IM23XLMT_OFFSET); 283 + off += scnprintf(buf + off, buf_size - off, 284 + "IM23XLMT -\t\t\t%#018llx\n", u.v64); 285 + 286 + u.v64 = ioread64(mmio + GEN4_IM45XLMT_OFFSET); 287 + off += scnprintf(buf + off, buf_size - off, 288 + "IM45XLMT -\t\t\t%#018llx\n", u.v64); 289 + 290 + off += scnprintf(buf + off, buf_size - off, 291 + "\nNTB Statistics:\n"); 292 + 293 + off += scnprintf(buf + off, buf_size - off, 294 + "\nNTB Hardware Errors:\n"); 295 + 296 + if (!pci_read_config_word(ndev->ntb.pdev, 297 + GEN4_DEVSTS_OFFSET, &u.v16)) 298 + off += scnprintf(buf + off, buf_size - off, 299 + "DEVSTS -\t\t%#06x\n", u.v16); 300 + 301 + u.v16 = ioread16(mmio + GEN4_LINK_STATUS_OFFSET); 302 + off += scnprintf(buf + off, buf_size - off, 303 + "LNKSTS -\t\t%#06x\n", u.v16); 304 + 305 + if (!pci_read_config_dword(ndev->ntb.pdev, 306 + GEN4_UNCERRSTS_OFFSET, &u.v32)) 307 + off += scnprintf(buf + off, buf_size - off, 308 + "UNCERRSTS -\t\t%#06x\n", u.v32); 309 + 310 + if (!pci_read_config_dword(ndev->ntb.pdev, 311 + GEN4_CORERRSTS_OFFSET, &u.v32)) 312 + off += scnprintf(buf + off, buf_size - off, 313 + "CORERRSTS -\t\t%#06x\n", u.v32); 314 + 315 + ret = simple_read_from_buffer(ubuf, count, offp, buf, off); 316 + kfree(buf); 317 + return ret; 318 + } 319 + 320 + static int intel_ntb4_mw_set_trans(struct ntb_dev *ntb, int pidx, int idx, 321 + dma_addr_t addr, resource_size_t size) 322 + { 323 + struct intel_ntb_dev *ndev = ntb_ndev(ntb); 324 + unsigned long xlat_reg, limit_reg, idx_reg; 325 + unsigned short base_idx, reg_val16; 326 + resource_size_t bar_size, mw_size; 327 + void __iomem *mmio; 328 + u64 base, limit, reg_val; 329 + int bar; 330 + 331 + if (pidx != NTB_DEF_PEER_IDX) 332 + return -EINVAL; 333 + 334 + if (idx >= ndev->b2b_idx && !ndev->b2b_off) 335 + idx += 1; 336 + 337 + bar = ndev_mw_to_bar(ndev, idx); 338 + if (bar < 0) 339 + return bar; 340 + 341 + bar_size = pci_resource_len(ndev->ntb.pdev, bar); 342 + 343 + if (idx == ndev->b2b_idx) 344 + mw_size = bar_size - ndev->b2b_off; 345 + else 346 + mw_size = bar_size; 347 + 348 + if (ndev->hwerr_flags & NTB_HWERR_BAR_ALIGN) { 349 + /* hardware requires that addr is aligned to bar size */ 350 + if (addr & (bar_size - 1)) 351 + return -EINVAL; 352 + } else { 353 + if (addr & (PAGE_SIZE - 1)) 354 + return -EINVAL; 355 + } 356 + 357 + /* make sure the range fits in the usable mw size */ 358 + if (size > mw_size) 359 + return -EINVAL; 360 + 361 + mmio = ndev->self_mmio; 362 + xlat_reg = ndev->xlat_reg->bar2_xlat + (idx * 0x10); 363 + limit_reg = ndev->xlat_reg->bar2_limit + (idx * 0x10); 364 + base = pci_resource_start(ndev->ntb.pdev, bar); 365 + 366 + /* Set the limit if supported, if size is not mw_size */ 367 + if (limit_reg && size != mw_size) { 368 + limit = base + size; 369 + base_idx = __ilog2_u64(size); 370 + } else { 371 + limit = base + mw_size; 372 + base_idx = __ilog2_u64(mw_size); 373 + } 374 + 375 + 376 + /* set and verify setting the translation address */ 377 + iowrite64(addr, mmio + xlat_reg); 378 + reg_val = ioread64(mmio + xlat_reg); 379 + if (reg_val != addr) { 380 + iowrite64(0, mmio + xlat_reg); 381 + return -EIO; 382 + } 383 + 384 + dev_dbg(&ntb->pdev->dev, "BAR %d IMXBASE: %#Lx\n", bar, reg_val); 385 + 386 + /* set and verify setting the limit */ 387 + iowrite64(limit, mmio + limit_reg); 388 + reg_val = ioread64(mmio + limit_reg); 389 + if (reg_val != limit) { 390 + iowrite64(base, mmio + limit_reg); 391 + iowrite64(0, mmio + xlat_reg); 392 + return -EIO; 393 + } 394 + 395 + dev_dbg(&ntb->pdev->dev, "BAR %d IMXLMT: %#Lx\n", bar, reg_val); 396 + 397 + if (ndev->hwerr_flags & NTB_HWERR_BAR_ALIGN) { 398 + idx_reg = ndev->xlat_reg->bar2_idx + (idx * 0x2); 399 + iowrite16(base_idx, mmio + idx_reg); 400 + reg_val16 = ioread16(mmio + idx_reg); 401 + if (reg_val16 != base_idx) { 402 + iowrite64(base, mmio + limit_reg); 403 + iowrite64(0, mmio + xlat_reg); 404 + iowrite16(0, mmio + idx_reg); 405 + return -EIO; 406 + } 407 + dev_dbg(&ntb->pdev->dev, "BAR %d IMBASEIDX: %#x\n", bar, reg_val16); 408 + } 409 + 410 + 411 + return 0; 412 + } 413 + 414 + static int intel_ntb4_link_enable(struct ntb_dev *ntb, 415 + enum ntb_speed max_speed, enum ntb_width max_width) 416 + { 417 + struct intel_ntb_dev *ndev; 418 + u32 ntb_ctl, ppd0; 419 + u16 lnkctl; 420 + 421 + ndev = container_of(ntb, struct intel_ntb_dev, ntb); 422 + 423 + dev_dbg(&ntb->pdev->dev, 424 + "Enabling link with max_speed %d max_width %d\n", 425 + max_speed, max_width); 426 + 427 + if (max_speed != NTB_SPEED_AUTO) 428 + dev_dbg(&ntb->pdev->dev, 429 + "ignoring max_speed %d\n", max_speed); 430 + if (max_width != NTB_WIDTH_AUTO) 431 + dev_dbg(&ntb->pdev->dev, 432 + "ignoring max_width %d\n", max_width); 433 + 434 + ntb_ctl = NTB_CTL_E2I_BAR23_SNOOP | NTB_CTL_I2E_BAR23_SNOOP; 435 + ntb_ctl |= NTB_CTL_E2I_BAR45_SNOOP | NTB_CTL_I2E_BAR45_SNOOP; 436 + iowrite32(ntb_ctl, ndev->self_mmio + ndev->reg->ntb_ctl); 437 + 438 + lnkctl = ioread16(ndev->self_mmio + GEN4_LINK_CTRL_OFFSET); 439 + lnkctl &= ~GEN4_LINK_CTRL_LINK_DISABLE; 440 + iowrite16(lnkctl, ndev->self_mmio + GEN4_LINK_CTRL_OFFSET); 441 + 442 + /* start link training in PPD0 */ 443 + ppd0 = ioread32(ndev->self_mmio + GEN4_PPD0_OFFSET); 444 + ppd0 |= GEN4_PPD_LINKTRN; 445 + iowrite32(ppd0, ndev->self_mmio + GEN4_PPD0_OFFSET); 446 + 447 + /* make sure link training has started */ 448 + ppd0 = ioread32(ndev->self_mmio + GEN4_PPD0_OFFSET); 449 + if (!(ppd0 & GEN4_PPD_LINKTRN)) { 450 + dev_warn(&ntb->pdev->dev, "Link is not training\n"); 451 + return -ENXIO; 452 + } 453 + 454 + ndev->dev_up = 1; 455 + 456 + return 0; 457 + } 458 + 459 + static int intel_ntb4_link_disable(struct ntb_dev *ntb) 460 + { 461 + struct intel_ntb_dev *ndev; 462 + u32 ntb_cntl; 463 + u16 lnkctl; 464 + 465 + ndev = container_of(ntb, struct intel_ntb_dev, ntb); 466 + 467 + dev_dbg(&ntb->pdev->dev, "Disabling link\n"); 468 + 469 + /* clear the snoop bits */ 470 + ntb_cntl = ioread32(ndev->self_mmio + ndev->reg->ntb_ctl); 471 + ntb_cntl &= ~(NTB_CTL_E2I_BAR23_SNOOP | NTB_CTL_I2E_BAR23_SNOOP); 472 + ntb_cntl &= ~(NTB_CTL_E2I_BAR45_SNOOP | NTB_CTL_I2E_BAR45_SNOOP); 473 + iowrite32(ntb_cntl, ndev->self_mmio + ndev->reg->ntb_ctl); 474 + 475 + lnkctl = ioread16(ndev->self_mmio + GEN4_LINK_CTRL_OFFSET); 476 + lnkctl |= GEN4_LINK_CTRL_LINK_DISABLE; 477 + iowrite16(lnkctl, ndev->self_mmio + GEN4_LINK_CTRL_OFFSET); 478 + 479 + ndev->dev_up = 0; 480 + 481 + return 0; 482 + } 483 + 484 + static int intel_ntb4_mw_get_align(struct ntb_dev *ntb, int pidx, int idx, 485 + resource_size_t *addr_align, 486 + resource_size_t *size_align, 487 + resource_size_t *size_max) 488 + { 489 + struct intel_ntb_dev *ndev = ntb_ndev(ntb); 490 + resource_size_t bar_size, mw_size; 491 + int bar; 492 + 493 + if (pidx != NTB_DEF_PEER_IDX) 494 + return -EINVAL; 495 + 496 + if (idx >= ndev->b2b_idx && !ndev->b2b_off) 497 + idx += 1; 498 + 499 + bar = ndev_mw_to_bar(ndev, idx); 500 + if (bar < 0) 501 + return bar; 502 + 503 + bar_size = pci_resource_len(ndev->ntb.pdev, bar); 504 + 505 + if (idx == ndev->b2b_idx) 506 + mw_size = bar_size - ndev->b2b_off; 507 + else 508 + mw_size = bar_size; 509 + 510 + if (addr_align) { 511 + if (ndev->hwerr_flags & NTB_HWERR_BAR_ALIGN) 512 + *addr_align = pci_resource_len(ndev->ntb.pdev, bar); 513 + else 514 + *addr_align = PAGE_SIZE; 515 + } 516 + 517 + if (size_align) 518 + *size_align = 1; 519 + 520 + if (size_max) 521 + *size_max = mw_size; 522 + 523 + return 0; 524 + } 525 + 526 + const struct ntb_dev_ops intel_ntb4_ops = { 527 + .mw_count = intel_ntb_mw_count, 528 + .mw_get_align = intel_ntb4_mw_get_align, 529 + .mw_set_trans = intel_ntb4_mw_set_trans, 530 + .peer_mw_count = intel_ntb_peer_mw_count, 531 + .peer_mw_get_addr = intel_ntb_peer_mw_get_addr, 532 + .link_is_up = intel_ntb_link_is_up, 533 + .link_enable = intel_ntb4_link_enable, 534 + .link_disable = intel_ntb4_link_disable, 535 + .db_valid_mask = intel_ntb_db_valid_mask, 536 + .db_vector_count = intel_ntb_db_vector_count, 537 + .db_vector_mask = intel_ntb_db_vector_mask, 538 + .db_read = intel_ntb3_db_read, 539 + .db_clear = intel_ntb3_db_clear, 540 + .db_set_mask = intel_ntb_db_set_mask, 541 + .db_clear_mask = intel_ntb_db_clear_mask, 542 + .peer_db_addr = intel_ntb3_peer_db_addr, 543 + .peer_db_set = intel_ntb3_peer_db_set, 544 + .spad_is_unsafe = intel_ntb_spad_is_unsafe, 545 + .spad_count = intel_ntb_spad_count, 546 + .spad_read = intel_ntb_spad_read, 547 + .spad_write = intel_ntb_spad_write, 548 + .peer_spad_addr = intel_ntb_peer_spad_addr, 549 + .peer_spad_read = intel_ntb_peer_spad_read, 550 + .peer_spad_write = intel_ntb_peer_spad_write, 551 + }; 552 +
+100
drivers/ntb/hw/intel/ntb_hw_gen4.h
··· 1 + /* SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause) */ 2 + /* Copyright(c) 2020 Intel Corporation. All rights reserved. */ 3 + #ifndef _NTB_INTEL_GEN4_H_ 4 + #define _NTB_INTEL_GEN4_H_ 5 + 6 + #include "ntb_hw_intel.h" 7 + 8 + /* Supported PCI device revision range for ICX */ 9 + #define PCI_DEVICE_REVISION_ICX_MIN 0x2 10 + #define PCI_DEVICE_REVISION_ICX_MAX 0xF 11 + 12 + /* Intel Gen4 NTB hardware */ 13 + /* PCIe config space */ 14 + #define GEN4_IMBAR23SZ_OFFSET 0x00c4 15 + #define GEN4_IMBAR45SZ_OFFSET 0x00c5 16 + #define GEN4_EMBAR23SZ_OFFSET 0x00c6 17 + #define GEN4_EMBAR45SZ_OFFSET 0x00c7 18 + #define GEN4_DEVCTRL_OFFSET 0x0048 19 + #define GEN4_DEVSTS_OFFSET 0x004a 20 + #define GEN4_UNCERRSTS_OFFSET 0x0104 21 + #define GEN4_CORERRSTS_OFFSET 0x0110 22 + 23 + /* BAR0 MMIO */ 24 + #define GEN4_NTBCNTL_OFFSET 0x0000 25 + #define GEN4_IM23XBASE_OFFSET 0x0010 /* IMBAR1XBASE */ 26 + #define GEN4_IM23XLMT_OFFSET 0x0018 /* IMBAR1XLMT */ 27 + #define GEN4_IM45XBASE_OFFSET 0x0020 /* IMBAR2XBASE */ 28 + #define GEN4_IM45XLMT_OFFSET 0x0028 /* IMBAR2XLMT */ 29 + #define GEN4_IM_INT_STATUS_OFFSET 0x0040 30 + #define GEN4_IM_INT_DISABLE_OFFSET 0x0048 31 + #define GEN4_INTVEC_OFFSET 0x0050 /* 0-32 vecs */ 32 + #define GEN4_IM23XBASEIDX_OFFSET 0x0074 33 + #define GEN4_IM45XBASEIDX_OFFSET 0x0076 34 + #define GEN4_IM_SPAD_OFFSET 0x0080 /* 0-15 SPADs */ 35 + #define GEN4_IM_SPAD_SEM_OFFSET 0x00c0 /* SPAD hw semaphore */ 36 + #define GEN4_IM_SPAD_STICKY_OFFSET 0x00c4 /* sticky SPAD */ 37 + #define GEN4_IM_DOORBELL_OFFSET 0x0100 /* 0-31 doorbells */ 38 + #define GEN4_EM_SPAD_OFFSET 0x8080 39 + /* note, link status is now in MMIO and not config space for NTB */ 40 + #define GEN4_LINK_CTRL_OFFSET 0xb050 41 + #define GEN4_LINK_STATUS_OFFSET 0xb052 42 + #define GEN4_PPD0_OFFSET 0xb0d4 43 + #define GEN4_PPD1_OFFSET 0xb4c0 44 + #define GEN4_LTSSMSTATEJMP 0xf040 45 + 46 + #define GEN4_PPD_CLEAR_TRN 0x0001 47 + #define GEN4_PPD_LINKTRN 0x0008 48 + #define GEN4_PPD_CONN_MASK 0x0300 49 + #define GEN4_PPD_CONN_B2B 0x0200 50 + #define GEN4_PPD_DEV_MASK 0x1000 51 + #define GEN4_PPD_DEV_DSD 0x1000 52 + #define GEN4_PPD_DEV_USD 0x0000 53 + #define GEN4_LINK_CTRL_LINK_DISABLE 0x0010 54 + 55 + #define GEN4_SLOTSTS 0xb05a 56 + #define GEN4_SLOTSTS_DLLSCS 0x100 57 + 58 + #define GEN4_PPD_TOPO_MASK (GEN4_PPD_CONN_MASK | GEN4_PPD_DEV_MASK) 59 + #define GEN4_PPD_TOPO_B2B_USD (GEN4_PPD_CONN_B2B | GEN4_PPD_DEV_USD) 60 + #define GEN4_PPD_TOPO_B2B_DSD (GEN4_PPD_CONN_B2B | GEN4_PPD_DEV_DSD) 61 + 62 + #define GEN4_DB_COUNT 32 63 + #define GEN4_DB_LINK 32 64 + #define GEN4_DB_LINK_BIT BIT_ULL(GEN4_DB_LINK) 65 + #define GEN4_DB_MSIX_VECTOR_COUNT 33 66 + #define GEN4_DB_MSIX_VECTOR_SHIFT 1 67 + #define GEN4_DB_TOTAL_SHIFT 33 68 + #define GEN4_SPAD_COUNT 16 69 + 70 + #define NTB_CTL_E2I_BAR23_SNOOP 0x000004 71 + #define NTB_CTL_E2I_BAR23_NOSNOOP 0x000008 72 + #define NTB_CTL_I2E_BAR23_SNOOP 0x000010 73 + #define NTB_CTL_I2E_BAR23_NOSNOOP 0x000020 74 + #define NTB_CTL_E2I_BAR45_SNOOP 0x000040 75 + #define NTB_CTL_E2I_BAR45_NOSNOO 0x000080 76 + #define NTB_CTL_I2E_BAR45_SNOOP 0x000100 77 + #define NTB_CTL_I2E_BAR45_NOSNOOP 0x000200 78 + #define NTB_CTL_BUSNO_DIS_INC 0x000400 79 + #define NTB_CTL_LINK_DOWN 0x010000 80 + 81 + #define NTB_SJC_FORCEDETECT 0x000004 82 + 83 + ssize_t ndev_ntb4_debugfs_read(struct file *filp, char __user *ubuf, 84 + size_t count, loff_t *offp); 85 + int gen4_init_dev(struct intel_ntb_dev *ndev); 86 + ssize_t ndev_ntb4_debugfs_read(struct file *filp, char __user *ubuf, 87 + size_t count, loff_t *offp); 88 + 89 + extern const struct ntb_dev_ops intel_ntb4_ops; 90 + 91 + static inline int pdev_is_ICX(struct pci_dev *pdev) 92 + { 93 + if (pdev_is_gen4(pdev) && 94 + pdev->revision >= PCI_DEVICE_REVISION_ICX_MIN && 95 + pdev->revision <= PCI_DEVICE_REVISION_ICX_MAX) 96 + return 1; 97 + return 0; 98 + } 99 + 100 + #endif
+12
drivers/ntb/hw/intel/ntb_hw_intel.h
··· 72 72 #define PCI_DEVICE_ID_INTEL_NTB_PS_BDX 0x6F0E 73 73 #define PCI_DEVICE_ID_INTEL_NTB_SS_BDX 0x6F0F 74 74 #define PCI_DEVICE_ID_INTEL_NTB_B2B_SKX 0x201C 75 + #define PCI_DEVICE_ID_INTEL_NTB_B2B_ICX 0x347e 75 76 76 77 /* Ntb control and link status */ 77 78 #define NTB_CTL_CFG_LOCK BIT(0) ··· 121 120 unsigned long bar0_base; 122 121 unsigned long bar2_xlat; 123 122 unsigned long bar2_limit; 123 + unsigned short bar2_idx; 124 124 }; 125 125 126 126 struct intel_b2b_addr { ··· 184 182 185 183 struct dentry *debugfs_dir; 186 184 struct dentry *debugfs_info; 185 + 186 + /* gen4 entries */ 187 + int dev_up; 187 188 }; 188 189 189 190 #define ntb_ndev(__ntb) container_of(__ntb, struct intel_ntb_dev, ntb) ··· 224 219 return 0; 225 220 } 226 221 222 + static inline int pdev_is_gen4(struct pci_dev *pdev) 223 + { 224 + if (pdev->device == PCI_DEVICE_ID_INTEL_NTB_B2B_ICX) 225 + return 1; 226 + 227 + return 0; 228 + } 227 229 #endif
+29 -20
drivers/ntb/test/ntb_perf.c
··· 101 101 #define DMA_MDELAY 10 102 102 103 103 #define MSG_TRIES 1000 104 - #define MSG_UDELAY_LOW 1000 105 - #define MSG_UDELAY_HIGH 2000 104 + #define MSG_UDELAY_LOW 1000000 105 + #define MSG_UDELAY_HIGH 2000000 106 106 107 107 #define PERF_BUF_LEN 1024 108 108 ··· 159 159 /* NTB connection setup service */ 160 160 struct work_struct service; 161 161 unsigned long sts; 162 + 163 + struct completion init_comp; 162 164 }; 163 165 #define to_peer_service(__work) \ 164 166 container_of(__work, struct perf_peer, service) ··· 549 547 550 548 /* Initialization is finally done */ 551 549 set_bit(PERF_STS_DONE, &peer->sts); 550 + complete_all(&peer->init_comp); 552 551 553 552 return 0; 554 553 } ··· 560 557 return; 561 558 562 559 (void)ntb_mw_clear_trans(peer->perf->ntb, peer->pidx, peer->gidx); 563 - dma_free_coherent(&peer->perf->ntb->dev, peer->inbuf_size, 560 + dma_free_coherent(&peer->perf->ntb->pdev->dev, peer->inbuf_size, 564 561 peer->inbuf, peer->inbuf_xlat); 565 562 peer->inbuf = NULL; 566 563 } ··· 589 586 590 587 perf_free_inbuf(peer); 591 588 592 - peer->inbuf = dma_alloc_coherent(&perf->ntb->dev, peer->inbuf_size, 593 - &peer->inbuf_xlat, GFP_KERNEL); 589 + peer->inbuf = dma_alloc_coherent(&perf->ntb->pdev->dev, 590 + peer->inbuf_size, &peer->inbuf_xlat, 591 + GFP_KERNEL); 594 592 if (!peer->inbuf) { 595 593 dev_err(&perf->ntb->dev, "Failed to alloc inbuf of %pa\n", 596 594 &peer->inbuf_size); ··· 641 637 perf_setup_outbuf(peer); 642 638 643 639 if (test_and_clear_bit(PERF_CMD_CLEAR, &peer->sts)) { 640 + init_completion(&peer->init_comp); 644 641 clear_bit(PERF_STS_DONE, &peer->sts); 645 642 if (test_bit(0, &peer->perf->busy_flag) && 646 643 peer == peer->perf->test_peer) { ··· 658 653 { 659 654 u64 mask; 660 655 661 - if (ntb_peer_mw_count(perf->ntb) < perf->pcnt + 1) { 656 + if (ntb_peer_mw_count(perf->ntb) < perf->pcnt) { 662 657 dev_err(&perf->ntb->dev, "Not enough memory windows\n"); 663 658 return -EINVAL; 664 659 } ··· 808 803 dst_vaddr = dst; 809 804 dst_dma_addr = peer->dma_dst_addr + (dst_vaddr - vbase); 810 805 811 - unmap = dmaengine_get_unmap_data(dma_dev, 2, GFP_NOWAIT); 806 + unmap = dmaengine_get_unmap_data(dma_dev, 1, GFP_NOWAIT); 812 807 if (!unmap) 813 808 return -ENOMEM; 814 809 ··· 821 816 } 822 817 unmap->to_cnt = 1; 823 818 824 - unmap->addr[1] = dst_dma_addr; 825 - if (dma_mapping_error(dma_dev, unmap->addr[1])) { 826 - ret = -EIO; 827 - goto err_free_resource; 828 - } 829 - unmap->from_cnt = 1; 830 - 831 819 do { 832 - tx = dmaengine_prep_dma_memcpy(pthr->dma_chan, unmap->addr[1], 820 + tx = dmaengine_prep_dma_memcpy(pthr->dma_chan, dst_dma_addr, 833 821 unmap->addr[0], len, DMA_PREP_INTERRUPT | DMA_CTRL_ACK); 834 822 if (!tx) 835 823 msleep(DMA_MDELAY); ··· 1008 1010 pthr->perf->test_peer->dma_dst_addr, 1009 1011 pthr->perf->test_peer->outbuf_size, 1010 1012 DMA_FROM_DEVICE, 0); 1011 - if (pthr->dma_chan) 1012 - dma_release_channel(pthr->dma_chan); 1013 + 1014 + dma_release_channel(pthr->dma_chan); 1013 1015 1014 1016 no_dma_notify: 1015 1017 atomic_dec(&perf->tsync); ··· 1081 1083 struct perf_thread *pthr; 1082 1084 int tidx, ret; 1083 1085 1084 - if (!test_bit(PERF_STS_DONE, &peer->sts)) 1085 - return -ENOLINK; 1086 + ret = wait_for_completion_interruptible(&peer->init_comp); 1087 + if (ret < 0) 1088 + return ret; 1086 1089 1087 1090 if (test_and_set_bit_lock(0, &perf->busy_flag)) 1088 1091 return -EBUSY; ··· 1454 1455 peer->gidx = pidx; 1455 1456 } 1456 1457 INIT_WORK(&peer->service, perf_service_work); 1458 + init_completion(&peer->init_comp); 1457 1459 } 1458 1460 if (perf->gidx == -1) 1459 1461 perf->gidx = pidx; 1462 + 1463 + /* 1464 + * Hardware with only two ports may not have unique port 1465 + * numbers. In this case, the gidxs should all be zero. 1466 + */ 1467 + if (perf->pcnt == 1 && ntb_port_number(perf->ntb) == 0 && 1468 + ntb_peer_port_number(perf->ntb, 0) == 0) { 1469 + perf->gidx = 0; 1470 + perf->peers[0].gidx = 0; 1471 + } 1460 1472 1461 1473 for (pidx = 0; pidx < perf->pcnt; pidx++) { 1462 1474 ret = perf_setup_peer_mw(&perf->peers[pidx]); ··· 1564 1554 destroy_workqueue(perf_wq); 1565 1555 } 1566 1556 module_exit(perf_exit); 1567 -
+6 -8
drivers/ntb/test/ntb_pingpong.c
··· 121 121 link = ntb_link_is_up(pp->ntb, NULL, NULL); 122 122 123 123 /* Find next available peer */ 124 - if (link & pp->nmask) { 124 + if (link & pp->nmask) 125 125 pidx = __ffs64(link & pp->nmask); 126 - out_db = BIT_ULL(pidx + 1); 127 - } else if (link & pp->pmask) { 126 + else if (link & pp->pmask) 128 127 pidx = __ffs64(link & pp->pmask); 129 - out_db = BIT_ULL(pidx); 130 - } else { 128 + else 131 129 return -ENODEV; 132 - } 130 + 131 + out_db = BIT_ULL(ntb_peer_port_number(pp->ntb, pidx)); 133 132 134 133 spin_lock(&pp->lock); 135 134 pp->out_pidx = pidx; ··· 302 303 break; 303 304 } 304 305 305 - pp->in_db = BIT_ULL(pidx); 306 + pp->in_db = BIT_ULL(lport); 306 307 pp->pmask = GENMASK_ULL(pidx, 0) >> 1; 307 308 pp->nmask = GENMASK_ULL(pcnt - 1, pidx); 308 309 ··· 431 432 debugfs_remove_recursive(pp_dbgfs_topdir); 432 433 } 433 434 module_exit(pp_exit); 434 -
+4 -5
drivers/ntb/test/ntb_tool.c
··· 504 504 buf[1] = '\n'; 505 505 buf[2] = '\0'; 506 506 507 - return simple_read_from_buffer(ubuf, size, offp, buf, 3); 507 + return simple_read_from_buffer(ubuf, size, offp, buf, 2); 508 508 } 509 509 510 510 static TOOL_FOPS_RDWR(tool_peer_link_fops, ··· 590 590 inmw->size = min_t(resource_size_t, req_size, size); 591 591 inmw->size = round_up(inmw->size, addr_align); 592 592 inmw->size = round_up(inmw->size, size_align); 593 - inmw->mm_base = dma_alloc_coherent(&tc->ntb->dev, inmw->size, 593 + inmw->mm_base = dma_alloc_coherent(&tc->ntb->pdev->dev, inmw->size, 594 594 &inmw->dma_base, GFP_KERNEL); 595 595 if (!inmw->mm_base) 596 596 return -ENOMEM; ··· 612 612 return 0; 613 613 614 614 err_free_dma: 615 - dma_free_coherent(&tc->ntb->dev, inmw->size, inmw->mm_base, 615 + dma_free_coherent(&tc->ntb->pdev->dev, inmw->size, inmw->mm_base, 616 616 inmw->dma_base); 617 617 inmw->mm_base = NULL; 618 618 inmw->dma_base = 0; ··· 629 629 630 630 if (inmw->mm_base != NULL) { 631 631 ntb_mw_clear_trans(tc->ntb, pidx, widx); 632 - dma_free_coherent(&tc->ntb->dev, inmw->size, 632 + dma_free_coherent(&tc->ntb->pdev->dev, inmw->size, 633 633 inmw->mm_base, inmw->dma_base); 634 634 } 635 635 ··· 1690 1690 debugfs_remove_recursive(tool_dbgfs_topdir); 1691 1691 } 1692 1692 module_exit(tool_exit); 1693 -
+3 -3
include/linux/ntb.h
··· 478 478 int ntb_register_device(struct ntb_dev *ntb); 479 479 480 480 /** 481 - * ntb_register_device() - unregister a ntb device 481 + * ntb_unregister_device() - unregister a ntb device 482 482 * @ntb: NTB device context. 483 483 * 484 484 * The device will be removed from the list of ntb devices. If the ntb device ··· 1351 1351 * @sidx: Scratchpad index. 1352 1352 * @spad_addr: OUT - The address of the peer scratchpad register. 1353 1353 * 1354 - * Return the address of the peer doorbell register. This may be used, for 1354 + * Return the address of the peer scratchpad register. This may be used, for 1355 1355 * example, by drivers that offload memory copy operations to a dma engine. 1356 1356 * 1357 1357 * Return: Zero on success, otherwise an error number. ··· 1373 1373 * 1374 1374 * Read the peer scratchpad register, and return the value. 1375 1375 * 1376 - * Return: The value of the local scratchpad register. 1376 + * Return: The value of the peer scratchpad register. 1377 1377 */ 1378 1378 static inline u32 ntb_peer_spad_read(struct ntb_dev *ntb, int pidx, int sidx) 1379 1379 {
+1 -1
tools/testing/selftests/ntb/ntb_test.sh
··· 241 241 split_remote $LOC 242 242 243 243 if [[ "$REMOTE" == "" ]]; then 244 - echo $(ls -1 "$LOC"/${NAME}* 2>/dev/null | wc -l) 244 + echo $(ls -1 "$VPATH"/${NAME}* 2>/dev/null | wc -l) 245 245 else 246 246 echo $(ssh "$REMOTE" "ls -1 \"$VPATH\"/${NAME}* | \ 247 247 wc -l" 2> /dev/null)