1 // SPDX-License-Identifier: ISC 2 /* 3 * Copyright (C) 2022 MediaTek Inc. 4 */ 5 6 #include <linux/kernel.h> 7 #include <linux/module.h> 8 #include <linux/pci.h> 9 10 #include "mt7996.h" 11 #include "mac.h" 12 #include "../trace.h" 13 14 static LIST_HEAD(hif_list); 15 static DEFINE_SPINLOCK(hif_lock); 16 static u32 hif_idx; 17 18 static const struct pci_device_id mt7996_pci_device_table[] = { 19 { PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, MT7996_DEVICE_ID) }, 20 { PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, MT7992_DEVICE_ID) }, 21 { PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, MT7990_DEVICE_ID) }, 22 { }, 23 }; 24 25 static const struct pci_device_id mt7996_hif_device_table[] = { 26 { PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, MT7996_DEVICE_ID_2) }, 27 { PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, MT7992_DEVICE_ID_2) }, 28 { PCI_DEVICE(PCI_VENDOR_ID_MEDIATEK, MT7990_DEVICE_ID_2) }, 29 { }, 30 }; 31 32 static struct mt7996_hif *mt7996_pci_get_hif2(u32 idx) 33 { 34 struct mt7996_hif *hif; 35 u32 val; 36 37 spin_lock_bh(&hif_lock); 38 39 list_for_each_entry(hif, &hif_list, list) { 40 val = readl(hif->regs + MT_PCIE_RECOG_ID); 41 val &= MT_PCIE_RECOG_ID_MASK; 42 if (val != idx) 43 continue; 44 45 get_device(hif->dev); 46 goto out; 47 } 48 hif = NULL; 49 50 out: 51 spin_unlock_bh(&hif_lock); 52 53 return hif; 54 } 55 56 static void mt7996_put_hif2(struct mt7996_hif *hif) 57 { 58 if (!hif) 59 return; 60 61 put_device(hif->dev); 62 } 63 64 static struct mt7996_hif *mt7996_pci_init_hif2(struct pci_dev *pdev) 65 { 66 hif_idx++; 67 68 if (!pci_get_device(PCI_VENDOR_ID_MEDIATEK, MT7996_DEVICE_ID_2, NULL) && 69 !pci_get_device(PCI_VENDOR_ID_MEDIATEK, MT7992_DEVICE_ID_2, NULL) && 70 !pci_get_device(PCI_VENDOR_ID_MEDIATEK, MT7990_DEVICE_ID_2, NULL)) 71 return NULL; 72 73 writel(hif_idx | MT_PCIE_RECOG_ID_SEM, 74 pcim_iomap_table(pdev)[0] + MT_PCIE_RECOG_ID); 75 76 return mt7996_pci_get_hif2(hif_idx); 77 } 78 79 static int mt7996_pci_hif2_probe(struct pci_dev *pdev) 80 { 81 struct mt7996_hif *hif; 82 83 hif = devm_kzalloc(&pdev->dev, sizeof(*hif), GFP_KERNEL); 84 if (!hif) 85 return -ENOMEM; 86 87 hif->dev = &pdev->dev; 88 hif->regs = pcim_iomap_table(pdev)[0]; 89 hif->irq = pdev->irq; 90 spin_lock_bh(&hif_lock); 91 list_add(&hif->list, &hif_list); 92 spin_unlock_bh(&hif_lock); 93 pci_set_drvdata(pdev, hif); 94 95 return 0; 96 } 97 98 static int mt7996_pci_probe(struct pci_dev *pdev, 99 const struct pci_device_id *id) 100 { 101 struct pci_dev *hif2_dev; 102 struct mt7996_hif *hif2; 103 struct mt7996_dev *dev; 104 int irq, hif2_irq, ret; 105 struct mt76_dev *mdev; 106 107 ret = pcim_enable_device(pdev); 108 if (ret) 109 return ret; 110 111 ret = pcim_iomap_regions(pdev, BIT(0), pci_name(pdev)); 112 if (ret) 113 return ret; 114 115 pci_set_master(pdev); 116 117 ret = dma_set_mask(&pdev->dev, DMA_BIT_MASK(36)); 118 if (ret) 119 return ret; 120 121 ret = dma_set_coherent_mask(&pdev->dev, DMA_BIT_MASK(32)); 122 if (ret) 123 return ret; 124 125 mt76_pci_disable_aspm(pdev); 126 127 if (id->device == MT7996_DEVICE_ID_2 || 128 id->device == MT7992_DEVICE_ID_2 || 129 id->device == MT7990_DEVICE_ID_2) 130 return mt7996_pci_hif2_probe(pdev); 131 132 dev = mt7996_mmio_probe(&pdev->dev, pcim_iomap_table(pdev)[0], 133 id->device); 134 if (IS_ERR(dev)) 135 return PTR_ERR(dev); 136 137 mdev = &dev->mt76; 138 mt7996_wfsys_reset(dev); 139 hif2 = mt7996_pci_init_hif2(pdev); 140 141 ret = mt7996_mmio_wed_init(dev, pdev, false, &irq); 142 if (ret < 0) 143 goto free_wed_or_irq_vector; 144 145 if (!ret) { 146 ret = pci_alloc_irq_vectors(pdev, 1, 1, PCI_IRQ_ALL_TYPES); 147 if (ret < 0) 148 goto free_device; 149 150 irq = pdev->irq; 151 } 152 153 ret = devm_request_irq(mdev->dev, irq, mt7996_irq_handler, 154 IRQF_SHARED, KBUILD_MODNAME, dev); 155 if (ret) 156 goto free_wed_or_irq_vector; 157 158 mt76_wr(dev, MT_INT_MASK_CSR, 0); 159 /* master switch of PCIe tnterrupt enable */ 160 mt76_wr(dev, MT_PCIE_MAC_INT_ENABLE, 0xff); 161 162 if (hif2) { 163 hif2_dev = container_of(hif2->dev, struct pci_dev, dev); 164 dev->hif2 = hif2; 165 166 ret = mt7996_mmio_wed_init(dev, hif2_dev, true, &hif2_irq); 167 if (ret < 0) 168 goto free_hif2_wed_irq_vector; 169 170 if (!ret) { 171 ret = pci_alloc_irq_vectors(hif2_dev, 1, 1, 172 PCI_IRQ_ALL_TYPES); 173 if (ret < 0) 174 goto free_hif2; 175 176 dev->hif2->irq = hif2_dev->irq; 177 hif2_irq = dev->hif2->irq; 178 } 179 180 ret = devm_request_irq(mdev->dev, hif2_irq, mt7996_irq_handler, 181 IRQF_SHARED, KBUILD_MODNAME "-hif", 182 dev); 183 if (ret) 184 goto free_hif2_wed_irq_vector; 185 186 mt76_wr(dev, MT_INT1_MASK_CSR, 0); 187 /* master switch of PCIe tnterrupt enable */ 188 mt76_wr(dev, MT_PCIE1_MAC_INT_ENABLE, 0xff); 189 } 190 191 ret = mt7996_register_device(dev); 192 if (ret) 193 goto free_hif2_irq; 194 195 return 0; 196 197 free_hif2_irq: 198 if (dev->hif2) 199 devm_free_irq(mdev->dev, hif2_irq, dev); 200 free_hif2_wed_irq_vector: 201 if (dev->hif2) { 202 if (mtk_wed_device_active(&dev->mt76.mmio.wed_hif2)) 203 mtk_wed_device_detach(&dev->mt76.mmio.wed_hif2); 204 else 205 pci_free_irq_vectors(hif2_dev); 206 } 207 free_hif2: 208 if (dev->hif2) 209 put_device(dev->hif2->dev); 210 devm_free_irq(mdev->dev, irq, dev); 211 free_wed_or_irq_vector: 212 if (mtk_wed_device_active(&dev->mt76.mmio.wed)) 213 mtk_wed_device_detach(&dev->mt76.mmio.wed); 214 else 215 pci_free_irq_vectors(pdev); 216 free_device: 217 mt76_free_device(&dev->mt76); 218 219 return ret; 220 } 221 222 static void mt7996_hif_remove(struct pci_dev *pdev) 223 { 224 struct mt7996_hif *hif = pci_get_drvdata(pdev); 225 226 list_del(&hif->list); 227 } 228 229 static void mt7996_pci_remove(struct pci_dev *pdev) 230 { 231 struct mt76_dev *mdev; 232 struct mt7996_dev *dev; 233 234 mdev = pci_get_drvdata(pdev); 235 dev = container_of(mdev, struct mt7996_dev, mt76); 236 mt7996_put_hif2(dev->hif2); 237 mt7996_unregister_device(dev); 238 } 239 240 struct pci_driver mt7996_hif_driver = { 241 .name = KBUILD_MODNAME "_hif", 242 .id_table = mt7996_hif_device_table, 243 .probe = mt7996_pci_probe, 244 .remove = mt7996_hif_remove, 245 }; 246 247 struct pci_driver mt7996_pci_driver = { 248 .name = KBUILD_MODNAME, 249 .id_table = mt7996_pci_device_table, 250 .probe = mt7996_pci_probe, 251 .remove = mt7996_pci_remove, 252 }; 253 254 MODULE_DEVICE_TABLE(pci, mt7996_pci_device_table); 255 MODULE_DEVICE_TABLE(pci, mt7996_hif_device_table); 256 MODULE_FIRMWARE(MT7996_FIRMWARE_WA); 257 MODULE_FIRMWARE(MT7996_FIRMWARE_WM); 258 MODULE_FIRMWARE(MT7996_FIRMWARE_DSP); 259 MODULE_FIRMWARE(MT7996_ROM_PATCH); 260 MODULE_FIRMWARE(MT7992_FIRMWARE_WA); 261 MODULE_FIRMWARE(MT7992_FIRMWARE_WM); 262 MODULE_FIRMWARE(MT7992_FIRMWARE_DSP); 263 MODULE_FIRMWARE(MT7992_ROM_PATCH); 264 MODULE_FIRMWARE(MT7990_FIRMWARE_WM); 265 MODULE_FIRMWARE(MT7990_ROM_PATCH); 266