1 // SPDX-License-Identifier: GPL-2.0+
3 * Rockchip AXI PCIe host controller driver
5 * Copyright (c) 2016 Rockchip, Inc.
7 * Author: Shawn Lin <shawn.lin@rock-chips.com>
8 * Wenrui Li <wenrui.li@rock-chips.com>
10 * Bits taken from Synopsys DesignWare Host controller driver and
11 * ARM PCI Host generic driver.
14 #include <linux/clk.h>
15 #include <linux/delay.h>
16 #include <linux/gpio/consumer.h>
17 #include <linux/of_pci.h>
18 #include <linux/phy/phy.h>
19 #include <linux/platform_device.h>
20 #include <linux/reset.h>
23 #include "pcie-rockchip.h"
25 int rockchip_pcie_parse_dt(struct rockchip_pcie
*rockchip
)
27 struct device
*dev
= rockchip
->dev
;
28 struct platform_device
*pdev
= to_platform_device(dev
);
29 struct device_node
*node
= dev
->of_node
;
30 struct resource
*regs
;
33 if (rockchip
->is_rc
) {
34 regs
= platform_get_resource_byname(pdev
,
37 rockchip
->reg_base
= devm_pci_remap_cfg_resource(dev
, regs
);
38 if (IS_ERR(rockchip
->reg_base
))
39 return PTR_ERR(rockchip
->reg_base
);
42 platform_get_resource_byname(pdev
, IORESOURCE_MEM
,
44 if (!rockchip
->mem_res
)
48 regs
= platform_get_resource_byname(pdev
, IORESOURCE_MEM
,
50 rockchip
->apb_base
= devm_ioremap_resource(dev
, regs
);
51 if (IS_ERR(rockchip
->apb_base
))
52 return PTR_ERR(rockchip
->apb_base
);
54 err
= rockchip_pcie_get_phys(rockchip
);
59 err
= of_property_read_u32(node
, "num-lanes", &rockchip
->lanes
);
60 if (!err
&& (rockchip
->lanes
== 0 ||
61 rockchip
->lanes
== 3 ||
62 rockchip
->lanes
> 4)) {
63 dev_warn(dev
, "invalid num-lanes, default to use one lane\n");
67 rockchip
->link_gen
= of_pci_get_max_link_speed(node
);
68 if (rockchip
->link_gen
< 0 || rockchip
->link_gen
> 2)
69 rockchip
->link_gen
= 2;
71 rockchip
->core_rst
= devm_reset_control_get_exclusive(dev
, "core");
72 if (IS_ERR(rockchip
->core_rst
)) {
73 if (PTR_ERR(rockchip
->core_rst
) != -EPROBE_DEFER
)
74 dev_err(dev
, "missing core reset property in node\n");
75 return PTR_ERR(rockchip
->core_rst
);
78 rockchip
->mgmt_rst
= devm_reset_control_get_exclusive(dev
, "mgmt");
79 if (IS_ERR(rockchip
->mgmt_rst
)) {
80 if (PTR_ERR(rockchip
->mgmt_rst
) != -EPROBE_DEFER
)
81 dev_err(dev
, "missing mgmt reset property in node\n");
82 return PTR_ERR(rockchip
->mgmt_rst
);
85 rockchip
->mgmt_sticky_rst
= devm_reset_control_get_exclusive(dev
,
87 if (IS_ERR(rockchip
->mgmt_sticky_rst
)) {
88 if (PTR_ERR(rockchip
->mgmt_sticky_rst
) != -EPROBE_DEFER
)
89 dev_err(dev
, "missing mgmt-sticky reset property in node\n");
90 return PTR_ERR(rockchip
->mgmt_sticky_rst
);
93 rockchip
->pipe_rst
= devm_reset_control_get_exclusive(dev
, "pipe");
94 if (IS_ERR(rockchip
->pipe_rst
)) {
95 if (PTR_ERR(rockchip
->pipe_rst
) != -EPROBE_DEFER
)
96 dev_err(dev
, "missing pipe reset property in node\n");
97 return PTR_ERR(rockchip
->pipe_rst
);
100 rockchip
->pm_rst
= devm_reset_control_get_exclusive(dev
, "pm");
101 if (IS_ERR(rockchip
->pm_rst
)) {
102 if (PTR_ERR(rockchip
->pm_rst
) != -EPROBE_DEFER
)
103 dev_err(dev
, "missing pm reset property in node\n");
104 return PTR_ERR(rockchip
->pm_rst
);
107 rockchip
->pclk_rst
= devm_reset_control_get_exclusive(dev
, "pclk");
108 if (IS_ERR(rockchip
->pclk_rst
)) {
109 if (PTR_ERR(rockchip
->pclk_rst
) != -EPROBE_DEFER
)
110 dev_err(dev
, "missing pclk reset property in node\n");
111 return PTR_ERR(rockchip
->pclk_rst
);
114 rockchip
->aclk_rst
= devm_reset_control_get_exclusive(dev
, "aclk");
115 if (IS_ERR(rockchip
->aclk_rst
)) {
116 if (PTR_ERR(rockchip
->aclk_rst
) != -EPROBE_DEFER
)
117 dev_err(dev
, "missing aclk reset property in node\n");
118 return PTR_ERR(rockchip
->aclk_rst
);
121 if (rockchip
->is_rc
) {
122 rockchip
->ep_gpio
= devm_gpiod_get(dev
, "ep", GPIOD_OUT_HIGH
);
123 if (IS_ERR(rockchip
->ep_gpio
)) {
124 dev_err(dev
, "missing ep-gpios property in node\n");
125 return PTR_ERR(rockchip
->ep_gpio
);
129 rockchip
->aclk_pcie
= devm_clk_get(dev
, "aclk");
130 if (IS_ERR(rockchip
->aclk_pcie
)) {
131 dev_err(dev
, "aclk clock not found\n");
132 return PTR_ERR(rockchip
->aclk_pcie
);
135 rockchip
->aclk_perf_pcie
= devm_clk_get(dev
, "aclk-perf");
136 if (IS_ERR(rockchip
->aclk_perf_pcie
)) {
137 dev_err(dev
, "aclk_perf clock not found\n");
138 return PTR_ERR(rockchip
->aclk_perf_pcie
);
141 rockchip
->hclk_pcie
= devm_clk_get(dev
, "hclk");
142 if (IS_ERR(rockchip
->hclk_pcie
)) {
143 dev_err(dev
, "hclk clock not found\n");
144 return PTR_ERR(rockchip
->hclk_pcie
);
147 rockchip
->clk_pcie_pm
= devm_clk_get(dev
, "pm");
148 if (IS_ERR(rockchip
->clk_pcie_pm
)) {
149 dev_err(dev
, "pm clock not found\n");
150 return PTR_ERR(rockchip
->clk_pcie_pm
);
155 EXPORT_SYMBOL_GPL(rockchip_pcie_parse_dt
);
157 int rockchip_pcie_init_port(struct rockchip_pcie
*rockchip
)
159 struct device
*dev
= rockchip
->dev
;
163 err
= reset_control_assert(rockchip
->aclk_rst
);
165 dev_err(dev
, "assert aclk_rst err %d\n", err
);
169 err
= reset_control_assert(rockchip
->pclk_rst
);
171 dev_err(dev
, "assert pclk_rst err %d\n", err
);
175 err
= reset_control_assert(rockchip
->pm_rst
);
177 dev_err(dev
, "assert pm_rst err %d\n", err
);
181 for (i
= 0; i
< MAX_LANE_NUM
; i
++) {
182 err
= phy_init(rockchip
->phys
[i
]);
184 dev_err(dev
, "init phy%d err %d\n", i
, err
);
189 err
= reset_control_assert(rockchip
->core_rst
);
191 dev_err(dev
, "assert core_rst err %d\n", err
);
195 err
= reset_control_assert(rockchip
->mgmt_rst
);
197 dev_err(dev
, "assert mgmt_rst err %d\n", err
);
201 err
= reset_control_assert(rockchip
->mgmt_sticky_rst
);
203 dev_err(dev
, "assert mgmt_sticky_rst err %d\n", err
);
207 err
= reset_control_assert(rockchip
->pipe_rst
);
209 dev_err(dev
, "assert pipe_rst err %d\n", err
);
215 err
= reset_control_deassert(rockchip
->pm_rst
);
217 dev_err(dev
, "deassert pm_rst err %d\n", err
);
221 err
= reset_control_deassert(rockchip
->aclk_rst
);
223 dev_err(dev
, "deassert aclk_rst err %d\n", err
);
227 err
= reset_control_deassert(rockchip
->pclk_rst
);
229 dev_err(dev
, "deassert pclk_rst err %d\n", err
);
233 if (rockchip
->link_gen
== 2)
234 rockchip_pcie_write(rockchip
, PCIE_CLIENT_GEN_SEL_2
,
237 rockchip_pcie_write(rockchip
, PCIE_CLIENT_GEN_SEL_1
,
240 regs
= PCIE_CLIENT_LINK_TRAIN_ENABLE
| PCIE_CLIENT_ARI_ENABLE
|
241 PCIE_CLIENT_CONF_LANE_NUM(rockchip
->lanes
);
244 regs
|= PCIE_CLIENT_CONF_ENABLE
| PCIE_CLIENT_MODE_RC
;
246 regs
|= PCIE_CLIENT_CONF_DISABLE
| PCIE_CLIENT_MODE_EP
;
248 rockchip_pcie_write(rockchip
, regs
, PCIE_CLIENT_CONFIG
);
250 for (i
= 0; i
< MAX_LANE_NUM
; i
++) {
251 err
= phy_power_on(rockchip
->phys
[i
]);
253 dev_err(dev
, "power on phy%d err %d\n", i
, err
);
254 goto err_power_off_phy
;
259 * Please don't reorder the deassert sequence of the following
262 err
= reset_control_deassert(rockchip
->mgmt_sticky_rst
);
264 dev_err(dev
, "deassert mgmt_sticky_rst err %d\n", err
);
265 goto err_power_off_phy
;
268 err
= reset_control_deassert(rockchip
->core_rst
);
270 dev_err(dev
, "deassert core_rst err %d\n", err
);
271 goto err_power_off_phy
;
274 err
= reset_control_deassert(rockchip
->mgmt_rst
);
276 dev_err(dev
, "deassert mgmt_rst err %d\n", err
);
277 goto err_power_off_phy
;
280 err
= reset_control_deassert(rockchip
->pipe_rst
);
282 dev_err(dev
, "deassert pipe_rst err %d\n", err
);
283 goto err_power_off_phy
;
289 phy_power_off(rockchip
->phys
[i
]);
293 phy_exit(rockchip
->phys
[i
]);
296 EXPORT_SYMBOL_GPL(rockchip_pcie_init_port
);
298 int rockchip_pcie_get_phys(struct rockchip_pcie
*rockchip
)
300 struct device
*dev
= rockchip
->dev
;
305 phy
= devm_phy_get(dev
, "pcie-phy");
307 rockchip
->legacy_phy
= true;
308 rockchip
->phys
[0] = phy
;
309 dev_warn(dev
, "legacy phy model is deprecated!\n");
313 if (PTR_ERR(phy
) == -EPROBE_DEFER
)
316 dev_dbg(dev
, "missing legacy phy; search for per-lane PHY\n");
318 for (i
= 0; i
< MAX_LANE_NUM
; i
++) {
319 name
= kasprintf(GFP_KERNEL
, "pcie-phy-%u", i
);
323 phy
= devm_of_phy_get(dev
, dev
->of_node
, name
);
327 if (PTR_ERR(phy
) != -EPROBE_DEFER
)
328 dev_err(dev
, "missing phy for lane %d: %ld\n",
333 rockchip
->phys
[i
] = phy
;
338 EXPORT_SYMBOL_GPL(rockchip_pcie_get_phys
);
340 void rockchip_pcie_deinit_phys(struct rockchip_pcie
*rockchip
)
344 for (i
= 0; i
< MAX_LANE_NUM
; i
++) {
345 /* inactive lanes are already powered off */
346 if (rockchip
->lanes_map
& BIT(i
))
347 phy_power_off(rockchip
->phys
[i
]);
348 phy_exit(rockchip
->phys
[i
]);
351 EXPORT_SYMBOL_GPL(rockchip_pcie_deinit_phys
);
353 int rockchip_pcie_enable_clocks(struct rockchip_pcie
*rockchip
)
355 struct device
*dev
= rockchip
->dev
;
358 err
= clk_prepare_enable(rockchip
->aclk_pcie
);
360 dev_err(dev
, "unable to enable aclk_pcie clock\n");
364 err
= clk_prepare_enable(rockchip
->aclk_perf_pcie
);
366 dev_err(dev
, "unable to enable aclk_perf_pcie clock\n");
367 goto err_aclk_perf_pcie
;
370 err
= clk_prepare_enable(rockchip
->hclk_pcie
);
372 dev_err(dev
, "unable to enable hclk_pcie clock\n");
376 err
= clk_prepare_enable(rockchip
->clk_pcie_pm
);
378 dev_err(dev
, "unable to enable clk_pcie_pm clock\n");
379 goto err_clk_pcie_pm
;
385 clk_disable_unprepare(rockchip
->hclk_pcie
);
387 clk_disable_unprepare(rockchip
->aclk_perf_pcie
);
389 clk_disable_unprepare(rockchip
->aclk_pcie
);
392 EXPORT_SYMBOL_GPL(rockchip_pcie_enable_clocks
);
394 void rockchip_pcie_disable_clocks(void *data
)
396 struct rockchip_pcie
*rockchip
= data
;
398 clk_disable_unprepare(rockchip
->clk_pcie_pm
);
399 clk_disable_unprepare(rockchip
->hclk_pcie
);
400 clk_disable_unprepare(rockchip
->aclk_perf_pcie
);
401 clk_disable_unprepare(rockchip
->aclk_pcie
);
403 EXPORT_SYMBOL_GPL(rockchip_pcie_disable_clocks
);
405 void rockchip_pcie_cfg_configuration_accesses(
406 struct rockchip_pcie
*rockchip
, u32 type
)
410 /* Configuration Accesses for region 0 */
411 rockchip_pcie_write(rockchip
, 0x0, PCIE_RC_BAR_CONF
);
413 rockchip_pcie_write(rockchip
,
414 (RC_REGION_0_ADDR_TRANS_L
+ RC_REGION_0_PASS_BITS
),
415 PCIE_CORE_OB_REGION_ADDR0
);
416 rockchip_pcie_write(rockchip
, RC_REGION_0_ADDR_TRANS_H
,
417 PCIE_CORE_OB_REGION_ADDR1
);
418 ob_desc_0
= rockchip_pcie_read(rockchip
, PCIE_CORE_OB_REGION_DESC0
);
419 ob_desc_0
&= ~(RC_REGION_0_TYPE_MASK
);
420 ob_desc_0
|= (type
| (0x1 << 23));
421 rockchip_pcie_write(rockchip
, ob_desc_0
, PCIE_CORE_OB_REGION_DESC0
);
422 rockchip_pcie_write(rockchip
, 0x0, PCIE_CORE_OB_REGION_DESC1
);
424 EXPORT_SYMBOL_GPL(rockchip_pcie_cfg_configuration_accesses
);