Skip to content

Commit f0e2cf7

Browse files
committed
phy: pipe3: insert delay to enumerate in GEN2 mode
8-bit delay value (0xF1) is required for GEN2 devices to be enumerated consistently. Added an API to be called from PHY drivers to set this delay value and called it from PIPE3 driver to set the delay value. Signed-off-by: Kishon Vijay Abraham I <kishon@ti.com> Reviewed-by: Roger Quadros <rogerq@ti.com>
1 parent 99bbd48 commit f0e2cf7

File tree

4 files changed

+71
-7
lines changed

4 files changed

+71
-7
lines changed

Documentation/devicetree/bindings/phy/ti-phy.txt

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -9,15 +9,17 @@ Required properties:
99
e.g. USB2_PHY on OMAP5.
1010
"ti,control-phy-pipe3" - if it has DPLL and individual Rx & Tx power control
1111
e.g. USB3 PHY and SATA PHY on OMAP5.
12+
"ti,control-phy-pcie" - for pcie to support external clock for pcie and to
13+
set PCS delay value.
14+
e.g. PCIE PHY in DRA7x
1215
"ti,control-phy-usb2-dra7" - if it has power down register like USB2 PHY on
1316
DRA7 platform.
1417
"ti,control-phy-usb2-am437" - if it has power down register like USB2 PHY on
1518
AM437 platform.
16-
- reg : Address and length of the register set for the device. It contains
17-
the address of "otghs_control" for control-phy-otghs or "power" register
18-
for other types.
19-
- reg-names: should be "otghs_control" control-phy-otghs and "power" for
20-
other types.
19+
- reg : register ranges as listed in the reg-names property
20+
- reg-names: "otghs_control" for control-phy-otghs
21+
"power", "pcie_pcs" and "control_sma" for control-phy-pcie
22+
"power" for all other types
2123

2224
omap_control_usb: omap-control-usb@4a002300 {
2325
compatible = "ti,control-phy-otghs";

drivers/phy/phy-omap-control.c

Lines changed: 51 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,41 @@
2626
#include <linux/clk.h>
2727
#include <linux/phy/omap_control_phy.h>
2828

29+
/**
30+
* omap_control_pcie_pcs - set the PCS delay count
31+
* @dev: the control module device
32+
* @id: index of the pcie PHY (should be 1 or 2)
33+
* @delay: 8 bit delay value
34+
*/
35+
void omap_control_pcie_pcs(struct device *dev, u8 id, u8 delay)
36+
{
37+
u32 val;
38+
struct omap_control_phy *control_phy;
39+
40+
if (IS_ERR(dev) || !dev) {
41+
pr_err("%s: invalid device\n", __func__);
42+
return;
43+
}
44+
45+
control_phy = dev_get_drvdata(dev);
46+
if (!control_phy) {
47+
dev_err(dev, "%s: invalid control phy device\n", __func__);
48+
return;
49+
}
50+
51+
if (control_phy->type != OMAP_CTRL_TYPE_PCIE) {
52+
dev_err(dev, "%s: unsupported operation\n", __func__);
53+
return;
54+
}
55+
56+
val = readl(control_phy->pcie_pcs);
57+
val &= ~(OMAP_CTRL_PCIE_PCS_MASK <<
58+
(id * OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT));
59+
val |= delay << (id * OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT);
60+
writel(val, control_phy->pcie_pcs);
61+
}
62+
EXPORT_SYMBOL_GPL(omap_control_pcie_pcs);
63+
2964
/**
3065
* omap_control_phy_power - power on/off the phy using control module reg
3166
* @dev: the control module device
@@ -61,6 +96,7 @@ void omap_control_phy_power(struct device *dev, int on)
6196
val |= OMAP_CTRL_DEV_PHY_PD;
6297
break;
6398

99+
case OMAP_CTRL_TYPE_PCIE:
64100
case OMAP_CTRL_TYPE_PIPE3:
65101
rate = clk_get_rate(control_phy->sys_clk);
66102
rate = rate/1000000;
@@ -211,6 +247,7 @@ EXPORT_SYMBOL_GPL(omap_control_usb_set_mode);
211247
static const enum omap_control_phy_type otghs_data = OMAP_CTRL_TYPE_OTGHS;
212248
static const enum omap_control_phy_type usb2_data = OMAP_CTRL_TYPE_USB2;
213249
static const enum omap_control_phy_type pipe3_data = OMAP_CTRL_TYPE_PIPE3;
250+
static const enum omap_control_phy_type pcie_data = OMAP_CTRL_TYPE_PCIE;
214251
static const enum omap_control_phy_type dra7usb2_data = OMAP_CTRL_TYPE_DRA7USB2;
215252
static const enum omap_control_phy_type am437usb2_data = OMAP_CTRL_TYPE_AM437USB2;
216253

@@ -227,6 +264,10 @@ static const struct of_device_id omap_control_phy_id_table[] = {
227264
.compatible = "ti,control-phy-pipe3",
228265
.data = &pipe3_data,
229266
},
267+
{
268+
.compatible = "ti,control-phy-pcie",
269+
.data = &pcie_data,
270+
},
230271
{
231272
.compatible = "ti,control-phy-usb2-dra7",
232273
.data = &dra7usb2_data,
@@ -279,7 +320,8 @@ static int omap_control_phy_probe(struct platform_device *pdev)
279320
}
280321
}
281322

282-
if (control_phy->type == OMAP_CTRL_TYPE_PIPE3) {
323+
if (control_phy->type == OMAP_CTRL_TYPE_PIPE3 ||
324+
control_phy->type == OMAP_CTRL_TYPE_PCIE) {
283325
control_phy->sys_clk = devm_clk_get(control_phy->dev,
284326
"sys_clkin");
285327
if (IS_ERR(control_phy->sys_clk)) {
@@ -288,6 +330,14 @@ static int omap_control_phy_probe(struct platform_device *pdev)
288330
}
289331
}
290332

333+
if (control_phy->type == OMAP_CTRL_TYPE_PCIE) {
334+
res = platform_get_resource_byname(pdev, IORESOURCE_MEM,
335+
"pcie_pcs");
336+
control_phy->pcie_pcs = devm_ioremap_resource(&pdev->dev, res);
337+
if (IS_ERR(control_phy->pcie_pcs))
338+
return PTR_ERR(control_phy->pcie_pcs);
339+
}
340+
291341
dev_set_drvdata(control_phy->dev, control_phy);
292342

293343
return 0;

drivers/phy/phy-ti-pipe3.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -217,8 +217,10 @@ static int ti_pipe3_init(struct phy *x)
217217
u32 val;
218218
int ret = 0;
219219

220-
if (of_device_is_compatible(phy->dev->of_node, "ti,phy-pipe3-pcie"))
220+
if (of_device_is_compatible(phy->dev->of_node, "ti,phy-pipe3-pcie")) {
221+
omap_control_pcie_pcs(phy->control_dev, phy->id, 0xF1);
221222
return 0;
223+
}
222224

223225
/* Bring it out of IDLE if it is IDLE */
224226
val = ti_pipe3_readl(phy->pll_ctrl_base, PLL_CONFIGURATION2);

include/linux/phy/omap_control_phy.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ enum omap_control_phy_type {
2323
OMAP_CTRL_TYPE_OTGHS = 1, /* Mailbox OTGHS_CONTROL */
2424
OMAP_CTRL_TYPE_USB2, /* USB2_PHY, power down in CONTROL_DEV_CONF */
2525
OMAP_CTRL_TYPE_PIPE3, /* PIPE3 PHY, DPLL & seperate Rx/Tx power */
26+
OMAP_CTRL_TYPE_PCIE, /* RX TX control of ACSPCIE */
2627
OMAP_CTRL_TYPE_DRA7USB2, /* USB2 PHY, power and power_aux e.g. DRA7 */
2728
OMAP_CTRL_TYPE_AM437USB2, /* USB2 PHY, power e.g. AM437x */
2829
};
@@ -33,6 +34,7 @@ struct omap_control_phy {
3334
u32 __iomem *otghs_control;
3435
u32 __iomem *power;
3536
u32 __iomem *power_aux;
37+
u32 __iomem *pcie_pcs;
3638

3739
struct clk *sys_clk;
3840

@@ -63,6 +65,9 @@ enum omap_control_usb_mode {
6365
#define OMAP_CTRL_PIPE3_PHY_TX_RX_POWERON 0x3
6466
#define OMAP_CTRL_PIPE3_PHY_TX_RX_POWEROFF 0x0
6567

68+
#define OMAP_CTRL_PCIE_PCS_MASK 0xff
69+
#define OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT 0x8
70+
6671
#define OMAP_CTRL_USB2_PHY_PD BIT(28)
6772

6873
#define AM437X_CTRL_USB2_PHY_PD BIT(0)
@@ -74,6 +79,7 @@ enum omap_control_usb_mode {
7479
void omap_control_phy_power(struct device *dev, int on);
7580
void omap_control_usb_set_mode(struct device *dev,
7681
enum omap_control_usb_mode mode);
82+
void omap_control_pcie_pcs(struct device *dev, u8 id, u8 delay);
7783
#else
7884

7985
static inline void omap_control_phy_power(struct device *dev, int on)
@@ -84,6 +90,10 @@ static inline void omap_control_usb_set_mode(struct device *dev,
8490
enum omap_control_usb_mode mode)
8591
{
8692
}
93+
94+
static inline void omap_control_pcie_pcs(struct device *dev, u8 id, u8 delay)
95+
{
96+
}
8797
#endif
8898

8999
#endif /* __OMAP_CONTROL_PHY_H__ */

0 commit comments

Comments
 (0)