pcie_layerscape.c 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149
  1. // SPDX-License-Identifier: GPL-2.0+
  2. /*
  3. * Copyright 2017-2020 NXP
  4. * Copyright 2014-2015 Freescale Semiconductor, Inc.
  5. * Layerscape PCIe driver
  6. */
  7. #include <common.h>
  8. #include <log.h>
  9. #include <asm/global_data.h>
  10. #include <asm/io.h>
  11. #include <errno.h>
  12. #include <malloc.h>
  13. #if defined(CONFIG_FSL_LSCH2) || defined(CONFIG_FSL_LSCH3) || \
  14. defined(CONFIG_ARM)
  15. #include <asm/arch/clock.h>
  16. #endif
  17. #include "pcie_layerscape.h"
  18. DECLARE_GLOBAL_DATA_PTR;
  19. LIST_HEAD(ls_pcie_list);
  20. unsigned int dbi_readl(struct ls_pcie *pcie, unsigned int offset)
  21. {
  22. return in_le32(pcie->dbi + offset);
  23. }
  24. void dbi_writel(struct ls_pcie *pcie, unsigned int value, unsigned int offset)
  25. {
  26. out_le32(pcie->dbi + offset, value);
  27. }
  28. unsigned int ctrl_readl(struct ls_pcie *pcie, unsigned int offset)
  29. {
  30. if (pcie->big_endian)
  31. return in_be32(pcie->ctrl + offset);
  32. else
  33. return in_le32(pcie->ctrl + offset);
  34. }
  35. void ctrl_writel(struct ls_pcie *pcie, unsigned int value,
  36. unsigned int offset)
  37. {
  38. if (pcie->big_endian)
  39. out_be32(pcie->ctrl + offset, value);
  40. else
  41. out_le32(pcie->ctrl + offset, value);
  42. }
  43. void ls_pcie_dbi_ro_wr_en(struct ls_pcie *pcie)
  44. {
  45. u32 reg, val;
  46. reg = PCIE_MISC_CONTROL_1_OFF;
  47. val = dbi_readl(pcie, reg);
  48. val |= PCIE_DBI_RO_WR_EN;
  49. dbi_writel(pcie, val, reg);
  50. }
  51. void ls_pcie_dbi_ro_wr_dis(struct ls_pcie *pcie)
  52. {
  53. u32 reg, val;
  54. reg = PCIE_MISC_CONTROL_1_OFF;
  55. val = dbi_readl(pcie, reg);
  56. val &= ~PCIE_DBI_RO_WR_EN;
  57. dbi_writel(pcie, val, reg);
  58. }
  59. static int ls_pcie_ltssm(struct ls_pcie *pcie)
  60. {
  61. u32 state;
  62. uint svr;
  63. svr = get_svr();
  64. if (((svr >> SVR_VAR_PER_SHIFT) & SVR_LS102XA_MASK) == SVR_LS102XA) {
  65. state = ctrl_readl(pcie, LS1021_PEXMSCPORTSR(pcie->idx));
  66. state = (state >> LS1021_LTSSM_STATE_SHIFT) & LTSSM_STATE_MASK;
  67. } else {
  68. state = ctrl_readl(pcie, PCIE_PF_DBG) & LTSSM_STATE_MASK;
  69. }
  70. return state;
  71. }
  72. int ls_pcie_link_up(struct ls_pcie *pcie)
  73. {
  74. int ltssm;
  75. ltssm = ls_pcie_ltssm(pcie);
  76. if (ltssm < LTSSM_PCIE_L0)
  77. return 0;
  78. return 1;
  79. }
  80. void ls_pcie_atu_outbound_set(struct ls_pcie *pcie, int idx, int type,
  81. u64 phys, u64 bus_addr, u64 size)
  82. {
  83. dbi_writel(pcie, PCIE_ATU_REGION_OUTBOUND | idx, PCIE_ATU_VIEWPORT);
  84. dbi_writel(pcie, (u32)phys, PCIE_ATU_LOWER_BASE);
  85. dbi_writel(pcie, phys >> 32, PCIE_ATU_UPPER_BASE);
  86. dbi_writel(pcie, (u32)phys + size - 1, PCIE_ATU_LIMIT);
  87. dbi_writel(pcie, (u32)bus_addr, PCIE_ATU_LOWER_TARGET);
  88. dbi_writel(pcie, bus_addr >> 32, PCIE_ATU_UPPER_TARGET);
  89. dbi_writel(pcie, type, PCIE_ATU_CR1);
  90. dbi_writel(pcie, PCIE_ATU_ENABLE, PCIE_ATU_CR2);
  91. }
  92. /* Use bar match mode and MEM type as default */
  93. void ls_pcie_atu_inbound_set(struct ls_pcie *pcie, u32 pf, u32 vf_flag,
  94. int type, int idx, int bar, u64 phys)
  95. {
  96. dbi_writel(pcie, PCIE_ATU_REGION_INBOUND | idx, PCIE_ATU_VIEWPORT);
  97. dbi_writel(pcie, (u32)phys, PCIE_ATU_LOWER_TARGET);
  98. dbi_writel(pcie, phys >> 32, PCIE_ATU_UPPER_TARGET);
  99. dbi_writel(pcie, type | PCIE_ATU_FUNC_NUM(pf), PCIE_ATU_CR1);
  100. dbi_writel(pcie, PCIE_ATU_ENABLE | PCIE_ATU_BAR_MODE_ENABLE |
  101. (vf_flag ? PCIE_ATU_FUNC_NUM_MATCH_EN : 0) |
  102. (vf_flag ? PCIE_ATU_VFBAR_MATCH_MODE_EN : 0) |
  103. PCIE_ATU_BAR_NUM(bar), PCIE_ATU_CR2);
  104. }
  105. void ls_pcie_dump_atu(struct ls_pcie *pcie, u32 win_num, u32 type)
  106. {
  107. int win_idx;
  108. for (win_idx = 0; win_idx < win_num; win_idx++) {
  109. dbi_writel(pcie, type | win_idx, PCIE_ATU_VIEWPORT);
  110. debug("iATU%d:\n", win_idx);
  111. debug("\tLOWER PHYS 0x%08x\n",
  112. dbi_readl(pcie, PCIE_ATU_LOWER_BASE));
  113. debug("\tUPPER PHYS 0x%08x\n",
  114. dbi_readl(pcie, PCIE_ATU_UPPER_BASE));
  115. if (type == PCIE_ATU_REGION_OUTBOUND) {
  116. debug("\tLOWER BUS 0x%08x\n",
  117. dbi_readl(pcie, PCIE_ATU_LOWER_TARGET));
  118. debug("\tUPPER BUS 0x%08x\n",
  119. dbi_readl(pcie, PCIE_ATU_UPPER_TARGET));
  120. debug("\tLIMIT 0x%08x\n",
  121. dbi_readl(pcie, PCIE_ATU_LIMIT));
  122. }
  123. debug("\tCR1 0x%08x\n",
  124. dbi_readl(pcie, PCIE_ATU_CR1));
  125. debug("\tCR2 0x%08x\n",
  126. dbi_readl(pcie, PCIE_ATU_CR2));
  127. }
  128. }