pcie_layerscape_rc.c 9.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379
  1. // SPDX-License-Identifier: GPL-2.0+
  2. /*
  3. * Copyright 2020 NXP
  4. * Layerscape PCIe driver
  5. */
  6. #include <common.h>
  7. #include <asm/arch/fsl_serdes.h>
  8. #include <pci.h>
  9. #include <asm/io.h>
  10. #include <errno.h>
  11. #include <malloc.h>
  12. #include <dm.h>
  13. #include <dm/devres.h>
  14. #if defined(CONFIG_FSL_LSCH2) || defined(CONFIG_FSL_LSCH3) || \
  15. defined(CONFIG_ARM)
  16. #include <asm/arch/clock.h>
  17. #endif
  18. #include "pcie_layerscape.h"
  19. DECLARE_GLOBAL_DATA_PTR;
  20. static void ls_pcie_cfg0_set_busdev(struct ls_pcie_rc *pcie_rc, u32 busdev)
  21. {
  22. struct ls_pcie *pcie = pcie_rc->pcie;
  23. dbi_writel(pcie, PCIE_ATU_REGION_OUTBOUND | PCIE_ATU_REGION_INDEX0,
  24. PCIE_ATU_VIEWPORT);
  25. dbi_writel(pcie, busdev, PCIE_ATU_LOWER_TARGET);
  26. }
  27. static void ls_pcie_cfg1_set_busdev(struct ls_pcie_rc *pcie_rc, u32 busdev)
  28. {
  29. struct ls_pcie *pcie = pcie_rc->pcie;
  30. dbi_writel(pcie, PCIE_ATU_REGION_OUTBOUND | PCIE_ATU_REGION_INDEX1,
  31. PCIE_ATU_VIEWPORT);
  32. dbi_writel(pcie, busdev, PCIE_ATU_LOWER_TARGET);
  33. }
  34. static void ls_pcie_setup_atu(struct ls_pcie_rc *pcie_rc)
  35. {
  36. struct pci_region *io, *mem, *pref;
  37. unsigned long long offset = 0;
  38. struct ls_pcie *pcie = pcie_rc->pcie;
  39. int idx = 0;
  40. uint svr;
  41. svr = get_svr();
  42. if (((svr >> SVR_VAR_PER_SHIFT) & SVR_LS102XA_MASK) == SVR_LS102XA) {
  43. offset = LS1021_PCIE_SPACE_OFFSET +
  44. LS1021_PCIE_SPACE_SIZE * pcie->idx;
  45. }
  46. /* ATU 0 : OUTBOUND : CFG0 */
  47. ls_pcie_atu_outbound_set(pcie, PCIE_ATU_REGION_INDEX0,
  48. PCIE_ATU_TYPE_CFG0,
  49. pcie_rc->cfg_res.start + offset,
  50. 0,
  51. fdt_resource_size(&pcie_rc->cfg_res) / 2);
  52. /* ATU 1 : OUTBOUND : CFG1 */
  53. ls_pcie_atu_outbound_set(pcie, PCIE_ATU_REGION_INDEX1,
  54. PCIE_ATU_TYPE_CFG1,
  55. pcie_rc->cfg_res.start + offset +
  56. fdt_resource_size(&pcie_rc->cfg_res) / 2,
  57. 0,
  58. fdt_resource_size(&pcie_rc->cfg_res) / 2);
  59. pci_get_regions(pcie_rc->bus, &io, &mem, &pref);
  60. idx = PCIE_ATU_REGION_INDEX1 + 1;
  61. /* Fix the pcie memory map for LS2088A series SoCs */
  62. svr = (svr >> SVR_VAR_PER_SHIFT) & 0xFFFFFE;
  63. if (svr == SVR_LS2088A || svr == SVR_LS2084A ||
  64. svr == SVR_LS2048A || svr == SVR_LS2044A ||
  65. svr == SVR_LS2081A || svr == SVR_LS2041A) {
  66. if (io)
  67. io->phys_start = (io->phys_start &
  68. (PCIE_PHYS_SIZE - 1)) +
  69. LS2088A_PCIE1_PHYS_ADDR +
  70. LS2088A_PCIE_PHYS_SIZE * pcie->idx;
  71. if (mem)
  72. mem->phys_start = (mem->phys_start &
  73. (PCIE_PHYS_SIZE - 1)) +
  74. LS2088A_PCIE1_PHYS_ADDR +
  75. LS2088A_PCIE_PHYS_SIZE * pcie->idx;
  76. if (pref)
  77. pref->phys_start = (pref->phys_start &
  78. (PCIE_PHYS_SIZE - 1)) +
  79. LS2088A_PCIE1_PHYS_ADDR +
  80. LS2088A_PCIE_PHYS_SIZE * pcie->idx;
  81. }
  82. if (io)
  83. /* ATU : OUTBOUND : IO */
  84. ls_pcie_atu_outbound_set(pcie, idx++,
  85. PCIE_ATU_TYPE_IO,
  86. io->phys_start + offset,
  87. io->bus_start,
  88. io->size);
  89. if (mem)
  90. /* ATU : OUTBOUND : MEM */
  91. ls_pcie_atu_outbound_set(pcie, idx++,
  92. PCIE_ATU_TYPE_MEM,
  93. mem->phys_start + offset,
  94. mem->bus_start,
  95. mem->size);
  96. if (pref)
  97. /* ATU : OUTBOUND : pref */
  98. ls_pcie_atu_outbound_set(pcie, idx++,
  99. PCIE_ATU_TYPE_MEM,
  100. pref->phys_start + offset,
  101. pref->bus_start,
  102. pref->size);
  103. ls_pcie_dump_atu(pcie, PCIE_ATU_REGION_NUM, PCIE_ATU_REGION_OUTBOUND);
  104. }
  105. /* Return 0 if the address is valid, -errno if not valid */
  106. static int ls_pcie_addr_valid(struct ls_pcie_rc *pcie_rc, pci_dev_t bdf)
  107. {
  108. struct udevice *bus = pcie_rc->bus;
  109. struct ls_pcie *pcie = pcie_rc->pcie;
  110. if (pcie->mode == PCI_HEADER_TYPE_NORMAL)
  111. return -ENODEV;
  112. if (!pcie_rc->enabled)
  113. return -ENXIO;
  114. if (PCI_BUS(bdf) < dev_seq(bus))
  115. return -EINVAL;
  116. if ((PCI_BUS(bdf) > dev_seq(bus)) && (!ls_pcie_link_up(pcie)))
  117. return -EINVAL;
  118. if (PCI_BUS(bdf) <= (dev_seq(bus) + 1) && (PCI_DEV(bdf) > 0))
  119. return -EINVAL;
  120. return 0;
  121. }
  122. int ls_pcie_conf_address(const struct udevice *bus, pci_dev_t bdf,
  123. uint offset, void **paddress)
  124. {
  125. struct ls_pcie_rc *pcie_rc = dev_get_priv(bus);
  126. struct ls_pcie *pcie = pcie_rc->pcie;
  127. u32 busdev;
  128. if (ls_pcie_addr_valid(pcie_rc, bdf))
  129. return -EINVAL;
  130. if (PCI_BUS(bdf) == dev_seq(bus)) {
  131. *paddress = pcie->dbi + offset;
  132. return 0;
  133. }
  134. busdev = PCIE_ATU_BUS(PCI_BUS(bdf) - dev_seq(bus)) |
  135. PCIE_ATU_DEV(PCI_DEV(bdf)) |
  136. PCIE_ATU_FUNC(PCI_FUNC(bdf));
  137. if (PCI_BUS(bdf) == dev_seq(bus) + 1) {
  138. ls_pcie_cfg0_set_busdev(pcie_rc, busdev);
  139. *paddress = pcie_rc->cfg0 + offset;
  140. } else {
  141. ls_pcie_cfg1_set_busdev(pcie_rc, busdev);
  142. *paddress = pcie_rc->cfg1 + offset;
  143. }
  144. return 0;
  145. }
  146. static int ls_pcie_read_config(const struct udevice *bus, pci_dev_t bdf,
  147. uint offset, ulong *valuep,
  148. enum pci_size_t size)
  149. {
  150. return pci_generic_mmap_read_config(bus, ls_pcie_conf_address,
  151. bdf, offset, valuep, size);
  152. }
  153. static int ls_pcie_write_config(struct udevice *bus, pci_dev_t bdf,
  154. uint offset, ulong value,
  155. enum pci_size_t size)
  156. {
  157. return pci_generic_mmap_write_config(bus, ls_pcie_conf_address,
  158. bdf, offset, value, size);
  159. }
  160. /* Clear multi-function bit */
  161. static void ls_pcie_clear_multifunction(struct ls_pcie_rc *pcie_rc)
  162. {
  163. struct ls_pcie *pcie = pcie_rc->pcie;
  164. writeb(PCI_HEADER_TYPE_BRIDGE, pcie->dbi + PCI_HEADER_TYPE);
  165. }
  166. /* Fix class value */
  167. static void ls_pcie_fix_class(struct ls_pcie_rc *pcie_rc)
  168. {
  169. struct ls_pcie *pcie = pcie_rc->pcie;
  170. writew(PCI_CLASS_BRIDGE_PCI, pcie->dbi + PCI_CLASS_DEVICE);
  171. }
  172. /* Drop MSG TLP except for Vendor MSG */
  173. static void ls_pcie_drop_msg_tlp(struct ls_pcie_rc *pcie_rc)
  174. {
  175. struct ls_pcie *pcie = pcie_rc->pcie;
  176. u32 val;
  177. val = dbi_readl(pcie, PCIE_STRFMR1);
  178. val &= 0xDFFFFFFF;
  179. dbi_writel(pcie, val, PCIE_STRFMR1);
  180. }
  181. /* Disable all bars in RC mode */
  182. static void ls_pcie_disable_bars(struct ls_pcie_rc *pcie_rc)
  183. {
  184. struct ls_pcie *pcie = pcie_rc->pcie;
  185. dbi_writel(pcie, 0, PCIE_CS2_OFFSET + PCI_BASE_ADDRESS_0);
  186. dbi_writel(pcie, 0, PCIE_CS2_OFFSET + PCI_BASE_ADDRESS_1);
  187. dbi_writel(pcie, 0xfffffffe, PCIE_CS2_OFFSET + PCI_ROM_ADDRESS1);
  188. }
  189. static void ls_pcie_setup_ctrl(struct ls_pcie_rc *pcie_rc)
  190. {
  191. struct ls_pcie *pcie = pcie_rc->pcie;
  192. ls_pcie_setup_atu(pcie_rc);
  193. ls_pcie_dbi_ro_wr_en(pcie);
  194. ls_pcie_fix_class(pcie_rc);
  195. ls_pcie_clear_multifunction(pcie_rc);
  196. ls_pcie_drop_msg_tlp(pcie_rc);
  197. ls_pcie_dbi_ro_wr_dis(pcie);
  198. ls_pcie_disable_bars(pcie_rc);
  199. pcie_rc->stream_id_cur = 0;
  200. }
  201. static int ls_pcie_probe(struct udevice *dev)
  202. {
  203. struct ls_pcie_rc *pcie_rc = dev_get_priv(dev);
  204. const void *fdt = gd->fdt_blob;
  205. int node = dev_of_offset(dev);
  206. struct ls_pcie *pcie;
  207. u16 link_sta;
  208. uint svr;
  209. int ret;
  210. fdt_size_t cfg_size;
  211. pcie_rc->bus = dev;
  212. pcie = devm_kmalloc(dev, sizeof(*pcie), GFP_KERNEL);
  213. if (!pcie)
  214. return -ENOMEM;
  215. pcie_rc->pcie = pcie;
  216. ret = fdt_get_named_resource(fdt, node, "reg", "reg-names",
  217. "dbi", &pcie_rc->dbi_res);
  218. if (ret) {
  219. printf("ls-pcie: resource \"dbi\" not found\n");
  220. return ret;
  221. }
  222. pcie->idx = (pcie_rc->dbi_res.start - PCIE_SYS_BASE_ADDR) /
  223. PCIE_CCSR_SIZE;
  224. list_add(&pcie_rc->list, &ls_pcie_list);
  225. pcie_rc->enabled = is_serdes_configured(PCIE_SRDS_PRTCL(pcie->idx));
  226. if (!pcie_rc->enabled) {
  227. printf("PCIe%d: %s disabled\n", pcie->idx, dev->name);
  228. return 0;
  229. }
  230. pcie->dbi = map_physmem(pcie_rc->dbi_res.start,
  231. fdt_resource_size(&pcie_rc->dbi_res),
  232. MAP_NOCACHE);
  233. pcie->mode = readb(pcie->dbi + PCI_HEADER_TYPE) & 0x7f;
  234. if (pcie->mode == PCI_HEADER_TYPE_NORMAL)
  235. return 0;
  236. ret = fdt_get_named_resource(fdt, node, "reg", "reg-names",
  237. "lut", &pcie_rc->lut_res);
  238. if (!ret)
  239. pcie->lut = map_physmem(pcie_rc->lut_res.start,
  240. fdt_resource_size(&pcie_rc->lut_res),
  241. MAP_NOCACHE);
  242. ret = fdt_get_named_resource(fdt, node, "reg", "reg-names",
  243. "ctrl", &pcie_rc->ctrl_res);
  244. if (!ret)
  245. pcie->ctrl = map_physmem(pcie_rc->ctrl_res.start,
  246. fdt_resource_size(&pcie_rc->ctrl_res),
  247. MAP_NOCACHE);
  248. if (!pcie->ctrl)
  249. pcie->ctrl = pcie->lut;
  250. if (!pcie->ctrl) {
  251. printf("%s: NOT find CTRL\n", dev->name);
  252. return -1;
  253. }
  254. ret = fdt_get_named_resource(fdt, node, "reg", "reg-names",
  255. "config", &pcie_rc->cfg_res);
  256. if (ret) {
  257. printf("%s: resource \"config\" not found\n", dev->name);
  258. return ret;
  259. }
  260. /*
  261. * Fix the pcie memory map address and PF control registers address
  262. * for LS2088A series SoCs
  263. */
  264. svr = get_svr();
  265. svr = (svr >> SVR_VAR_PER_SHIFT) & 0xFFFFFE;
  266. if (svr == SVR_LS2088A || svr == SVR_LS2084A ||
  267. svr == SVR_LS2048A || svr == SVR_LS2044A ||
  268. svr == SVR_LS2081A || svr == SVR_LS2041A) {
  269. cfg_size = fdt_resource_size(&pcie_rc->cfg_res);
  270. pcie_rc->cfg_res.start = LS2088A_PCIE1_PHYS_ADDR +
  271. LS2088A_PCIE_PHYS_SIZE * pcie->idx;
  272. pcie_rc->cfg_res.end = pcie_rc->cfg_res.start + cfg_size;
  273. pcie->ctrl = pcie->lut + 0x40000;
  274. }
  275. pcie_rc->cfg0 = map_physmem(pcie_rc->cfg_res.start,
  276. fdt_resource_size(&pcie_rc->cfg_res),
  277. MAP_NOCACHE);
  278. pcie_rc->cfg1 = pcie_rc->cfg0 +
  279. fdt_resource_size(&pcie_rc->cfg_res) / 2;
  280. pcie->big_endian = fdtdec_get_bool(fdt, node, "big-endian");
  281. debug("%s dbi:%lx lut:%lx ctrl:0x%lx cfg0:0x%lx, big-endian:%d\n",
  282. dev->name, (unsigned long)pcie->dbi, (unsigned long)pcie->lut,
  283. (unsigned long)pcie->ctrl, (unsigned long)pcie_rc->cfg0,
  284. pcie->big_endian);
  285. printf("PCIe%u: %s %s", pcie->idx, dev->name, "Root Complex");
  286. ls_pcie_setup_ctrl(pcie_rc);
  287. if (!ls_pcie_link_up(pcie)) {
  288. /* Let the user know there's no PCIe link */
  289. printf(": no link\n");
  290. return 0;
  291. }
  292. /* Print the negotiated PCIe link width */
  293. link_sta = readw(pcie->dbi + PCIE_LINK_STA);
  294. printf(": x%d gen%d\n", (link_sta & PCIE_LINK_WIDTH_MASK) >> 4,
  295. link_sta & PCIE_LINK_SPEED_MASK);
  296. return 0;
  297. }
  298. static const struct dm_pci_ops ls_pcie_ops = {
  299. .read_config = ls_pcie_read_config,
  300. .write_config = ls_pcie_write_config,
  301. };
  302. static const struct udevice_id ls_pcie_ids[] = {
  303. { .compatible = "fsl,ls-pcie" },
  304. { }
  305. };
  306. U_BOOT_DRIVER(pci_layerscape) = {
  307. .name = "pci_layerscape",
  308. .id = UCLASS_PCI,
  309. .of_match = ls_pcie_ids,
  310. .ops = &ls_pcie_ops,
  311. .probe = ls_pcie_probe,
  312. .priv_auto = sizeof(struct ls_pcie_rc),
  313. };