Linux-mediatek Archive on lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 1/6] phy: phy-mt65xx-usb3: add reference clock of usb3 analog phy
From: Chunfeng Yun @ 2017-01-18  5:51 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Matthias Brugger, Felipe Balbi, Chunfeng Yun, linux-kernel,
	linux-arm-kernel, linux-usb, linux-mediatek

usually, the reference clock of usb3 analog phy comes from
26M oscillator directly, but some SoCs are not, add it for
compatibility.

Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
---
 drivers/phy/phy-mt65xx-usb3.c |   36 ++++++++++++++++++++++++++++--------
 1 file changed, 28 insertions(+), 8 deletions(-)

diff --git a/drivers/phy/phy-mt65xx-usb3.c b/drivers/phy/phy-mt65xx-usb3.c
index d972067..fc9a4f0 100644
--- a/drivers/phy/phy-mt65xx-usb3.c
+++ b/drivers/phy/phy-mt65xx-usb3.c
@@ -149,7 +149,8 @@ struct mt65xx_phy_instance {
 struct mt65xx_u3phy {
 	struct device *dev;
 	void __iomem *sif_base;	/* include sif2, but exclude port's */
-	struct clk *u3phya_ref;	/* reference clock of usb3 anolog phy */
+	struct clk *u2ref_clk;	/* reference clock of u2 analog phy */
+	struct clk *u3ref_clk;	/* reference clock of u3 analog phy */
 	const struct mt65xx_phy_pdata *pdata;
 	struct mt65xx_phy_instance **phys;
 	int nphys;
@@ -429,11 +430,17 @@ static int mt65xx_phy_init(struct phy *phy)
 {
 	struct mt65xx_phy_instance *instance = phy_get_drvdata(phy);
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
+	struct clk *ref_clk;
 	int ret;
 
-	ret = clk_prepare_enable(u3phy->u3phya_ref);
+	if (instance->type == PHY_TYPE_USB2)
+		ref_clk = u3phy->u2ref_clk;
+	else
+		ref_clk = u3phy->u3ref_clk;
+
+	ret = clk_prepare_enable(ref_clk);
 	if (ret) {
-		dev_err(u3phy->dev, "failed to enable u3phya_ref\n");
+		dev_err(u3phy->dev, "failed to enable ref clk\n");
 		return ret;
 	}
 
@@ -464,9 +471,16 @@ static int mt65xx_phy_exit(struct phy *phy)
 {
 	struct mt65xx_phy_instance *instance = phy_get_drvdata(phy);
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
+	struct clk *ref_clk;
 
 	phy_instance_exit(u3phy, instance);
-	clk_disable_unprepare(u3phy->u3phya_ref);
+
+	if (instance->type == PHY_TYPE_USB2)
+		ref_clk = u3phy->u2ref_clk;
+	else
+		ref_clk = u3phy->u3ref_clk;
+
+	clk_disable_unprepare(ref_clk);
 	return 0;
 }
 
@@ -566,10 +580,16 @@ static int mt65xx_u3phy_probe(struct platform_device *pdev)
 		return PTR_ERR(u3phy->sif_base);
 	}
 
-	u3phy->u3phya_ref = devm_clk_get(dev, "u3phya_ref");
-	if (IS_ERR(u3phy->u3phya_ref)) {
-		dev_err(dev, "error to get u3phya_ref\n");
-		return PTR_ERR(u3phy->u3phya_ref);
+	u3phy->u2ref_clk = devm_clk_get(dev, "u2ref_clk");
+	if (IS_ERR(u3phy->u2ref_clk)) {
+		dev_err(dev, "failed to get u2ref_clk\n");
+		return PTR_ERR(u3phy->u2ref_clk);
+	}
+
+	u3phy->u3ref_clk = devm_clk_get(dev, "u3ref_clk");
+	if (IS_ERR(u3phy->u3ref_clk)) {
+		dev_err(dev, "failed to get u3ref_clk\n");
+		return PTR_ERR(u3phy->u3ref_clk);
 	}
 
 	port = 0;
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 2/6] phy: phy-mt65xx-usb3: split SuperSpeed port into two ones
From: Chunfeng Yun @ 2017-01-18  5:51 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Felipe Balbi, linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Chunfeng Yun,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Matthias Brugger,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r
In-Reply-To: <1484718665-11584-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

Currently usb3 port in fact includes two sub-ports, but it is not
flexible for some cases, such as following one:
    usb3 port0 includes u2port0 and u3port0;
    usb2 port0 includes u2port1;
If wants to support only HS, we can use u2port0 or u2port1, when
select u2port0, u3port0 is not needed;
If wants to support SS, we can compound u2port0 and u3port0,
or u2port1 and u3port0, if select latter one, u2port0 is not needed.

So it's more flexible to split usb3 port into two ones and also try
best to save power by disabling unnecessary ports.

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 drivers/phy/phy-mt65xx-usb3.c |  124 ++++++++++++++++++++---------------------
 1 file changed, 61 insertions(+), 63 deletions(-)

diff --git a/drivers/phy/phy-mt65xx-usb3.c b/drivers/phy/phy-mt65xx-usb3.c
index fc9a4f0..c187a3b 100644
--- a/drivers/phy/phy-mt65xx-usb3.c
+++ b/drivers/phy/phy-mt65xx-usb3.c
@@ -30,11 +30,11 @@
 #define SSUSB_SIFSLV_SPLLC		0x0000
 #define SSUSB_SIFSLV_U2FREQ		0x0100
 
-/* offsets of sub-segment in each port registers */
+/* offsets of banks in each u2phy registers */
 #define SSUSB_SIFSLV_U2PHY_COM_BASE	0x0000
-#define SSUSB_SIFSLV_U3PHYD_BASE	0x0100
-#define SSUSB_USB30_PHYA_SIV_B_BASE	0x0300
-#define SSUSB_SIFSLV_U3PHYA_DA_BASE	0x0400
+/* offsets of banks in each u3phy registers */
+#define SSUSB_SIFSLV_U3PHYD_BASE	0x0000
+#define SSUSB_SIFSLV_U3PHYA_BASE	0x0200
 
 #define U3P_USBPHYACR0		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0000)
 #define PA0_RG_U2PLL_FORCE_ON		BIT(15)
@@ -49,7 +49,6 @@
 #define PA5_RG_U2_HS_100U_U3_EN	BIT(11)
 
 #define U3P_USBPHYACR6		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0018)
-#define PA6_RG_U2_ISO_EN		BIT(31)
 #define PA6_RG_U2_BC11_SW_EN		BIT(23)
 #define PA6_RG_U2_OTG_VBUSCMP_EN	BIT(20)
 #define PA6_RG_U2_SQTH		GENMASK(3, 0)
@@ -91,18 +90,18 @@
 #define P2C_RG_SESSEND			BIT(4)
 #define P2C_RG_AVALID			BIT(2)
 
-#define U3P_U3_PHYA_REG0	(SSUSB_USB30_PHYA_SIV_B_BASE + 0x0000)
+#define U3P_U3_PHYA_REG0	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0000)
 #define P3A_RG_U3_VUSB10_ON		BIT(5)
 
-#define U3P_U3_PHYA_REG6	(SSUSB_USB30_PHYA_SIV_B_BASE + 0x0018)
+#define U3P_U3_PHYA_REG6	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0018)
 #define P3A_RG_TX_EIDLE_CM		GENMASK(31, 28)
 #define P3A_RG_TX_EIDLE_CM_VAL(x)	((0xf & (x)) << 28)
 
-#define U3P_U3_PHYA_REG9	(SSUSB_USB30_PHYA_SIV_B_BASE + 0x0024)
+#define U3P_U3_PHYA_REG9	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0024)
 #define P3A_RG_RX_DAC_MUX		GENMASK(5, 1)
 #define P3A_RG_RX_DAC_MUX_VAL(x)	((0x1f & (x)) << 1)
 
-#define U3P_U3PHYA_DA_REG0	(SSUSB_SIFSLV_U3PHYA_DA_BASE + 0x0000)
+#define U3P_U3PHYA_DA_REG0	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0100)
 #define P3A_RG_XTAL_EXT_EN_U3		GENMASK(11, 10)
 #define P3A_RG_XTAL_EXT_EN_U3_VAL(x)	((0x3 & (x)) << 10)
 
@@ -148,7 +147,7 @@ struct mt65xx_phy_instance {
 
 struct mt65xx_u3phy {
 	struct device *dev;
-	void __iomem *sif_base;	/* include sif2, but exclude port's */
+	void __iomem *sif_base;	/* only shared sif */
 	struct clk *u2ref_clk;	/* reference clock of u2 analog phy */
 	struct clk *u3ref_clk;	/* reference clock of u3 analog phy */
 	const struct mt65xx_phy_pdata *pdata;
@@ -179,7 +178,7 @@ static void hs_slew_rate_calibrate(struct mt65xx_u3phy *u3phy,
 	tmp = readl(sif_base + U3P_U2FREQ_FMCR0);
 	tmp &= ~(P2F_RG_CYCLECNT | P2F_RG_MONCLK_SEL);
 	tmp |= P2F_RG_CYCLECNT_VAL(U3P_FM_DET_CYCLE_CNT);
-	tmp |= P2F_RG_MONCLK_SEL_VAL(instance->index);
+	tmp |= P2F_RG_MONCLK_SEL_VAL(instance->index >> 1);
 	writel(tmp, sif_base + U3P_U2FREQ_FMCR0);
 
 	/* enable frequency meter */
@@ -227,6 +226,41 @@ static void hs_slew_rate_calibrate(struct mt65xx_u3phy *u3phy,
 	writel(tmp, instance->port_base + U3P_USBPHYACR5);
 }
 
+static void u3_phy_instance_init(struct mt65xx_u3phy *u3phy,
+	struct mt65xx_phy_instance *instance)
+{
+	void __iomem *port_base = instance->port_base;
+	u32 tmp;
+
+	/* gating PCIe Analog XTAL clock */
+	tmp = readl(u3phy->sif_base + U3P_XTALCTL3);
+	tmp |= XC3_RG_U3_XTAL_RX_PWD | XC3_RG_U3_FRC_XTAL_RX_PWD;
+	writel(tmp, u3phy->sif_base + U3P_XTALCTL3);
+
+	/* gating XSQ */
+	tmp = readl(port_base + U3P_U3PHYA_DA_REG0);
+	tmp &= ~P3A_RG_XTAL_EXT_EN_U3;
+	tmp |= P3A_RG_XTAL_EXT_EN_U3_VAL(2);
+	writel(tmp, port_base + U3P_U3PHYA_DA_REG0);
+
+	tmp = readl(port_base + U3P_U3_PHYA_REG9);
+	tmp &= ~P3A_RG_RX_DAC_MUX;
+	tmp |= P3A_RG_RX_DAC_MUX_VAL(4);
+	writel(tmp, port_base + U3P_U3_PHYA_REG9);
+
+	tmp = readl(port_base + U3P_U3_PHYA_REG6);
+	tmp &= ~P3A_RG_TX_EIDLE_CM;
+	tmp |= P3A_RG_TX_EIDLE_CM_VAL(0xe);
+	writel(tmp, port_base + U3P_U3_PHYA_REG6);
+
+	tmp = readl(port_base + U3P_PHYD_CDR1);
+	tmp &= ~(P3D_RG_CDR_BIR_LTD0 | P3D_RG_CDR_BIR_LTD1);
+	tmp |= P3D_RG_CDR_BIR_LTD0_VAL(0xc) | P3D_RG_CDR_BIR_LTD1_VAL(0x3);
+	writel(tmp, port_base + U3P_PHYD_CDR1);
+
+	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, instance->index);
+}
+
 static void phy_instance_init(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
@@ -276,26 +310,6 @@ static void phy_instance_init(struct mt65xx_u3phy *u3phy,
 	tmp |= PA6_RG_U2_SQTH_VAL(2);
 	writel(tmp, port_base + U3P_USBPHYACR6);
 
-	tmp = readl(port_base + U3P_U3PHYA_DA_REG0);
-	tmp &= ~P3A_RG_XTAL_EXT_EN_U3;
-	tmp |= P3A_RG_XTAL_EXT_EN_U3_VAL(2);
-	writel(tmp, port_base + U3P_U3PHYA_DA_REG0);
-
-	tmp = readl(port_base + U3P_U3_PHYA_REG9);
-	tmp &= ~P3A_RG_RX_DAC_MUX;
-	tmp |= P3A_RG_RX_DAC_MUX_VAL(4);
-	writel(tmp, port_base + U3P_U3_PHYA_REG9);
-
-	tmp = readl(port_base + U3P_U3_PHYA_REG6);
-	tmp &= ~P3A_RG_TX_EIDLE_CM;
-	tmp |= P3A_RG_TX_EIDLE_CM_VAL(0xe);
-	writel(tmp, port_base + U3P_U3_PHYA_REG6);
-
-	tmp = readl(port_base + U3P_PHYD_CDR1);
-	tmp &= ~(P3D_RG_CDR_BIR_LTD0 | P3D_RG_CDR_BIR_LTD1);
-	tmp |= P3D_RG_CDR_BIR_LTD0_VAL(0xc) | P3D_RG_CDR_BIR_LTD1_VAL(0x3);
-	writel(tmp, port_base + U3P_PHYD_CDR1);
-
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, index);
 }
 
@@ -306,13 +320,6 @@ static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 	u32 index = instance->index;
 	u32 tmp;
 
-	if (!index) {
-		/* Set RG_SSUSB_VUSB10_ON as 1 after VUSB10 ready */
-		tmp = readl(port_base + U3P_U3_PHYA_REG0);
-		tmp |= P3A_RG_U3_VUSB10_ON;
-		writel(tmp, port_base + U3P_U3_PHYA_REG0);
-	}
-
 	/* (force_suspendm=0) (let suspendm=1, enable usb 480MHz pll) */
 	tmp = readl(port_base + U3P_U2PHYDTM0);
 	tmp &= ~(P2C_FORCE_SUSPENDM | P2C_RG_XCVRSEL);
@@ -325,10 +332,6 @@ static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 	writel(tmp, port_base + U3P_USBPHYACR6);
 
 	if (!index) {
-		tmp = readl(u3phy->sif_base + U3P_XTALCTL3);
-		tmp |= XC3_RG_U3_XTAL_RX_PWD | XC3_RG_U3_FRC_XTAL_RX_PWD;
-		writel(tmp, u3phy->sif_base + U3P_XTALCTL3);
-
 		/* switch 100uA current to SSUSB */
 		tmp = readl(port_base + U3P_USBPHYACR5);
 		tmp |= PA5_RG_U2_HS_100U_U3_EN;
@@ -340,12 +343,6 @@ static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 	tmp &= ~P2C_RG_SESSEND;
 	writel(tmp, port_base + U3P_U2PHYDTM1);
 
-	/* USB 2.0 slew rate calibration */
-	tmp = readl(port_base + U3P_USBPHYACR5);
-	tmp &= ~PA5_RG_U2_HSTX_SRCTRL;
-	tmp |= PA5_RG_U2_HSTX_SRCTRL_VAL(4);
-	writel(tmp, port_base + U3P_USBPHYACR5);
-
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
 		tmp = readl(port_base + U3D_U2PHYDCR0);
 		tmp |= P2C_RG_SIF_U2PLL_FORCE_ON;
@@ -393,12 +390,6 @@ static void phy_instance_power_off(struct mt65xx_u3phy *u3phy,
 	tmp |= P2C_RG_SESSEND;
 	writel(tmp, port_base + U3P_U2PHYDTM1);
 
-	if (!index) {
-		tmp = readl(port_base + U3P_U3_PHYA_REG0);
-		tmp &= ~P3A_RG_U3_VUSB10_ON;
-		writel(tmp, port_base + U3P_U3_PHYA_REG0);
-	}
-
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
 		tmp = readl(port_base + U3D_U2PHYDCR0);
 		tmp &= ~P2C_RG_SIF_U2PLL_FORCE_ON;
@@ -444,7 +435,11 @@ static int mt65xx_phy_init(struct phy *phy)
 		return ret;
 	}
 
-	phy_instance_init(u3phy, instance);
+	if (instance->type == PHY_TYPE_USB2)
+		phy_instance_init(u3phy, instance);
+	else
+		u3_phy_instance_init(u3phy, instance);
+
 	return 0;
 }
 
@@ -453,8 +448,10 @@ static int mt65xx_phy_power_on(struct phy *phy)
 	struct mt65xx_phy_instance *instance = phy_get_drvdata(phy);
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
 
-	phy_instance_power_on(u3phy, instance);
-	hs_slew_rate_calibrate(u3phy, instance);
+	if (instance->type == PHY_TYPE_USB2) {
+		phy_instance_power_on(u3phy, instance);
+		hs_slew_rate_calibrate(u3phy, instance);
+	}
 	return 0;
 }
 
@@ -463,7 +460,9 @@ static int mt65xx_phy_power_off(struct phy *phy)
 	struct mt65xx_phy_instance *instance = phy_get_drvdata(phy);
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
 
-	phy_instance_power_off(u3phy, instance);
+	if (instance->type == PHY_TYPE_USB2)
+		phy_instance_power_off(u3phy, instance);
+
 	return 0;
 }
 
@@ -473,13 +472,12 @@ static int mt65xx_phy_exit(struct phy *phy)
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
 	struct clk *ref_clk;
 
-	phy_instance_exit(u3phy, instance);
-
-	if (instance->type == PHY_TYPE_USB2)
+	if (instance->type == PHY_TYPE_USB2) {
+		phy_instance_exit(u3phy, instance);
 		ref_clk = u3phy->u2ref_clk;
-	else
+	} else {
 		ref_clk = u3phy->u3ref_clk;
-
+	}
 	clk_disable_unprepare(ref_clk);
 	return 0;
 }
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 3/6] phy: phy-mt65xx-usb3: add support for mt2712 platform
From: Chunfeng Yun @ 2017-01-18  5:51 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Felipe Balbi, linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Chunfeng Yun,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Matthias Brugger,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r
In-Reply-To: <1484718665-11584-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

There are some variations from mt2701 to mt2712:
1. banks shared by multiple ports are put back into each port,
    such as SPLLC and U2FREQ;
2. add a new bank MISC for u2port, and CHIP for u3port;
3. bank's offset in each port are also rearranged;

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 drivers/phy/phy-mt65xx-usb3.c |  326 ++++++++++++++++++++++++++---------------
 1 file changed, 208 insertions(+), 118 deletions(-)

diff --git a/drivers/phy/phy-mt65xx-usb3.c b/drivers/phy/phy-mt65xx-usb3.c
index c187a3b..d515c69 100644
--- a/drivers/phy/phy-mt65xx-usb3.c
+++ b/drivers/phy/phy-mt65xx-usb3.c
@@ -23,46 +23,54 @@
 #include <linux/phy/phy.h>
 #include <linux/platform_device.h>
 
-/*
- * for sifslv2 register, but exclude port's;
- * relative to USB3_SIF2_BASE base address
- */
-#define SSUSB_SIFSLV_SPLLC		0x0000
-#define SSUSB_SIFSLV_U2FREQ		0x0100
-
-/* offsets of banks in each u2phy registers */
-#define SSUSB_SIFSLV_U2PHY_COM_BASE	0x0000
-/* offsets of banks in each u3phy registers */
-#define SSUSB_SIFSLV_U3PHYD_BASE	0x0000
-#define SSUSB_SIFSLV_U3PHYA_BASE	0x0200
-
-#define U3P_USBPHYACR0		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0000)
+/* version V1 sub-banks offset base address */
+/* banks shared by multiple phys */
+#define SSUSB_SIFSLV_V1_SPLLC		0x000	/* shared by u3 phys */
+#define SSUSB_SIFSLV_V1_U2FREQ		0x100	/* shared by u2 phys */
+/* u2 phy bank */
+#define SSUSB_SIFSLV_V1_U2PHY_COM	0x000
+/* u3 phy banks */
+#define SSUSB_SIFSLV_V1_U3PHYD		0x000
+#define SSUSB_SIFSLV_V1_U3PHYA		0x200
+
+/* version V2 sub-banks offset base address */
+/* u2 phy banks */
+#define SSUSB_SIFSLV_V2_MISC		0x000
+#define SSUSB_SIFSLV_V2_U2FREQ		0x100
+#define SSUSB_SIFSLV_V2_U2PHY_COM	0x300
+/* u3 phy banks */
+#define SSUSB_SIFSLV_V2_SPLLC		0x000
+#define SSUSB_SIFSLV_V2_CHIP		0x100
+#define SSUSB_SIFSLV_V2_U3PHYD		0x200
+#define SSUSB_SIFSLV_V2_U3PHYA		0x400
+
+#define U3P_USBPHYACR0		0x000
 #define PA0_RG_U2PLL_FORCE_ON		BIT(15)
 
-#define U3P_USBPHYACR2		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0008)
+#define U3P_USBPHYACR2		0x008
 #define PA2_RG_SIF_U2PLL_FORCE_EN	BIT(18)
 
-#define U3P_USBPHYACR5		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0014)
+#define U3P_USBPHYACR5		0x014
 #define PA5_RG_U2_HSTX_SRCAL_EN	BIT(15)
 #define PA5_RG_U2_HSTX_SRCTRL		GENMASK(14, 12)
 #define PA5_RG_U2_HSTX_SRCTRL_VAL(x)	((0x7 & (x)) << 12)
 #define PA5_RG_U2_HS_100U_U3_EN	BIT(11)
 
-#define U3P_USBPHYACR6		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0018)
+#define U3P_USBPHYACR6		0x018
 #define PA6_RG_U2_BC11_SW_EN		BIT(23)
 #define PA6_RG_U2_OTG_VBUSCMP_EN	BIT(20)
 #define PA6_RG_U2_SQTH		GENMASK(3, 0)
 #define PA6_RG_U2_SQTH_VAL(x)	(0xf & (x))
 
-#define U3P_U2PHYACR4		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0020)
+#define U3P_U2PHYACR4		0x020
 #define P2C_RG_USB20_GPIO_CTL		BIT(9)
 #define P2C_USB20_GPIO_MODE		BIT(8)
 #define P2C_U2_GPIO_CTR_MSK	(P2C_RG_USB20_GPIO_CTL | P2C_USB20_GPIO_MODE)
 
-#define U3D_U2PHYDCR0		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0060)
+#define U3D_U2PHYDCR0		0x060
 #define P2C_RG_SIF_U2PLL_FORCE_ON	BIT(24)
 
-#define U3P_U2PHYDTM0		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0068)
+#define U3P_U2PHYDTM0		0x068
 #define P2C_FORCE_UART_EN		BIT(26)
 #define P2C_FORCE_DATAIN		BIT(23)
 #define P2C_FORCE_DM_PULLDOWN		BIT(21)
@@ -84,47 +92,44 @@
 		P2C_FORCE_TERMSEL | P2C_RG_DMPULLDOWN | \
 		P2C_RG_DPPULLDOWN | P2C_RG_TERMSEL)
 
-#define U3P_U2PHYDTM1		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x006C)
+#define U3P_U2PHYDTM1		0x06C
 #define P2C_RG_UART_EN			BIT(16)
 #define P2C_RG_VBUSVALID		BIT(5)
 #define P2C_RG_SESSEND			BIT(4)
 #define P2C_RG_AVALID			BIT(2)
 
-#define U3P_U3_PHYA_REG0	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0000)
-#define P3A_RG_U3_VUSB10_ON		BIT(5)
-
-#define U3P_U3_PHYA_REG6	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0018)
+#define U3P_U3_PHYA_REG6	0x018
 #define P3A_RG_TX_EIDLE_CM		GENMASK(31, 28)
 #define P3A_RG_TX_EIDLE_CM_VAL(x)	((0xf & (x)) << 28)
 
-#define U3P_U3_PHYA_REG9	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0024)
+#define U3P_U3_PHYA_REG9	0x024
 #define P3A_RG_RX_DAC_MUX		GENMASK(5, 1)
 #define P3A_RG_RX_DAC_MUX_VAL(x)	((0x1f & (x)) << 1)
 
-#define U3P_U3PHYA_DA_REG0	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0100)
+#define U3P_U3_PHYA_DA_REG0	0x100
 #define P3A_RG_XTAL_EXT_EN_U3		GENMASK(11, 10)
 #define P3A_RG_XTAL_EXT_EN_U3_VAL(x)	((0x3 & (x)) << 10)
 
-#define U3P_PHYD_CDR1		(SSUSB_SIFSLV_U3PHYD_BASE + 0x005c)
+#define U3P_U3_PHYD_CDR1		0x05c
 #define P3D_RG_CDR_BIR_LTD1		GENMASK(28, 24)
 #define P3D_RG_CDR_BIR_LTD1_VAL(x)	((0x1f & (x)) << 24)
 #define P3D_RG_CDR_BIR_LTD0		GENMASK(12, 8)
 #define P3D_RG_CDR_BIR_LTD0_VAL(x)	((0x1f & (x)) << 8)
 
-#define U3P_XTALCTL3		(SSUSB_SIFSLV_SPLLC + 0x0018)
+#define U3P_SPLLC_XTALCTL3		0x018
 #define XC3_RG_U3_XTAL_RX_PWD		BIT(9)
 #define XC3_RG_U3_FRC_XTAL_RX_PWD	BIT(8)
 
-#define U3P_U2FREQ_FMCR0	(SSUSB_SIFSLV_U2FREQ + 0x00)
+#define U3P_U2FREQ_FMCR0	0x00
 #define P2F_RG_MONCLK_SEL	GENMASK(27, 26)
 #define P2F_RG_MONCLK_SEL_VAL(x)	((0x3 & (x)) << 26)
 #define P2F_RG_FREQDET_EN	BIT(24)
 #define P2F_RG_CYCLECNT		GENMASK(23, 0)
 #define P2F_RG_CYCLECNT_VAL(x)	((P2F_RG_CYCLECNT) & (x))
 
-#define U3P_U2FREQ_VALUE	(SSUSB_SIFSLV_U2FREQ + 0x0c)
+#define U3P_U2FREQ_VALUE	0x0c
 
-#define U3P_U2FREQ_FMMONR1	(SSUSB_SIFSLV_U2FREQ + 0x10)
+#define U3P_U2FREQ_FMMONR1	0x10
 #define P2F_USB_FM_VALID	BIT(0)
 #define P2F_RG_FRCK_EN		BIT(8)
 
@@ -133,14 +138,37 @@
 #define U3P_SR_COEF_DIVISOR	1000
 #define U3P_FM_DET_CYCLE_CNT	1024
 
+enum mt_phy_version {
+	MT_PHY_V1 = 1,
+	MT_PHY_V2,
+};
+
 struct mt65xx_phy_pdata {
 	/* avoid RX sensitivity level degradation only for mt8173 */
 	bool avoid_rx_sen_degradation;
+	enum mt_phy_version version;
+};
+
+struct u2phy_banks {
+	void __iomem *misc;
+	void __iomem *fmreg;
+	void __iomem *com;
+};
+
+struct u3phy_banks {
+	void __iomem *spllc;
+	void __iomem *chip;
+	void __iomem *phyd; /* include u3phyd_bank2 */
+	void __iomem *phya; /* include u3phya_da */
 };
 
 struct mt65xx_phy_instance {
 	struct phy *phy;
 	void __iomem *port_base;
+	union {
+		struct u2phy_banks u2_banks;
+		struct u3phy_banks u3_banks;
+	};
 	u32 index;
 	u8 type;
 };
@@ -158,49 +186,53 @@ struct mt65xx_u3phy {
 static void hs_slew_rate_calibrate(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *sif_base = u3phy->sif_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *fmreg = u2_banks->fmreg;
+	void __iomem *com = u2_banks->com;
 	int calibration_val;
 	int fm_out;
 	u32 tmp;
 
 	/* enable USB ring oscillator */
-	tmp = readl(instance->port_base + U3P_USBPHYACR5);
+	tmp = readl(com + U3P_USBPHYACR5);
 	tmp |= PA5_RG_U2_HSTX_SRCAL_EN;
-	writel(tmp, instance->port_base + U3P_USBPHYACR5);
+	writel(tmp, com + U3P_USBPHYACR5);
 	udelay(1);
 
 	/*enable free run clock */
-	tmp = readl(sif_base + U3P_U2FREQ_FMMONR1);
+	tmp = readl(fmreg + U3P_U2FREQ_FMMONR1);
 	tmp |= P2F_RG_FRCK_EN;
-	writel(tmp, sif_base + U3P_U2FREQ_FMMONR1);
+	writel(tmp, fmreg + U3P_U2FREQ_FMMONR1);
 
 	/* set cycle count as 1024, and select u2 channel */
-	tmp = readl(sif_base + U3P_U2FREQ_FMCR0);
+	tmp = readl(fmreg + U3P_U2FREQ_FMCR0);
 	tmp &= ~(P2F_RG_CYCLECNT | P2F_RG_MONCLK_SEL);
 	tmp |= P2F_RG_CYCLECNT_VAL(U3P_FM_DET_CYCLE_CNT);
-	tmp |= P2F_RG_MONCLK_SEL_VAL(instance->index >> 1);
-	writel(tmp, sif_base + U3P_U2FREQ_FMCR0);
+	if (u3phy->pdata->version == MT_PHY_V1)
+		tmp |= P2F_RG_MONCLK_SEL_VAL(instance->index >> 1);
+
+	writel(tmp, fmreg + U3P_U2FREQ_FMCR0);
 
 	/* enable frequency meter */
-	tmp = readl(sif_base + U3P_U2FREQ_FMCR0);
+	tmp = readl(fmreg + U3P_U2FREQ_FMCR0);
 	tmp |= P2F_RG_FREQDET_EN;
-	writel(tmp, sif_base + U3P_U2FREQ_FMCR0);
+	writel(tmp, fmreg + U3P_U2FREQ_FMCR0);
 
 	/* ignore return value */
-	readl_poll_timeout(sif_base + U3P_U2FREQ_FMMONR1, tmp,
+	readl_poll_timeout(fmreg + U3P_U2FREQ_FMMONR1, tmp,
 		  (tmp & P2F_USB_FM_VALID), 10, 200);
 
-	fm_out = readl(sif_base + U3P_U2FREQ_VALUE);
+	fm_out = readl(fmreg + U3P_U2FREQ_VALUE);
 
 	/* disable frequency meter */
-	tmp = readl(sif_base + U3P_U2FREQ_FMCR0);
+	tmp = readl(fmreg + U3P_U2FREQ_FMCR0);
 	tmp &= ~P2F_RG_FREQDET_EN;
-	writel(tmp, sif_base + U3P_U2FREQ_FMCR0);
+	writel(tmp, fmreg + U3P_U2FREQ_FMCR0);
 
 	/*disable free run clock */
-	tmp = readl(sif_base + U3P_U2FREQ_FMMONR1);
+	tmp = readl(fmreg + U3P_U2FREQ_FMMONR1);
 	tmp &= ~P2F_RG_FRCK_EN;
-	writel(tmp, sif_base + U3P_U2FREQ_FMMONR1);
+	writel(tmp, fmreg + U3P_U2FREQ_FMMONR1);
 
 	if (fm_out) {
 		/* ( 1024 / FM_OUT ) x reference clock frequency x 0.028 */
@@ -215,48 +247,48 @@ static void hs_slew_rate_calibrate(struct mt65xx_u3phy *u3phy,
 		instance->index, fm_out, calibration_val);
 
 	/* set HS slew rate */
-	tmp = readl(instance->port_base + U3P_USBPHYACR5);
+	tmp = readl(com + U3P_USBPHYACR5);
 	tmp &= ~PA5_RG_U2_HSTX_SRCTRL;
 	tmp |= PA5_RG_U2_HSTX_SRCTRL_VAL(calibration_val);
-	writel(tmp, instance->port_base + U3P_USBPHYACR5);
+	writel(tmp, com + U3P_USBPHYACR5);
 
 	/* disable USB ring oscillator */
-	tmp = readl(instance->port_base + U3P_USBPHYACR5);
+	tmp = readl(com + U3P_USBPHYACR5);
 	tmp &= ~PA5_RG_U2_HSTX_SRCAL_EN;
-	writel(tmp, instance->port_base + U3P_USBPHYACR5);
+	writel(tmp, com + U3P_USBPHYACR5);
 }
 
 static void u3_phy_instance_init(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u3phy_banks *u3_banks = &instance->u3_banks;
 	u32 tmp;
 
 	/* gating PCIe Analog XTAL clock */
-	tmp = readl(u3phy->sif_base + U3P_XTALCTL3);
+	tmp = readl(u3_banks->spllc + U3P_SPLLC_XTALCTL3);
 	tmp |= XC3_RG_U3_XTAL_RX_PWD | XC3_RG_U3_FRC_XTAL_RX_PWD;
-	writel(tmp, u3phy->sif_base + U3P_XTALCTL3);
+	writel(tmp, u3_banks->spllc + U3P_SPLLC_XTALCTL3);
 
 	/* gating XSQ */
-	tmp = readl(port_base + U3P_U3PHYA_DA_REG0);
+	tmp = readl(u3_banks->phya + U3P_U3_PHYA_DA_REG0);
 	tmp &= ~P3A_RG_XTAL_EXT_EN_U3;
 	tmp |= P3A_RG_XTAL_EXT_EN_U3_VAL(2);
-	writel(tmp, port_base + U3P_U3PHYA_DA_REG0);
+	writel(tmp, u3_banks->phya + U3P_U3_PHYA_DA_REG0);
 
-	tmp = readl(port_base + U3P_U3_PHYA_REG9);
+	tmp = readl(u3_banks->phya + U3P_U3_PHYA_REG9);
 	tmp &= ~P3A_RG_RX_DAC_MUX;
 	tmp |= P3A_RG_RX_DAC_MUX_VAL(4);
-	writel(tmp, port_base + U3P_U3_PHYA_REG9);
+	writel(tmp, u3_banks->phya + U3P_U3_PHYA_REG9);
 
-	tmp = readl(port_base + U3P_U3_PHYA_REG6);
+	tmp = readl(u3_banks->phya + U3P_U3_PHYA_REG6);
 	tmp &= ~P3A_RG_TX_EIDLE_CM;
 	tmp |= P3A_RG_TX_EIDLE_CM_VAL(0xe);
-	writel(tmp, port_base + U3P_U3_PHYA_REG6);
+	writel(tmp, u3_banks->phya + U3P_U3_PHYA_REG6);
 
-	tmp = readl(port_base + U3P_PHYD_CDR1);
+	tmp = readl(u3_banks->phyd + U3P_U3_PHYD_CDR1);
 	tmp &= ~(P3D_RG_CDR_BIR_LTD0 | P3D_RG_CDR_BIR_LTD1);
 	tmp |= P3D_RG_CDR_BIR_LTD0_VAL(0xc) | P3D_RG_CDR_BIR_LTD1_VAL(0x3);
-	writel(tmp, port_base + U3P_PHYD_CDR1);
+	writel(tmp, u3_banks->phyd + U3P_U3_PHYD_CDR1);
 
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, instance->index);
 }
@@ -264,51 +296,52 @@ static void u3_phy_instance_init(struct mt65xx_u3phy *u3phy,
 static void phy_instance_init(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *com = u2_banks->com;
 	u32 index = instance->index;
 	u32 tmp;
 
 	/* switch to USB function. (system register, force ip into usb mode) */
-	tmp = readl(port_base + U3P_U2PHYDTM0);
+	tmp = readl(com + U3P_U2PHYDTM0);
 	tmp &= ~P2C_FORCE_UART_EN;
 	tmp |= P2C_RG_XCVRSEL_VAL(1) | P2C_RG_DATAIN_VAL(0);
-	writel(tmp, port_base + U3P_U2PHYDTM0);
+	writel(tmp, com + U3P_U2PHYDTM0);
 
-	tmp = readl(port_base + U3P_U2PHYDTM1);
+	tmp = readl(com + U3P_U2PHYDTM1);
 	tmp &= ~P2C_RG_UART_EN;
-	writel(tmp, port_base + U3P_U2PHYDTM1);
+	writel(tmp, com + U3P_U2PHYDTM1);
 
 	if (!index) {
-		tmp = readl(port_base + U3P_U2PHYACR4);
+		tmp = readl(com + U3P_U2PHYACR4);
 		tmp &= ~P2C_U2_GPIO_CTR_MSK;
-		writel(tmp, port_base + U3P_U2PHYACR4);
+		writel(tmp, com + U3P_U2PHYACR4);
 	}
 
 	if (u3phy->pdata->avoid_rx_sen_degradation) {
 		if (!index) {
-			tmp = readl(port_base + U3P_USBPHYACR2);
+			tmp = readl(com + U3P_USBPHYACR2);
 			tmp |= PA2_RG_SIF_U2PLL_FORCE_EN;
-			writel(tmp, port_base + U3P_USBPHYACR2);
+			writel(tmp, com + U3P_USBPHYACR2);
 
-			tmp = readl(port_base + U3D_U2PHYDCR0);
+			tmp = readl(com + U3D_U2PHYDCR0);
 			tmp &= ~P2C_RG_SIF_U2PLL_FORCE_ON;
-			writel(tmp, port_base + U3D_U2PHYDCR0);
+			writel(tmp, com + U3D_U2PHYDCR0);
 		} else {
-			tmp = readl(port_base + U3D_U2PHYDCR0);
+			tmp = readl(com + U3D_U2PHYDCR0);
 			tmp |= P2C_RG_SIF_U2PLL_FORCE_ON;
-			writel(tmp, port_base + U3D_U2PHYDCR0);
+			writel(tmp, com + U3D_U2PHYDCR0);
 
-			tmp = readl(port_base + U3P_U2PHYDTM0);
+			tmp = readl(com + U3P_U2PHYDTM0);
 			tmp |= P2C_RG_SUSPENDM | P2C_FORCE_SUSPENDM;
-			writel(tmp, port_base + U3P_U2PHYDTM0);
+			writel(tmp, com + U3P_U2PHYDTM0);
 		}
 	}
 
-	tmp = readl(port_base + U3P_USBPHYACR6);
+	tmp = readl(com + U3P_USBPHYACR6);
 	tmp &= ~PA6_RG_U2_BC11_SW_EN;	/* DP/DM BC1.1 path Disable */
 	tmp &= ~PA6_RG_U2_SQTH;
 	tmp |= PA6_RG_U2_SQTH_VAL(2);
-	writel(tmp, port_base + U3P_USBPHYACR6);
+	writel(tmp, com + U3P_USBPHYACR6);
 
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, index);
 }
@@ -316,41 +349,42 @@ static void phy_instance_init(struct mt65xx_u3phy *u3phy,
 static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *com = u2_banks->com;
 	u32 index = instance->index;
 	u32 tmp;
 
 	/* (force_suspendm=0) (let suspendm=1, enable usb 480MHz pll) */
-	tmp = readl(port_base + U3P_U2PHYDTM0);
+	tmp = readl(com + U3P_U2PHYDTM0);
 	tmp &= ~(P2C_FORCE_SUSPENDM | P2C_RG_XCVRSEL);
 	tmp &= ~(P2C_RG_DATAIN | P2C_DTM0_PART_MASK);
-	writel(tmp, port_base + U3P_U2PHYDTM0);
+	writel(tmp, com + U3P_U2PHYDTM0);
 
 	/* OTG Enable */
-	tmp = readl(port_base + U3P_USBPHYACR6);
+	tmp = readl(com + U3P_USBPHYACR6);
 	tmp |= PA6_RG_U2_OTG_VBUSCMP_EN;
-	writel(tmp, port_base + U3P_USBPHYACR6);
+	writel(tmp, com + U3P_USBPHYACR6);
 
 	if (!index) {
 		/* switch 100uA current to SSUSB */
-		tmp = readl(port_base + U3P_USBPHYACR5);
+		tmp = readl(com + U3P_USBPHYACR5);
 		tmp |= PA5_RG_U2_HS_100U_U3_EN;
-		writel(tmp, port_base + U3P_USBPHYACR5);
+		writel(tmp, com + U3P_USBPHYACR5);
 	}
 
-	tmp = readl(port_base + U3P_U2PHYDTM1);
+	tmp = readl(com + U3P_U2PHYDTM1);
 	tmp |= P2C_RG_VBUSVALID | P2C_RG_AVALID;
 	tmp &= ~P2C_RG_SESSEND;
-	writel(tmp, port_base + U3P_U2PHYDTM1);
+	writel(tmp, com + U3P_U2PHYDTM1);
 
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
-		tmp = readl(port_base + U3D_U2PHYDCR0);
+		tmp = readl(com + U3D_U2PHYDCR0);
 		tmp |= P2C_RG_SIF_U2PLL_FORCE_ON;
-		writel(tmp, port_base + U3D_U2PHYDCR0);
+		writel(tmp, com + U3D_U2PHYDCR0);
 
-		tmp = readl(port_base + U3P_U2PHYDTM0);
+		tmp = readl(com + U3P_U2PHYDTM0);
 		tmp |= P2C_RG_SUSPENDM | P2C_FORCE_SUSPENDM;
-		writel(tmp, port_base + U3P_U2PHYDTM0);
+		writel(tmp, com + U3P_U2PHYDTM0);
 	}
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, index);
 }
@@ -358,42 +392,43 @@ static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 static void phy_instance_power_off(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *com = u2_banks->com;
 	u32 index = instance->index;
 	u32 tmp;
 
-	tmp = readl(port_base + U3P_U2PHYDTM0);
+	tmp = readl(com + U3P_U2PHYDTM0);
 	tmp &= ~(P2C_RG_XCVRSEL | P2C_RG_DATAIN);
 	tmp |= P2C_FORCE_SUSPENDM;
-	writel(tmp, port_base + U3P_U2PHYDTM0);
+	writel(tmp, com + U3P_U2PHYDTM0);
 
 	/* OTG Disable */
-	tmp = readl(port_base + U3P_USBPHYACR6);
+	tmp = readl(com + U3P_USBPHYACR6);
 	tmp &= ~PA6_RG_U2_OTG_VBUSCMP_EN;
-	writel(tmp, port_base + U3P_USBPHYACR6);
+	writel(tmp, com + U3P_USBPHYACR6);
 
 	if (!index) {
 		/* switch 100uA current back to USB2.0 */
-		tmp = readl(port_base + U3P_USBPHYACR5);
+		tmp = readl(com + U3P_USBPHYACR5);
 		tmp &= ~PA5_RG_U2_HS_100U_U3_EN;
-		writel(tmp, port_base + U3P_USBPHYACR5);
+		writel(tmp, com + U3P_USBPHYACR5);
 	}
 
 	/* let suspendm=0, set utmi into analog power down */
-	tmp = readl(port_base + U3P_U2PHYDTM0);
+	tmp = readl(com + U3P_U2PHYDTM0);
 	tmp &= ~P2C_RG_SUSPENDM;
-	writel(tmp, port_base + U3P_U2PHYDTM0);
+	writel(tmp, com + U3P_U2PHYDTM0);
 	udelay(1);
 
-	tmp = readl(port_base + U3P_U2PHYDTM1);
+	tmp = readl(com + U3P_U2PHYDTM1);
 	tmp &= ~(P2C_RG_VBUSVALID | P2C_RG_AVALID);
 	tmp |= P2C_RG_SESSEND;
-	writel(tmp, port_base + U3P_U2PHYDTM1);
+	writel(tmp, com + U3P_U2PHYDTM1);
 
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
-		tmp = readl(port_base + U3D_U2PHYDCR0);
+		tmp = readl(com + U3D_U2PHYDCR0);
 		tmp &= ~P2C_RG_SIF_U2PLL_FORCE_ON;
-		writel(tmp, port_base + U3D_U2PHYDCR0);
+		writel(tmp, com + U3D_U2PHYDCR0);
 	}
 
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, index);
@@ -402,18 +437,55 @@ static void phy_instance_power_off(struct mt65xx_u3phy *u3phy,
 static void phy_instance_exit(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *com = u2_banks->com;
 	u32 index = instance->index;
 	u32 tmp;
 
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
-		tmp = readl(port_base + U3D_U2PHYDCR0);
+		tmp = readl(com + U3D_U2PHYDCR0);
 		tmp &= ~P2C_RG_SIF_U2PLL_FORCE_ON;
-		writel(tmp, port_base + U3D_U2PHYDCR0);
+		writel(tmp, com + U3D_U2PHYDCR0);
 
-		tmp = readl(port_base + U3P_U2PHYDTM0);
+		tmp = readl(com + U3P_U2PHYDTM0);
 		tmp &= ~P2C_FORCE_SUSPENDM;
-		writel(tmp, port_base + U3P_U2PHYDTM0);
+		writel(tmp, com + U3P_U2PHYDTM0);
+	}
+}
+
+static void phy_v1_banks_init(struct mt65xx_u3phy *u3phy,
+	struct mt65xx_phy_instance *instance)
+{
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	struct u3phy_banks *u3_banks = &instance->u3_banks;
+
+	if (instance->type == PHY_TYPE_USB2) {
+		u2_banks->misc = NULL;
+		u2_banks->fmreg = u3phy->sif_base + SSUSB_SIFSLV_V1_U2FREQ;
+		u2_banks->com = instance->port_base + SSUSB_SIFSLV_V1_U2PHY_COM;
+	} else if (instance->type == PHY_TYPE_USB3) {
+		u3_banks->spllc = u3phy->sif_base + SSUSB_SIFSLV_V1_SPLLC;
+		u3_banks->chip = NULL;
+		u3_banks->phyd = instance->port_base + SSUSB_SIFSLV_V1_U3PHYD;
+		u3_banks->phya = instance->port_base + SSUSB_SIFSLV_V1_U3PHYA;
+	}
+}
+
+static void phy_v2_banks_init(struct mt65xx_u3phy *u3phy,
+	struct mt65xx_phy_instance *instance)
+{
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	struct u3phy_banks *u3_banks = &instance->u3_banks;
+
+	if (instance->type == PHY_TYPE_USB2) {
+		u2_banks->misc = instance->port_base + SSUSB_SIFSLV_V2_MISC;
+		u2_banks->fmreg = instance->port_base + SSUSB_SIFSLV_V2_U2FREQ;
+		u2_banks->com = instance->port_base + SSUSB_SIFSLV_V2_U2PHY_COM;
+	} else if (instance->type == PHY_TYPE_USB3) {
+		u3_banks->spllc = instance->port_base + SSUSB_SIFSLV_V2_SPLLC;
+		u3_banks->chip = instance->port_base + SSUSB_SIFSLV_V2_CHIP;
+		u3_banks->phyd = instance->port_base + SSUSB_SIFSLV_V2_U3PHYD;
+		u3_banks->phya = instance->port_base + SSUSB_SIFSLV_V2_U3PHYA;
 	}
 }
 
@@ -490,7 +562,6 @@ static struct phy *mt65xx_phy_xlate(struct device *dev,
 	struct device_node *phy_np = args->np;
 	int index;
 
-
 	if (args->args_count != 1) {
 		dev_err(dev, "invalid number of cells in 'phy' property\n");
 		return ERR_PTR(-EINVAL);
@@ -508,13 +579,21 @@ static struct phy *mt65xx_phy_xlate(struct device *dev,
 	}
 
 	instance->type = args->args[0];
-
 	if (!(instance->type == PHY_TYPE_USB2 ||
 	      instance->type == PHY_TYPE_USB3)) {
 		dev_err(dev, "unsupported device type: %d\n", instance->type);
 		return ERR_PTR(-EINVAL);
 	}
 
+	if (u3phy->pdata->version == MT_PHY_V1) {
+		phy_v1_banks_init(u3phy, instance);
+	} else if (u3phy->pdata->version == MT_PHY_V2) {
+		phy_v2_banks_init(u3phy, instance);
+	} else {
+		dev_err(dev, "phy version is not supported\n");
+		return ERR_PTR(-EINVAL);
+	}
+
 	return instance->phy;
 }
 
@@ -528,14 +607,22 @@ static struct phy *mt65xx_phy_xlate(struct device *dev,
 
 static const struct mt65xx_phy_pdata mt2701_pdata = {
 	.avoid_rx_sen_degradation = false,
+	.version = MT_PHY_V1,
+};
+
+static const struct mt65xx_phy_pdata mt2712_pdata = {
+	.avoid_rx_sen_degradation = false,
+	.version = MT_PHY_V2,
 };
 
 static const struct mt65xx_phy_pdata mt8173_pdata = {
 	.avoid_rx_sen_degradation = true,
+	.version = MT_PHY_V1,
 };
 
 static const struct of_device_id mt65xx_u3phy_id_table[] = {
 	{ .compatible = "mediatek,mt2701-u3phy", .data = &mt2701_pdata },
+	{ .compatible = "mediatek,mt2712-u3phy", .data = &mt2712_pdata },
 	{ .compatible = "mediatek,mt8173-u3phy", .data = &mt8173_pdata },
 	{ },
 };
@@ -571,11 +658,14 @@ static int mt65xx_u3phy_probe(struct platform_device *pdev)
 	u3phy->dev = dev;
 	platform_set_drvdata(pdev, u3phy);
 
-	sif_res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-	u3phy->sif_base = devm_ioremap_resource(dev, sif_res);
-	if (IS_ERR(u3phy->sif_base)) {
-		dev_err(dev, "failed to remap sif regs\n");
-		return PTR_ERR(u3phy->sif_base);
+	if (u3phy->pdata->version == MT_PHY_V1) {
+		/* get banks shared by multiple phys */
+		sif_res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+		u3phy->sif_base = devm_ioremap_resource(dev, sif_res);
+		if (IS_ERR(u3phy->sif_base)) {
+			dev_err(dev, "failed to remap sif regs\n");
+			return PTR_ERR(u3phy->sif_base);
+		}
 	}
 
 	u3phy->u2ref_clk = devm_clk_get(dev, "u2ref_clk");
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 4/6] arm64: dts: mt8173: add a new reference clock for usb3 analog phy
From: Chunfeng Yun @ 2017-01-18  5:51 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Felipe Balbi, linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Chunfeng Yun,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Matthias Brugger,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r
In-Reply-To: <1484718665-11584-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

add a new reference clock which comes from 26M oscillator directly
for SuperSpeed analog phy. and the old one which comes for PLL is
48M for HighSpeed analog phy.

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 arch/arm64/boot/dts/mediatek/mt8173.dtsi |    4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/arch/arm64/boot/dts/mediatek/mt8173.dtsi b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
index 12e7027..5d1663b 100644
--- a/arch/arm64/boot/dts/mediatek/mt8173.dtsi
+++ b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
@@ -754,8 +754,8 @@
 		u3phy: usb-phy@11290000 {
 			compatible = "mediatek,mt8173-u3phy";
 			reg = <0 0x11290000 0 0x800>;
-			clocks = <&apmixedsys CLK_APMIXED_REF2USB_TX>;
-			clock-names = "u3phya_ref";
+			clocks = <&apmixedsys CLK_APMIXED_REF2USB_TX>, <&clk26m>;
+			clock-names = "u2ref_clk", "u3ref_clk";
 			#address-cells = <2>;
 			#size-cells = <2>;
 			ranges;
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 5/6] arm64: dts: mt8173: split usb SuperSpeed port into two ports
From: Chunfeng Yun @ 2017-01-18  5:51 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Matthias Brugger, Felipe Balbi, Chunfeng Yun, linux-kernel,
	linux-arm-kernel, linux-usb, linux-mediatek
In-Reply-To: <1484718665-11584-1-git-send-email-chunfeng.yun@mediatek.com>

split the old SuperSpeed port node into a HighSpeed one and a new
SuperSpeed one.

Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
---
 arch/arm64/boot/dts/mediatek/mt8173.dtsi |   19 +++++++++++++------
 1 file changed, 13 insertions(+), 6 deletions(-)

diff --git a/arch/arm64/boot/dts/mediatek/mt8173.dtsi b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
index 5d1663b..07fd2eb 100644
--- a/arch/arm64/boot/dts/mediatek/mt8173.dtsi
+++ b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
@@ -724,8 +724,9 @@
 			      <0 0x11280700 0 0x0100>;
 			reg-names = "mac", "ippc";
 			interrupts = <GIC_SPI 64 IRQ_TYPE_LEVEL_LOW>;
-			phys = <&phy_port0 PHY_TYPE_USB3>,
-			       <&phy_port1 PHY_TYPE_USB2>;
+			phys = <&u2port0 PHY_TYPE_USB2>,
+			       <&u3port0 PHY_TYPE_USB3>,
+			       <&u2port1 PHY_TYPE_USB2>;
 			power-domains = <&scpsys MT8173_POWER_DOMAIN_USB>;
 			clocks = <&topckgen CLK_TOP_USB30_SEL>,
 				 <&pericfg CLK_PERI_USB0>,
@@ -761,14 +762,20 @@
 			ranges;
 			status = "okay";
 
-			phy_port0: port@11290800 {
-				reg = <0 0x11290800 0 0x800>;
+			u2port0: port@11290800 {
+				reg = <0 0x11290800 0 0x100>;
 				#phy-cells = <1>;
 				status = "okay";
 			};
 
-			phy_port1: port@11291000 {
-				reg = <0 0x11291000 0 0x800>;
+			u3port0: port@11290900 {
+				reg = <0 0x11290900 0 0x700>;
+				#phy-cells = <1>;
+				status = "okay";
+			};
+
+			u2port1: port@11291000 {
+				reg = <0 0x11291000 0 0x100>;
 				#phy-cells = <1>;
 				status = "okay";
 			};
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 6/6] dt-bindings: phy-mt65xx-usb: add support for mt2712 platform
From: Chunfeng Yun @ 2017-01-18  5:51 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Matthias Brugger, Felipe Balbi, Chunfeng Yun, linux-kernel,
	linux-arm-kernel, linux-usb, linux-mediatek
In-Reply-To: <1484718665-11584-1-git-send-email-chunfeng.yun@mediatek.com>

add a new compatible string for "mt2712", and a new reference clock
for SuperSpeed analog phy;

Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
---
 .../devicetree/bindings/phy/phy-mt65xx-usb.txt     |   81 +++++++++++++++++---
 1 file changed, 70 insertions(+), 11 deletions(-)

diff --git a/Documentation/devicetree/bindings/phy/phy-mt65xx-usb.txt b/Documentation/devicetree/bindings/phy/phy-mt65xx-usb.txt
index 33a2b1e..8f91136 100644
--- a/Documentation/devicetree/bindings/phy/phy-mt65xx-usb.txt
+++ b/Documentation/devicetree/bindings/phy/phy-mt65xx-usb.txt
@@ -6,19 +6,25 @@ This binding describes a usb3.0 phy for mt65xx platforms of Medaitek SoC.
 Required properties (controller (parent) node):
  - compatible	: should be one of
 		  "mediatek,mt2701-u3phy"
+		  "mediatek,mt2712-u3phy"
 		  "mediatek,mt8173-u3phy"
- - reg		: offset and length of register for phy, exclude port's
-		  register.
  - clocks	: a list of phandle + clock-specifier pairs, one for each
 		  entry in clock-names
  - clock-names	: must contain
-		  "u3phya_ref": for reference clock of usb3.0 analog phy.
+		  "u2ref_clk": 48M reference clock of HighSpeed analog phy.
+		  "u3ref_clk": 26M reference clock of SuperSpeed analog phy,
+			sometimes is 24M, 25M or 27M, depended on platform.
 
 Required nodes	: a sub-node is required for each port the controller
 		  provides. Address range information including the usual
 		  'reg' property is used inside these nodes to describe
 		  the controller's topology.
 
+Optional properties (controller (parent) node):
+ - reg		: offset and length of register shared by multiple ports,
+		  exclude port's private register. It is needed on mt2701
+		  and mt8173, but not on mt2712.
+
 Required properties (port (child) node):
 - reg		: address and length of the register set for the port.
 - #phy-cells	: should be 1 (See second example)
@@ -31,21 +37,27 @@ Example:
 u3phy: usb-phy@11290000 {
 	compatible = "mediatek,mt8173-u3phy";
 	reg = <0 0x11290000 0 0x800>;
-	clocks = <&apmixedsys CLK_APMIXED_REF2USB_TX>;
-	clock-names = "u3phya_ref";
+	clocks = <&apmixedsys CLK_APMIXED_REF2USB_TX>, <&clk26m>;
+	clock-names = "u2ref_clk", "u3ref_clk";
 	#address-cells = <2>;
 	#size-cells = <2>;
 	ranges;
 	status = "okay";
 
-	phy_port0: port@11290800 {
-		reg = <0 0x11290800 0 0x800>;
+	u2port0: port@11290800 {
+		reg = <0 0x11290800 0 0x100>;
+		#phy-cells = <1>;
+		status = "okay";
+	};
+
+	u3port0: port@11290900 {
+		reg = <0 0x11290800 0 0x700>;
 		#phy-cells = <1>;
 		status = "okay";
 	};
 
-	phy_port1: port@11291000 {
-		reg = <0 0x11291000 0 0x800>;
+	u2port1: port@11291000 {
+		reg = <0 0x11291000 0 0x100>;
 		#phy-cells = <1>;
 		status = "okay";
 	};
@@ -64,7 +76,54 @@ Example:
 
 usb30: usb@11270000 {
 	...
-	phys = <&phy_port0 PHY_TYPE_USB3>;
-	phy-names = "usb3-0";
+	phys = <&u2port0 PHY_TYPE_USB2>, <&u3port0 PHY_TYPE_USB3>;
+	phy-names = "usb2-0", "usb3-0";
 	...
 };
+
+
+Layout differences of banks between mt8173/mt2701 and mt2712
+-------------------------------------------------------------
+mt8173 and mt2701:
+port        offset    bank
+shared      0x0000    SPLLC
+            0x0100    FMREG
+u2 port0    0x0800    U2PHY_COM
+u3 port0    0x0900    U3PHYD
+            0x0a00    U3PHYD_BANK2
+            0x0b00    U3PHYA
+            0x0c00    U3PHYA_DA
+u2 port1    0x1000    U2PHY_COM
+u3 port1    0x1100    U3PHYD
+            0x1200    U3PHYD_BANK2
+            0x1300    U3PHYA
+            0x1400    U3PHYA_DA
+u2 port2    0x1800    U2PHY_COM
+            ...
+
+mt2712:
+port        offset    bank
+u2 port0    0x0000    MISC
+            0x0100    FMREG
+            0x0300    U2PHY_COM
+u3 port0    0x0700    SPLLC
+            0x0800    CHIP
+            0x0900    U3PHYD
+            0x0a00    U3PHYD_BANK2
+            0x0b00    U3PHYA
+            0x0c00    U3PHYA_DA
+u2 port1    0x1000    MISC
+            0x1100    FMREG
+            0x1300    U2PHY_COM
+u3 port1    0x1700    SPLLC
+            0x1800    CHIP
+            0x1900    U3PHYD
+            0x1a00    U3PHYD_BANK2
+            0x1b00    U3PHYA
+            0x1c00    U3PHYA_DA
+u2 port2    0x2000    MISC
+            ...
+
+    SPLLC shared by u3 ports and FMREG shared by u2 ports on
+mt8173/mt2701 are put back into each port; a new bank MISC for
+u2 ports and CHIP for u3 ports are added on mt2712.
-- 
1.7.9.5

^ permalink raw reply related

* Re: [PATCH v11 07/12] drm/mediatek: cleaning up and refine
From: CK Hu @ 2017-01-18  5:55 UTC (permalink / raw)
  To: YT Shen
  Cc: Mark Rutland, devicetree, srv_heupstream, emil.l.velikov,
	linux-kernel, dri-devel, Rob Herring, linux-mediatek,
	Matthias Brugger, yingjoe.chen, shaoming chen, linux-arm-kernel
In-Reply-To: <1484117473-46644-8-git-send-email-yt.shen@mediatek.com>

Hi, YT:

On Wed, 2017-01-11 at 14:51 +0800, YT Shen wrote:
> cleaning up unused define and refine function name and variable
> 
> Signed-off-by: shaoming chen <shaoming.chen@mediatek.com>
> Signed-off-by: YT Shen <yt.shen@mediatek.com>

Acked-by: CK Hu <ck.hu@mediatek.com>

> ---
>  drivers/gpu/drm/mediatek/mtk_dsi.c     | 73 ++++++++++++++++------------------
>  drivers/gpu/drm/mediatek/mtk_mipi_tx.c |  8 ++--
>  2 files changed, 39 insertions(+), 42 deletions(-)
> 
> diff --git a/drivers/gpu/drm/mediatek/mtk_dsi.c b/drivers/gpu/drm/mediatek/mtk_dsi.c
> index 2c42f90..6f4b3bb 100644
> --- a/drivers/gpu/drm/mediatek/mtk_dsi.c
> +++ b/drivers/gpu/drm/mediatek/mtk_dsi.c
> @@ -27,9 +27,6 @@
>  
>  #include "mtk_drm_ddp_comp.h"
>  
> -#define DSI_VIDEO_FIFO_DEPTH	(1920 / 4)
> -#define DSI_HOST_FIFO_DEPTH	64
> -
>  #define DSI_START		0x00
>  
>  #define DSI_CON_CTRL		0x10
> @@ -46,7 +43,7 @@
>  #define MIX_MODE			BIT(17)
>  
>  #define DSI_TXRX_CTRL		0x18
> -#define VC_NUM				(2 << 0)
> +#define VC_NUM				BIT(1)
>  #define LANE_NUM			(0xf << 2)
>  #define DIS_EOT				BIT(6)
>  #define NULL_EN				BIT(7)
> @@ -164,7 +161,7 @@ static void mtk_dsi_mask(struct mtk_dsi *dsi, u32 offset, u32 mask, u32 data)
>  	writel((temp & ~mask) | (data & mask), dsi->regs + offset);
>  }
>  
> -static void dsi_phy_timconfig(struct mtk_dsi *dsi)
> +static void mtk_dsi_phy_timconfig(struct mtk_dsi *dsi)
>  {
>  	u32 timcon0, timcon1, timcon2, timcon3;
>  	u32 ui, cycle_time;
> @@ -196,7 +193,7 @@ static void mtk_dsi_disable(struct mtk_dsi *dsi)
>  	mtk_dsi_mask(dsi, DSI_CON_CTRL, DSI_EN, 0);
>  }
>  
> -static void mtk_dsi_reset(struct mtk_dsi *dsi)
> +static void mtk_dsi_reset_engine(struct mtk_dsi *dsi)
>  {
>  	mtk_dsi_mask(dsi, DSI_CON_CTRL, DSI_RESET, DSI_RESET);
>  	mtk_dsi_mask(dsi, DSI_CON_CTRL, DSI_RESET, 0);
> @@ -267,8 +264,8 @@ static int mtk_dsi_poweron(struct mtk_dsi *dsi)
>  	}
>  
>  	mtk_dsi_enable(dsi);
> -	mtk_dsi_reset(dsi);
> -	dsi_phy_timconfig(dsi);
> +	mtk_dsi_reset_engine(dsi);
> +	mtk_dsi_phy_timconfig(dsi);
>  
>  	return 0;
>  
> @@ -281,33 +278,33 @@ static int mtk_dsi_poweron(struct mtk_dsi *dsi)
>  	return ret;
>  }
>  
> -static void dsi_clk_ulp_mode_enter(struct mtk_dsi *dsi)
> +static void mtk_dsi_clk_ulp_mode_enter(struct mtk_dsi *dsi)
>  {
>  	mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_HS_TX_EN, 0);
>  	mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_ULPM_EN, 0);
>  }
>  
> -static void dsi_clk_ulp_mode_leave(struct mtk_dsi *dsi)
> +static void mtk_dsi_clk_ulp_mode_leave(struct mtk_dsi *dsi)
>  {
>  	mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_ULPM_EN, 0);
>  	mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_WAKEUP_EN, LC_WAKEUP_EN);
>  	mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_WAKEUP_EN, 0);
>  }
>  
> -static void dsi_lane0_ulp_mode_enter(struct mtk_dsi *dsi)
> +static void mtk_dsi_lane0_ulp_mode_enter(struct mtk_dsi *dsi)
>  {
>  	mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_HS_TX_EN, 0);
>  	mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_ULPM_EN, 0);
>  }
>  
> -static void dsi_lane0_ulp_mode_leave(struct mtk_dsi *dsi)
> +static void mtk_dsi_lane0_ulp_mode_leave(struct mtk_dsi *dsi)
>  {
>  	mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_ULPM_EN, 0);
>  	mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_WAKEUP_EN, LD0_WAKEUP_EN);
>  	mtk_dsi_mask(dsi, DSI_PHY_LD0CON, LD0_WAKEUP_EN, 0);
>  }
>  
> -static bool dsi_clk_hs_state(struct mtk_dsi *dsi)
> +static bool mtk_dsi_clk_hs_state(struct mtk_dsi *dsi)
>  {
>  	u32 tmp_reg1;
>  
> @@ -315,15 +312,15 @@ static bool dsi_clk_hs_state(struct mtk_dsi *dsi)
>  	return ((tmp_reg1 & LC_HS_TX_EN) == 1) ? true : false;
>  }
>  
> -static void dsi_clk_hs_mode(struct mtk_dsi *dsi, bool enter)
> +static void mtk_dsi_clk_hs_mode(struct mtk_dsi *dsi, bool enter)
>  {
> -	if (enter && !dsi_clk_hs_state(dsi))
> +	if (enter && !mtk_dsi_clk_hs_state(dsi))
>  		mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_HS_TX_EN, LC_HS_TX_EN);
> -	else if (!enter && dsi_clk_hs_state(dsi))
> +	else if (!enter && mtk_dsi_clk_hs_state(dsi))
>  		mtk_dsi_mask(dsi, DSI_PHY_LCCON, LC_HS_TX_EN, 0);
>  }
>  
> -static void dsi_set_mode(struct mtk_dsi *dsi)
> +static void mtk_dsi_set_mode(struct mtk_dsi *dsi)
>  {
>  	u32 vid_mode = CMD_MODE;
>  
> @@ -338,7 +335,7 @@ static void dsi_set_mode(struct mtk_dsi *dsi)
>  	writel(vid_mode, dsi->regs + DSI_MODE_CTRL);
>  }
>  
> -static void dsi_ps_control_vact(struct mtk_dsi *dsi)
> +static void mtk_dsi_ps_control_vact(struct mtk_dsi *dsi)
>  {
>  	struct videomode *vm = &dsi->vm;
>  	u32 dsi_buf_bpp, ps_wc;
> @@ -372,7 +369,7 @@ static void dsi_ps_control_vact(struct mtk_dsi *dsi)
>  	writel(ps_wc, dsi->regs + DSI_HSTX_CKL_WC);
>  }
>  
> -static void dsi_rxtx_control(struct mtk_dsi *dsi)
> +static void mtk_dsi_rxtx_control(struct mtk_dsi *dsi)
>  {
>  	u32 tmp_reg;
>  
> @@ -397,9 +394,9 @@ static void dsi_rxtx_control(struct mtk_dsi *dsi)
>  	writel(tmp_reg, dsi->regs + DSI_TXRX_CTRL);
>  }
>  
> -static void dsi_ps_control(struct mtk_dsi *dsi)
> +static void mtk_dsi_ps_control(struct mtk_dsi *dsi)
>  {
> -	unsigned int dsi_tmp_buf_bpp;
> +	u32 dsi_tmp_buf_bpp;
>  	u32 tmp_reg;
>  
>  	switch (dsi->format) {
> @@ -429,12 +426,12 @@ static void dsi_ps_control(struct mtk_dsi *dsi)
>  	writel(tmp_reg, dsi->regs + DSI_PSCTRL);
>  }
>  
> -static void dsi_config_vdo_timing(struct mtk_dsi *dsi)
> +static void mtk_dsi_config_vdo_timing(struct mtk_dsi *dsi)
>  {
> -	unsigned int horizontal_sync_active_byte;
> -	unsigned int horizontal_backporch_byte;
> -	unsigned int horizontal_frontporch_byte;
> -	unsigned int dsi_tmp_buf_bpp;
> +	u32 horizontal_sync_active_byte;
> +	u32 horizontal_backporch_byte;
> +	u32 horizontal_frontporch_byte;
> +	u32 dsi_tmp_buf_bpp;
>  
>  	struct videomode *vm = &dsi->vm;
>  
> @@ -463,7 +460,7 @@ static void dsi_config_vdo_timing(struct mtk_dsi *dsi)
>  	writel(horizontal_backporch_byte, dsi->regs + DSI_HBP_WC);
>  	writel(horizontal_frontporch_byte, dsi->regs + DSI_HFP_WC);
>  
> -	dsi_ps_control(dsi);
> +	mtk_dsi_ps_control(dsi);
>  }
>  
>  static void mtk_dsi_start(struct mtk_dsi *dsi)
> @@ -480,8 +477,8 @@ static void mtk_dsi_poweroff(struct mtk_dsi *dsi)
>  	if (--dsi->refcount != 0)
>  		return;
>  
> -	dsi_lane0_ulp_mode_enter(dsi);
> -	dsi_clk_ulp_mode_enter(dsi);
> +	mtk_dsi_lane0_ulp_mode_enter(dsi);
> +	mtk_dsi_clk_ulp_mode_enter(dsi);
>  
>  	mtk_dsi_disable(dsi);
>  
> @@ -511,18 +508,18 @@ static void mtk_output_dsi_enable(struct mtk_dsi *dsi)
>  		return;
>  	}
>  
> -	dsi_rxtx_control(dsi);
> +	mtk_dsi_rxtx_control(dsi);
>  
> -	dsi_clk_ulp_mode_leave(dsi);
> -	dsi_lane0_ulp_mode_leave(dsi);
> -	dsi_clk_hs_mode(dsi, 0);
> -	dsi_set_mode(dsi);
> +	mtk_dsi_clk_ulp_mode_leave(dsi);
> +	mtk_dsi_lane0_ulp_mode_leave(dsi);
> +	mtk_dsi_clk_hs_mode(dsi, 0);
> +	mtk_dsi_set_mode(dsi);
>  
> -	dsi_ps_control_vact(dsi);
> -	dsi_config_vdo_timing(dsi);
> +	mtk_dsi_ps_control_vact(dsi);
> +	mtk_dsi_config_vdo_timing(dsi);
>  
> -	dsi_set_mode(dsi);
> -	dsi_clk_hs_mode(dsi, 1);
> +	mtk_dsi_set_mode(dsi);
> +	mtk_dsi_clk_hs_mode(dsi, 1);
>  
>  	mtk_dsi_start(dsi);
>  
> diff --git a/drivers/gpu/drm/mediatek/mtk_mipi_tx.c b/drivers/gpu/drm/mediatek/mtk_mipi_tx.c
> index c4a0165..fd84914 100644
> --- a/drivers/gpu/drm/mediatek/mtk_mipi_tx.c
> +++ b/drivers/gpu/drm/mediatek/mtk_mipi_tx.c
> @@ -134,7 +134,7 @@ struct mtk_mipitx_data {
>  struct mtk_mipi_tx {
>  	struct device *dev;
>  	void __iomem *regs;
> -	unsigned int data_rate;
> +	u32 data_rate;
>  	const struct mtk_mipitx_data *driver_data;
>  	struct clk_hw pll_hw;
>  	struct clk *pll;
> @@ -172,7 +172,7 @@ static void mtk_mipi_tx_update_bits(struct mtk_mipi_tx *mipi_tx, u32 offset,
>  static int mtk_mipi_tx_pll_prepare(struct clk_hw *hw)
>  {
>  	struct mtk_mipi_tx *mipi_tx = mtk_mipi_tx_from_clk_hw(hw);
> -	unsigned int txdiv, txdiv0, txdiv1;
> +	u8 txdiv, txdiv0, txdiv1;
>  	u64 pcw;
>  
>  	dev_dbg(mipi_tx->dev, "prepare: %u Hz\n", mipi_tx->data_rate);
> @@ -326,7 +326,7 @@ static unsigned long mtk_mipi_tx_pll_recalc_rate(struct clk_hw *hw,
>  static int mtk_mipi_tx_power_on_signal(struct phy *phy)
>  {
>  	struct mtk_mipi_tx *mipi_tx = phy_get_drvdata(phy);
> -	unsigned int reg;
> +	u32 reg;
>  
>  	for (reg = MIPITX_DSI_CLOCK_LANE;
>  	     reg <= MIPITX_DSI_DATA_LANE3; reg += 4)
> @@ -357,7 +357,7 @@ static int mtk_mipi_tx_power_on(struct phy *phy)
>  static void mtk_mipi_tx_power_off_signal(struct phy *phy)
>  {
>  	struct mtk_mipi_tx *mipi_tx = phy_get_drvdata(phy);
> -	unsigned int reg;
> +	u32 reg;
>  
>  	mtk_mipi_tx_set_bits(mipi_tx, MIPITX_DSI_TOP_CON,
>  			     RG_DSI_PAD_TIE_LOW_EN);


_______________________________________________
dri-devel mailing list
dri-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/dri-devel

^ permalink raw reply

* [RESEND PATCH 1/6] phy: phy-mt65xx-usb3: add reference clock of usb3 analog phy
From: Chunfeng Yun @ 2017-01-18  6:00 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Felipe Balbi,
	Ian Campbell, linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Chunfeng Yun, Rob Herring,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Matthias Brugger,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

usually, the reference clock of usb3 analog phy comes from
26M oscillator directly, but some SoCs are not, add it for
compatibility.

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 drivers/phy/phy-mt65xx-usb3.c |   36 ++++++++++++++++++++++++++++--------
 1 file changed, 28 insertions(+), 8 deletions(-)

diff --git a/drivers/phy/phy-mt65xx-usb3.c b/drivers/phy/phy-mt65xx-usb3.c
index d972067..fc9a4f0 100644
--- a/drivers/phy/phy-mt65xx-usb3.c
+++ b/drivers/phy/phy-mt65xx-usb3.c
@@ -149,7 +149,8 @@ struct mt65xx_phy_instance {
 struct mt65xx_u3phy {
 	struct device *dev;
 	void __iomem *sif_base;	/* include sif2, but exclude port's */
-	struct clk *u3phya_ref;	/* reference clock of usb3 anolog phy */
+	struct clk *u2ref_clk;	/* reference clock of u2 analog phy */
+	struct clk *u3ref_clk;	/* reference clock of u3 analog phy */
 	const struct mt65xx_phy_pdata *pdata;
 	struct mt65xx_phy_instance **phys;
 	int nphys;
@@ -429,11 +430,17 @@ static int mt65xx_phy_init(struct phy *phy)
 {
 	struct mt65xx_phy_instance *instance = phy_get_drvdata(phy);
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
+	struct clk *ref_clk;
 	int ret;
 
-	ret = clk_prepare_enable(u3phy->u3phya_ref);
+	if (instance->type == PHY_TYPE_USB2)
+		ref_clk = u3phy->u2ref_clk;
+	else
+		ref_clk = u3phy->u3ref_clk;
+
+	ret = clk_prepare_enable(ref_clk);
 	if (ret) {
-		dev_err(u3phy->dev, "failed to enable u3phya_ref\n");
+		dev_err(u3phy->dev, "failed to enable ref clk\n");
 		return ret;
 	}
 
@@ -464,9 +471,16 @@ static int mt65xx_phy_exit(struct phy *phy)
 {
 	struct mt65xx_phy_instance *instance = phy_get_drvdata(phy);
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
+	struct clk *ref_clk;
 
 	phy_instance_exit(u3phy, instance);
-	clk_disable_unprepare(u3phy->u3phya_ref);
+
+	if (instance->type == PHY_TYPE_USB2)
+		ref_clk = u3phy->u2ref_clk;
+	else
+		ref_clk = u3phy->u3ref_clk;
+
+	clk_disable_unprepare(ref_clk);
 	return 0;
 }
 
@@ -566,10 +580,16 @@ static int mt65xx_u3phy_probe(struct platform_device *pdev)
 		return PTR_ERR(u3phy->sif_base);
 	}
 
-	u3phy->u3phya_ref = devm_clk_get(dev, "u3phya_ref");
-	if (IS_ERR(u3phy->u3phya_ref)) {
-		dev_err(dev, "error to get u3phya_ref\n");
-		return PTR_ERR(u3phy->u3phya_ref);
+	u3phy->u2ref_clk = devm_clk_get(dev, "u2ref_clk");
+	if (IS_ERR(u3phy->u2ref_clk)) {
+		dev_err(dev, "failed to get u2ref_clk\n");
+		return PTR_ERR(u3phy->u2ref_clk);
+	}
+
+	u3phy->u3ref_clk = devm_clk_get(dev, "u3ref_clk");
+	if (IS_ERR(u3phy->u3ref_clk)) {
+		dev_err(dev, "failed to get u3ref_clk\n");
+		return PTR_ERR(u3phy->u3ref_clk);
 	}
 
 	port = 0;
-- 
1.7.9.5

^ permalink raw reply related

* [RESEND PATCH 2/6] phy: phy-mt65xx-usb3: split SuperSpeed port into two ones
From: Chunfeng Yun @ 2017-01-18  6:00 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Felipe Balbi,
	Ian Campbell, linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Chunfeng Yun, Rob Herring,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Matthias Brugger,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r
In-Reply-To: <1484719214-11989-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

Currently usb3 port in fact includes two sub-ports, but it is not
flexible for some cases, such as following one:
    usb3 port0 includes u2port0 and u3port0;
    usb2 port0 includes u2port1;
If wants to support only HS, we can use u2port0 or u2port1, when
select u2port0, u3port0 is not needed;
If wants to support SS, we can compound u2port0 and u3port0,
or u2port1 and u3port0, if select latter one, u2port0 is not needed.

So it's more flexible to split usb3 port into two ones and also try
best to save power by disabling unnecessary ports.

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 drivers/phy/phy-mt65xx-usb3.c |  124 ++++++++++++++++++++---------------------
 1 file changed, 61 insertions(+), 63 deletions(-)

diff --git a/drivers/phy/phy-mt65xx-usb3.c b/drivers/phy/phy-mt65xx-usb3.c
index fc9a4f0..c187a3b 100644
--- a/drivers/phy/phy-mt65xx-usb3.c
+++ b/drivers/phy/phy-mt65xx-usb3.c
@@ -30,11 +30,11 @@
 #define SSUSB_SIFSLV_SPLLC		0x0000
 #define SSUSB_SIFSLV_U2FREQ		0x0100
 
-/* offsets of sub-segment in each port registers */
+/* offsets of banks in each u2phy registers */
 #define SSUSB_SIFSLV_U2PHY_COM_BASE	0x0000
-#define SSUSB_SIFSLV_U3PHYD_BASE	0x0100
-#define SSUSB_USB30_PHYA_SIV_B_BASE	0x0300
-#define SSUSB_SIFSLV_U3PHYA_DA_BASE	0x0400
+/* offsets of banks in each u3phy registers */
+#define SSUSB_SIFSLV_U3PHYD_BASE	0x0000
+#define SSUSB_SIFSLV_U3PHYA_BASE	0x0200
 
 #define U3P_USBPHYACR0		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0000)
 #define PA0_RG_U2PLL_FORCE_ON		BIT(15)
@@ -49,7 +49,6 @@
 #define PA5_RG_U2_HS_100U_U3_EN	BIT(11)
 
 #define U3P_USBPHYACR6		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0018)
-#define PA6_RG_U2_ISO_EN		BIT(31)
 #define PA6_RG_U2_BC11_SW_EN		BIT(23)
 #define PA6_RG_U2_OTG_VBUSCMP_EN	BIT(20)
 #define PA6_RG_U2_SQTH		GENMASK(3, 0)
@@ -91,18 +90,18 @@
 #define P2C_RG_SESSEND			BIT(4)
 #define P2C_RG_AVALID			BIT(2)
 
-#define U3P_U3_PHYA_REG0	(SSUSB_USB30_PHYA_SIV_B_BASE + 0x0000)
+#define U3P_U3_PHYA_REG0	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0000)
 #define P3A_RG_U3_VUSB10_ON		BIT(5)
 
-#define U3P_U3_PHYA_REG6	(SSUSB_USB30_PHYA_SIV_B_BASE + 0x0018)
+#define U3P_U3_PHYA_REG6	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0018)
 #define P3A_RG_TX_EIDLE_CM		GENMASK(31, 28)
 #define P3A_RG_TX_EIDLE_CM_VAL(x)	((0xf & (x)) << 28)
 
-#define U3P_U3_PHYA_REG9	(SSUSB_USB30_PHYA_SIV_B_BASE + 0x0024)
+#define U3P_U3_PHYA_REG9	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0024)
 #define P3A_RG_RX_DAC_MUX		GENMASK(5, 1)
 #define P3A_RG_RX_DAC_MUX_VAL(x)	((0x1f & (x)) << 1)
 
-#define U3P_U3PHYA_DA_REG0	(SSUSB_SIFSLV_U3PHYA_DA_BASE + 0x0000)
+#define U3P_U3PHYA_DA_REG0	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0100)
 #define P3A_RG_XTAL_EXT_EN_U3		GENMASK(11, 10)
 #define P3A_RG_XTAL_EXT_EN_U3_VAL(x)	((0x3 & (x)) << 10)
 
@@ -148,7 +147,7 @@ struct mt65xx_phy_instance {
 
 struct mt65xx_u3phy {
 	struct device *dev;
-	void __iomem *sif_base;	/* include sif2, but exclude port's */
+	void __iomem *sif_base;	/* only shared sif */
 	struct clk *u2ref_clk;	/* reference clock of u2 analog phy */
 	struct clk *u3ref_clk;	/* reference clock of u3 analog phy */
 	const struct mt65xx_phy_pdata *pdata;
@@ -179,7 +178,7 @@ static void hs_slew_rate_calibrate(struct mt65xx_u3phy *u3phy,
 	tmp = readl(sif_base + U3P_U2FREQ_FMCR0);
 	tmp &= ~(P2F_RG_CYCLECNT | P2F_RG_MONCLK_SEL);
 	tmp |= P2F_RG_CYCLECNT_VAL(U3P_FM_DET_CYCLE_CNT);
-	tmp |= P2F_RG_MONCLK_SEL_VAL(instance->index);
+	tmp |= P2F_RG_MONCLK_SEL_VAL(instance->index >> 1);
 	writel(tmp, sif_base + U3P_U2FREQ_FMCR0);
 
 	/* enable frequency meter */
@@ -227,6 +226,41 @@ static void hs_slew_rate_calibrate(struct mt65xx_u3phy *u3phy,
 	writel(tmp, instance->port_base + U3P_USBPHYACR5);
 }
 
+static void u3_phy_instance_init(struct mt65xx_u3phy *u3phy,
+	struct mt65xx_phy_instance *instance)
+{
+	void __iomem *port_base = instance->port_base;
+	u32 tmp;
+
+	/* gating PCIe Analog XTAL clock */
+	tmp = readl(u3phy->sif_base + U3P_XTALCTL3);
+	tmp |= XC3_RG_U3_XTAL_RX_PWD | XC3_RG_U3_FRC_XTAL_RX_PWD;
+	writel(tmp, u3phy->sif_base + U3P_XTALCTL3);
+
+	/* gating XSQ */
+	tmp = readl(port_base + U3P_U3PHYA_DA_REG0);
+	tmp &= ~P3A_RG_XTAL_EXT_EN_U3;
+	tmp |= P3A_RG_XTAL_EXT_EN_U3_VAL(2);
+	writel(tmp, port_base + U3P_U3PHYA_DA_REG0);
+
+	tmp = readl(port_base + U3P_U3_PHYA_REG9);
+	tmp &= ~P3A_RG_RX_DAC_MUX;
+	tmp |= P3A_RG_RX_DAC_MUX_VAL(4);
+	writel(tmp, port_base + U3P_U3_PHYA_REG9);
+
+	tmp = readl(port_base + U3P_U3_PHYA_REG6);
+	tmp &= ~P3A_RG_TX_EIDLE_CM;
+	tmp |= P3A_RG_TX_EIDLE_CM_VAL(0xe);
+	writel(tmp, port_base + U3P_U3_PHYA_REG6);
+
+	tmp = readl(port_base + U3P_PHYD_CDR1);
+	tmp &= ~(P3D_RG_CDR_BIR_LTD0 | P3D_RG_CDR_BIR_LTD1);
+	tmp |= P3D_RG_CDR_BIR_LTD0_VAL(0xc) | P3D_RG_CDR_BIR_LTD1_VAL(0x3);
+	writel(tmp, port_base + U3P_PHYD_CDR1);
+
+	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, instance->index);
+}
+
 static void phy_instance_init(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
@@ -276,26 +310,6 @@ static void phy_instance_init(struct mt65xx_u3phy *u3phy,
 	tmp |= PA6_RG_U2_SQTH_VAL(2);
 	writel(tmp, port_base + U3P_USBPHYACR6);
 
-	tmp = readl(port_base + U3P_U3PHYA_DA_REG0);
-	tmp &= ~P3A_RG_XTAL_EXT_EN_U3;
-	tmp |= P3A_RG_XTAL_EXT_EN_U3_VAL(2);
-	writel(tmp, port_base + U3P_U3PHYA_DA_REG0);
-
-	tmp = readl(port_base + U3P_U3_PHYA_REG9);
-	tmp &= ~P3A_RG_RX_DAC_MUX;
-	tmp |= P3A_RG_RX_DAC_MUX_VAL(4);
-	writel(tmp, port_base + U3P_U3_PHYA_REG9);
-
-	tmp = readl(port_base + U3P_U3_PHYA_REG6);
-	tmp &= ~P3A_RG_TX_EIDLE_CM;
-	tmp |= P3A_RG_TX_EIDLE_CM_VAL(0xe);
-	writel(tmp, port_base + U3P_U3_PHYA_REG6);
-
-	tmp = readl(port_base + U3P_PHYD_CDR1);
-	tmp &= ~(P3D_RG_CDR_BIR_LTD0 | P3D_RG_CDR_BIR_LTD1);
-	tmp |= P3D_RG_CDR_BIR_LTD0_VAL(0xc) | P3D_RG_CDR_BIR_LTD1_VAL(0x3);
-	writel(tmp, port_base + U3P_PHYD_CDR1);
-
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, index);
 }
 
@@ -306,13 +320,6 @@ static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 	u32 index = instance->index;
 	u32 tmp;
 
-	if (!index) {
-		/* Set RG_SSUSB_VUSB10_ON as 1 after VUSB10 ready */
-		tmp = readl(port_base + U3P_U3_PHYA_REG0);
-		tmp |= P3A_RG_U3_VUSB10_ON;
-		writel(tmp, port_base + U3P_U3_PHYA_REG0);
-	}
-
 	/* (force_suspendm=0) (let suspendm=1, enable usb 480MHz pll) */
 	tmp = readl(port_base + U3P_U2PHYDTM0);
 	tmp &= ~(P2C_FORCE_SUSPENDM | P2C_RG_XCVRSEL);
@@ -325,10 +332,6 @@ static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 	writel(tmp, port_base + U3P_USBPHYACR6);
 
 	if (!index) {
-		tmp = readl(u3phy->sif_base + U3P_XTALCTL3);
-		tmp |= XC3_RG_U3_XTAL_RX_PWD | XC3_RG_U3_FRC_XTAL_RX_PWD;
-		writel(tmp, u3phy->sif_base + U3P_XTALCTL3);
-
 		/* switch 100uA current to SSUSB */
 		tmp = readl(port_base + U3P_USBPHYACR5);
 		tmp |= PA5_RG_U2_HS_100U_U3_EN;
@@ -340,12 +343,6 @@ static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 	tmp &= ~P2C_RG_SESSEND;
 	writel(tmp, port_base + U3P_U2PHYDTM1);
 
-	/* USB 2.0 slew rate calibration */
-	tmp = readl(port_base + U3P_USBPHYACR5);
-	tmp &= ~PA5_RG_U2_HSTX_SRCTRL;
-	tmp |= PA5_RG_U2_HSTX_SRCTRL_VAL(4);
-	writel(tmp, port_base + U3P_USBPHYACR5);
-
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
 		tmp = readl(port_base + U3D_U2PHYDCR0);
 		tmp |= P2C_RG_SIF_U2PLL_FORCE_ON;
@@ -393,12 +390,6 @@ static void phy_instance_power_off(struct mt65xx_u3phy *u3phy,
 	tmp |= P2C_RG_SESSEND;
 	writel(tmp, port_base + U3P_U2PHYDTM1);
 
-	if (!index) {
-		tmp = readl(port_base + U3P_U3_PHYA_REG0);
-		tmp &= ~P3A_RG_U3_VUSB10_ON;
-		writel(tmp, port_base + U3P_U3_PHYA_REG0);
-	}
-
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
 		tmp = readl(port_base + U3D_U2PHYDCR0);
 		tmp &= ~P2C_RG_SIF_U2PLL_FORCE_ON;
@@ -444,7 +435,11 @@ static int mt65xx_phy_init(struct phy *phy)
 		return ret;
 	}
 
-	phy_instance_init(u3phy, instance);
+	if (instance->type == PHY_TYPE_USB2)
+		phy_instance_init(u3phy, instance);
+	else
+		u3_phy_instance_init(u3phy, instance);
+
 	return 0;
 }
 
@@ -453,8 +448,10 @@ static int mt65xx_phy_power_on(struct phy *phy)
 	struct mt65xx_phy_instance *instance = phy_get_drvdata(phy);
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
 
-	phy_instance_power_on(u3phy, instance);
-	hs_slew_rate_calibrate(u3phy, instance);
+	if (instance->type == PHY_TYPE_USB2) {
+		phy_instance_power_on(u3phy, instance);
+		hs_slew_rate_calibrate(u3phy, instance);
+	}
 	return 0;
 }
 
@@ -463,7 +460,9 @@ static int mt65xx_phy_power_off(struct phy *phy)
 	struct mt65xx_phy_instance *instance = phy_get_drvdata(phy);
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
 
-	phy_instance_power_off(u3phy, instance);
+	if (instance->type == PHY_TYPE_USB2)
+		phy_instance_power_off(u3phy, instance);
+
 	return 0;
 }
 
@@ -473,13 +472,12 @@ static int mt65xx_phy_exit(struct phy *phy)
 	struct mt65xx_u3phy *u3phy = dev_get_drvdata(phy->dev.parent);
 	struct clk *ref_clk;
 
-	phy_instance_exit(u3phy, instance);
-
-	if (instance->type == PHY_TYPE_USB2)
+	if (instance->type == PHY_TYPE_USB2) {
+		phy_instance_exit(u3phy, instance);
 		ref_clk = u3phy->u2ref_clk;
-	else
+	} else {
 		ref_clk = u3phy->u3ref_clk;
-
+	}
 	clk_disable_unprepare(ref_clk);
 	return 0;
 }
-- 
1.7.9.5

^ permalink raw reply related

* [RESEND PATCH 3/6] phy: phy-mt65xx-usb3: add support for mt2712 platform
From: Chunfeng Yun @ 2017-01-18  6:00 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Matthias Brugger, Felipe Balbi, Rob Herring, Mark Rutland,
	Ian Campbell, Chunfeng Yun, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	devicetree-u79uwXL29TY76Z2rM5mHXA
In-Reply-To: <1484719214-11989-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

There are some variations from mt2701 to mt2712:
1. banks shared by multiple ports are put back into each port,
    such as SPLLC and U2FREQ;
2. add a new bank MISC for u2port, and CHIP for u3port;
3. bank's offset in each port are also rearranged;

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 drivers/phy/phy-mt65xx-usb3.c |  326 ++++++++++++++++++++++++++---------------
 1 file changed, 208 insertions(+), 118 deletions(-)

diff --git a/drivers/phy/phy-mt65xx-usb3.c b/drivers/phy/phy-mt65xx-usb3.c
index c187a3b..d515c69 100644
--- a/drivers/phy/phy-mt65xx-usb3.c
+++ b/drivers/phy/phy-mt65xx-usb3.c
@@ -23,46 +23,54 @@
 #include <linux/phy/phy.h>
 #include <linux/platform_device.h>
 
-/*
- * for sifslv2 register, but exclude port's;
- * relative to USB3_SIF2_BASE base address
- */
-#define SSUSB_SIFSLV_SPLLC		0x0000
-#define SSUSB_SIFSLV_U2FREQ		0x0100
-
-/* offsets of banks in each u2phy registers */
-#define SSUSB_SIFSLV_U2PHY_COM_BASE	0x0000
-/* offsets of banks in each u3phy registers */
-#define SSUSB_SIFSLV_U3PHYD_BASE	0x0000
-#define SSUSB_SIFSLV_U3PHYA_BASE	0x0200
-
-#define U3P_USBPHYACR0		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0000)
+/* version V1 sub-banks offset base address */
+/* banks shared by multiple phys */
+#define SSUSB_SIFSLV_V1_SPLLC		0x000	/* shared by u3 phys */
+#define SSUSB_SIFSLV_V1_U2FREQ		0x100	/* shared by u2 phys */
+/* u2 phy bank */
+#define SSUSB_SIFSLV_V1_U2PHY_COM	0x000
+/* u3 phy banks */
+#define SSUSB_SIFSLV_V1_U3PHYD		0x000
+#define SSUSB_SIFSLV_V1_U3PHYA		0x200
+
+/* version V2 sub-banks offset base address */
+/* u2 phy banks */
+#define SSUSB_SIFSLV_V2_MISC		0x000
+#define SSUSB_SIFSLV_V2_U2FREQ		0x100
+#define SSUSB_SIFSLV_V2_U2PHY_COM	0x300
+/* u3 phy banks */
+#define SSUSB_SIFSLV_V2_SPLLC		0x000
+#define SSUSB_SIFSLV_V2_CHIP		0x100
+#define SSUSB_SIFSLV_V2_U3PHYD		0x200
+#define SSUSB_SIFSLV_V2_U3PHYA		0x400
+
+#define U3P_USBPHYACR0		0x000
 #define PA0_RG_U2PLL_FORCE_ON		BIT(15)
 
-#define U3P_USBPHYACR2		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0008)
+#define U3P_USBPHYACR2		0x008
 #define PA2_RG_SIF_U2PLL_FORCE_EN	BIT(18)
 
-#define U3P_USBPHYACR5		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0014)
+#define U3P_USBPHYACR5		0x014
 #define PA5_RG_U2_HSTX_SRCAL_EN	BIT(15)
 #define PA5_RG_U2_HSTX_SRCTRL		GENMASK(14, 12)
 #define PA5_RG_U2_HSTX_SRCTRL_VAL(x)	((0x7 & (x)) << 12)
 #define PA5_RG_U2_HS_100U_U3_EN	BIT(11)
 
-#define U3P_USBPHYACR6		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0018)
+#define U3P_USBPHYACR6		0x018
 #define PA6_RG_U2_BC11_SW_EN		BIT(23)
 #define PA6_RG_U2_OTG_VBUSCMP_EN	BIT(20)
 #define PA6_RG_U2_SQTH		GENMASK(3, 0)
 #define PA6_RG_U2_SQTH_VAL(x)	(0xf & (x))
 
-#define U3P_U2PHYACR4		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0020)
+#define U3P_U2PHYACR4		0x020
 #define P2C_RG_USB20_GPIO_CTL		BIT(9)
 #define P2C_USB20_GPIO_MODE		BIT(8)
 #define P2C_U2_GPIO_CTR_MSK	(P2C_RG_USB20_GPIO_CTL | P2C_USB20_GPIO_MODE)
 
-#define U3D_U2PHYDCR0		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0060)
+#define U3D_U2PHYDCR0		0x060
 #define P2C_RG_SIF_U2PLL_FORCE_ON	BIT(24)
 
-#define U3P_U2PHYDTM0		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x0068)
+#define U3P_U2PHYDTM0		0x068
 #define P2C_FORCE_UART_EN		BIT(26)
 #define P2C_FORCE_DATAIN		BIT(23)
 #define P2C_FORCE_DM_PULLDOWN		BIT(21)
@@ -84,47 +92,44 @@
 		P2C_FORCE_TERMSEL | P2C_RG_DMPULLDOWN | \
 		P2C_RG_DPPULLDOWN | P2C_RG_TERMSEL)
 
-#define U3P_U2PHYDTM1		(SSUSB_SIFSLV_U2PHY_COM_BASE + 0x006C)
+#define U3P_U2PHYDTM1		0x06C
 #define P2C_RG_UART_EN			BIT(16)
 #define P2C_RG_VBUSVALID		BIT(5)
 #define P2C_RG_SESSEND			BIT(4)
 #define P2C_RG_AVALID			BIT(2)
 
-#define U3P_U3_PHYA_REG0	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0000)
-#define P3A_RG_U3_VUSB10_ON		BIT(5)
-
-#define U3P_U3_PHYA_REG6	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0018)
+#define U3P_U3_PHYA_REG6	0x018
 #define P3A_RG_TX_EIDLE_CM		GENMASK(31, 28)
 #define P3A_RG_TX_EIDLE_CM_VAL(x)	((0xf & (x)) << 28)
 
-#define U3P_U3_PHYA_REG9	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0024)
+#define U3P_U3_PHYA_REG9	0x024
 #define P3A_RG_RX_DAC_MUX		GENMASK(5, 1)
 #define P3A_RG_RX_DAC_MUX_VAL(x)	((0x1f & (x)) << 1)
 
-#define U3P_U3PHYA_DA_REG0	(SSUSB_SIFSLV_U3PHYA_BASE + 0x0100)
+#define U3P_U3_PHYA_DA_REG0	0x100
 #define P3A_RG_XTAL_EXT_EN_U3		GENMASK(11, 10)
 #define P3A_RG_XTAL_EXT_EN_U3_VAL(x)	((0x3 & (x)) << 10)
 
-#define U3P_PHYD_CDR1		(SSUSB_SIFSLV_U3PHYD_BASE + 0x005c)
+#define U3P_U3_PHYD_CDR1		0x05c
 #define P3D_RG_CDR_BIR_LTD1		GENMASK(28, 24)
 #define P3D_RG_CDR_BIR_LTD1_VAL(x)	((0x1f & (x)) << 24)
 #define P3D_RG_CDR_BIR_LTD0		GENMASK(12, 8)
 #define P3D_RG_CDR_BIR_LTD0_VAL(x)	((0x1f & (x)) << 8)
 
-#define U3P_XTALCTL3		(SSUSB_SIFSLV_SPLLC + 0x0018)
+#define U3P_SPLLC_XTALCTL3		0x018
 #define XC3_RG_U3_XTAL_RX_PWD		BIT(9)
 #define XC3_RG_U3_FRC_XTAL_RX_PWD	BIT(8)
 
-#define U3P_U2FREQ_FMCR0	(SSUSB_SIFSLV_U2FREQ + 0x00)
+#define U3P_U2FREQ_FMCR0	0x00
 #define P2F_RG_MONCLK_SEL	GENMASK(27, 26)
 #define P2F_RG_MONCLK_SEL_VAL(x)	((0x3 & (x)) << 26)
 #define P2F_RG_FREQDET_EN	BIT(24)
 #define P2F_RG_CYCLECNT		GENMASK(23, 0)
 #define P2F_RG_CYCLECNT_VAL(x)	((P2F_RG_CYCLECNT) & (x))
 
-#define U3P_U2FREQ_VALUE	(SSUSB_SIFSLV_U2FREQ + 0x0c)
+#define U3P_U2FREQ_VALUE	0x0c
 
-#define U3P_U2FREQ_FMMONR1	(SSUSB_SIFSLV_U2FREQ + 0x10)
+#define U3P_U2FREQ_FMMONR1	0x10
 #define P2F_USB_FM_VALID	BIT(0)
 #define P2F_RG_FRCK_EN		BIT(8)
 
@@ -133,14 +138,37 @@
 #define U3P_SR_COEF_DIVISOR	1000
 #define U3P_FM_DET_CYCLE_CNT	1024
 
+enum mt_phy_version {
+	MT_PHY_V1 = 1,
+	MT_PHY_V2,
+};
+
 struct mt65xx_phy_pdata {
 	/* avoid RX sensitivity level degradation only for mt8173 */
 	bool avoid_rx_sen_degradation;
+	enum mt_phy_version version;
+};
+
+struct u2phy_banks {
+	void __iomem *misc;
+	void __iomem *fmreg;
+	void __iomem *com;
+};
+
+struct u3phy_banks {
+	void __iomem *spllc;
+	void __iomem *chip;
+	void __iomem *phyd; /* include u3phyd_bank2 */
+	void __iomem *phya; /* include u3phya_da */
 };
 
 struct mt65xx_phy_instance {
 	struct phy *phy;
 	void __iomem *port_base;
+	union {
+		struct u2phy_banks u2_banks;
+		struct u3phy_banks u3_banks;
+	};
 	u32 index;
 	u8 type;
 };
@@ -158,49 +186,53 @@ struct mt65xx_u3phy {
 static void hs_slew_rate_calibrate(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *sif_base = u3phy->sif_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *fmreg = u2_banks->fmreg;
+	void __iomem *com = u2_banks->com;
 	int calibration_val;
 	int fm_out;
 	u32 tmp;
 
 	/* enable USB ring oscillator */
-	tmp = readl(instance->port_base + U3P_USBPHYACR5);
+	tmp = readl(com + U3P_USBPHYACR5);
 	tmp |= PA5_RG_U2_HSTX_SRCAL_EN;
-	writel(tmp, instance->port_base + U3P_USBPHYACR5);
+	writel(tmp, com + U3P_USBPHYACR5);
 	udelay(1);
 
 	/*enable free run clock */
-	tmp = readl(sif_base + U3P_U2FREQ_FMMONR1);
+	tmp = readl(fmreg + U3P_U2FREQ_FMMONR1);
 	tmp |= P2F_RG_FRCK_EN;
-	writel(tmp, sif_base + U3P_U2FREQ_FMMONR1);
+	writel(tmp, fmreg + U3P_U2FREQ_FMMONR1);
 
 	/* set cycle count as 1024, and select u2 channel */
-	tmp = readl(sif_base + U3P_U2FREQ_FMCR0);
+	tmp = readl(fmreg + U3P_U2FREQ_FMCR0);
 	tmp &= ~(P2F_RG_CYCLECNT | P2F_RG_MONCLK_SEL);
 	tmp |= P2F_RG_CYCLECNT_VAL(U3P_FM_DET_CYCLE_CNT);
-	tmp |= P2F_RG_MONCLK_SEL_VAL(instance->index >> 1);
-	writel(tmp, sif_base + U3P_U2FREQ_FMCR0);
+	if (u3phy->pdata->version == MT_PHY_V1)
+		tmp |= P2F_RG_MONCLK_SEL_VAL(instance->index >> 1);
+
+	writel(tmp, fmreg + U3P_U2FREQ_FMCR0);
 
 	/* enable frequency meter */
-	tmp = readl(sif_base + U3P_U2FREQ_FMCR0);
+	tmp = readl(fmreg + U3P_U2FREQ_FMCR0);
 	tmp |= P2F_RG_FREQDET_EN;
-	writel(tmp, sif_base + U3P_U2FREQ_FMCR0);
+	writel(tmp, fmreg + U3P_U2FREQ_FMCR0);
 
 	/* ignore return value */
-	readl_poll_timeout(sif_base + U3P_U2FREQ_FMMONR1, tmp,
+	readl_poll_timeout(fmreg + U3P_U2FREQ_FMMONR1, tmp,
 		  (tmp & P2F_USB_FM_VALID), 10, 200);
 
-	fm_out = readl(sif_base + U3P_U2FREQ_VALUE);
+	fm_out = readl(fmreg + U3P_U2FREQ_VALUE);
 
 	/* disable frequency meter */
-	tmp = readl(sif_base + U3P_U2FREQ_FMCR0);
+	tmp = readl(fmreg + U3P_U2FREQ_FMCR0);
 	tmp &= ~P2F_RG_FREQDET_EN;
-	writel(tmp, sif_base + U3P_U2FREQ_FMCR0);
+	writel(tmp, fmreg + U3P_U2FREQ_FMCR0);
 
 	/*disable free run clock */
-	tmp = readl(sif_base + U3P_U2FREQ_FMMONR1);
+	tmp = readl(fmreg + U3P_U2FREQ_FMMONR1);
 	tmp &= ~P2F_RG_FRCK_EN;
-	writel(tmp, sif_base + U3P_U2FREQ_FMMONR1);
+	writel(tmp, fmreg + U3P_U2FREQ_FMMONR1);
 
 	if (fm_out) {
 		/* ( 1024 / FM_OUT ) x reference clock frequency x 0.028 */
@@ -215,48 +247,48 @@ static void hs_slew_rate_calibrate(struct mt65xx_u3phy *u3phy,
 		instance->index, fm_out, calibration_val);
 
 	/* set HS slew rate */
-	tmp = readl(instance->port_base + U3P_USBPHYACR5);
+	tmp = readl(com + U3P_USBPHYACR5);
 	tmp &= ~PA5_RG_U2_HSTX_SRCTRL;
 	tmp |= PA5_RG_U2_HSTX_SRCTRL_VAL(calibration_val);
-	writel(tmp, instance->port_base + U3P_USBPHYACR5);
+	writel(tmp, com + U3P_USBPHYACR5);
 
 	/* disable USB ring oscillator */
-	tmp = readl(instance->port_base + U3P_USBPHYACR5);
+	tmp = readl(com + U3P_USBPHYACR5);
 	tmp &= ~PA5_RG_U2_HSTX_SRCAL_EN;
-	writel(tmp, instance->port_base + U3P_USBPHYACR5);
+	writel(tmp, com + U3P_USBPHYACR5);
 }
 
 static void u3_phy_instance_init(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u3phy_banks *u3_banks = &instance->u3_banks;
 	u32 tmp;
 
 	/* gating PCIe Analog XTAL clock */
-	tmp = readl(u3phy->sif_base + U3P_XTALCTL3);
+	tmp = readl(u3_banks->spllc + U3P_SPLLC_XTALCTL3);
 	tmp |= XC3_RG_U3_XTAL_RX_PWD | XC3_RG_U3_FRC_XTAL_RX_PWD;
-	writel(tmp, u3phy->sif_base + U3P_XTALCTL3);
+	writel(tmp, u3_banks->spllc + U3P_SPLLC_XTALCTL3);
 
 	/* gating XSQ */
-	tmp = readl(port_base + U3P_U3PHYA_DA_REG0);
+	tmp = readl(u3_banks->phya + U3P_U3_PHYA_DA_REG0);
 	tmp &= ~P3A_RG_XTAL_EXT_EN_U3;
 	tmp |= P3A_RG_XTAL_EXT_EN_U3_VAL(2);
-	writel(tmp, port_base + U3P_U3PHYA_DA_REG0);
+	writel(tmp, u3_banks->phya + U3P_U3_PHYA_DA_REG0);
 
-	tmp = readl(port_base + U3P_U3_PHYA_REG9);
+	tmp = readl(u3_banks->phya + U3P_U3_PHYA_REG9);
 	tmp &= ~P3A_RG_RX_DAC_MUX;
 	tmp |= P3A_RG_RX_DAC_MUX_VAL(4);
-	writel(tmp, port_base + U3P_U3_PHYA_REG9);
+	writel(tmp, u3_banks->phya + U3P_U3_PHYA_REG9);
 
-	tmp = readl(port_base + U3P_U3_PHYA_REG6);
+	tmp = readl(u3_banks->phya + U3P_U3_PHYA_REG6);
 	tmp &= ~P3A_RG_TX_EIDLE_CM;
 	tmp |= P3A_RG_TX_EIDLE_CM_VAL(0xe);
-	writel(tmp, port_base + U3P_U3_PHYA_REG6);
+	writel(tmp, u3_banks->phya + U3P_U3_PHYA_REG6);
 
-	tmp = readl(port_base + U3P_PHYD_CDR1);
+	tmp = readl(u3_banks->phyd + U3P_U3_PHYD_CDR1);
 	tmp &= ~(P3D_RG_CDR_BIR_LTD0 | P3D_RG_CDR_BIR_LTD1);
 	tmp |= P3D_RG_CDR_BIR_LTD0_VAL(0xc) | P3D_RG_CDR_BIR_LTD1_VAL(0x3);
-	writel(tmp, port_base + U3P_PHYD_CDR1);
+	writel(tmp, u3_banks->phyd + U3P_U3_PHYD_CDR1);
 
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, instance->index);
 }
@@ -264,51 +296,52 @@ static void u3_phy_instance_init(struct mt65xx_u3phy *u3phy,
 static void phy_instance_init(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *com = u2_banks->com;
 	u32 index = instance->index;
 	u32 tmp;
 
 	/* switch to USB function. (system register, force ip into usb mode) */
-	tmp = readl(port_base + U3P_U2PHYDTM0);
+	tmp = readl(com + U3P_U2PHYDTM0);
 	tmp &= ~P2C_FORCE_UART_EN;
 	tmp |= P2C_RG_XCVRSEL_VAL(1) | P2C_RG_DATAIN_VAL(0);
-	writel(tmp, port_base + U3P_U2PHYDTM0);
+	writel(tmp, com + U3P_U2PHYDTM0);
 
-	tmp = readl(port_base + U3P_U2PHYDTM1);
+	tmp = readl(com + U3P_U2PHYDTM1);
 	tmp &= ~P2C_RG_UART_EN;
-	writel(tmp, port_base + U3P_U2PHYDTM1);
+	writel(tmp, com + U3P_U2PHYDTM1);
 
 	if (!index) {
-		tmp = readl(port_base + U3P_U2PHYACR4);
+		tmp = readl(com + U3P_U2PHYACR4);
 		tmp &= ~P2C_U2_GPIO_CTR_MSK;
-		writel(tmp, port_base + U3P_U2PHYACR4);
+		writel(tmp, com + U3P_U2PHYACR4);
 	}
 
 	if (u3phy->pdata->avoid_rx_sen_degradation) {
 		if (!index) {
-			tmp = readl(port_base + U3P_USBPHYACR2);
+			tmp = readl(com + U3P_USBPHYACR2);
 			tmp |= PA2_RG_SIF_U2PLL_FORCE_EN;
-			writel(tmp, port_base + U3P_USBPHYACR2);
+			writel(tmp, com + U3P_USBPHYACR2);
 
-			tmp = readl(port_base + U3D_U2PHYDCR0);
+			tmp = readl(com + U3D_U2PHYDCR0);
 			tmp &= ~P2C_RG_SIF_U2PLL_FORCE_ON;
-			writel(tmp, port_base + U3D_U2PHYDCR0);
+			writel(tmp, com + U3D_U2PHYDCR0);
 		} else {
-			tmp = readl(port_base + U3D_U2PHYDCR0);
+			tmp = readl(com + U3D_U2PHYDCR0);
 			tmp |= P2C_RG_SIF_U2PLL_FORCE_ON;
-			writel(tmp, port_base + U3D_U2PHYDCR0);
+			writel(tmp, com + U3D_U2PHYDCR0);
 
-			tmp = readl(port_base + U3P_U2PHYDTM0);
+			tmp = readl(com + U3P_U2PHYDTM0);
 			tmp |= P2C_RG_SUSPENDM | P2C_FORCE_SUSPENDM;
-			writel(tmp, port_base + U3P_U2PHYDTM0);
+			writel(tmp, com + U3P_U2PHYDTM0);
 		}
 	}
 
-	tmp = readl(port_base + U3P_USBPHYACR6);
+	tmp = readl(com + U3P_USBPHYACR6);
 	tmp &= ~PA6_RG_U2_BC11_SW_EN;	/* DP/DM BC1.1 path Disable */
 	tmp &= ~PA6_RG_U2_SQTH;
 	tmp |= PA6_RG_U2_SQTH_VAL(2);
-	writel(tmp, port_base + U3P_USBPHYACR6);
+	writel(tmp, com + U3P_USBPHYACR6);
 
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, index);
 }
@@ -316,41 +349,42 @@ static void phy_instance_init(struct mt65xx_u3phy *u3phy,
 static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *com = u2_banks->com;
 	u32 index = instance->index;
 	u32 tmp;
 
 	/* (force_suspendm=0) (let suspendm=1, enable usb 480MHz pll) */
-	tmp = readl(port_base + U3P_U2PHYDTM0);
+	tmp = readl(com + U3P_U2PHYDTM0);
 	tmp &= ~(P2C_FORCE_SUSPENDM | P2C_RG_XCVRSEL);
 	tmp &= ~(P2C_RG_DATAIN | P2C_DTM0_PART_MASK);
-	writel(tmp, port_base + U3P_U2PHYDTM0);
+	writel(tmp, com + U3P_U2PHYDTM0);
 
 	/* OTG Enable */
-	tmp = readl(port_base + U3P_USBPHYACR6);
+	tmp = readl(com + U3P_USBPHYACR6);
 	tmp |= PA6_RG_U2_OTG_VBUSCMP_EN;
-	writel(tmp, port_base + U3P_USBPHYACR6);
+	writel(tmp, com + U3P_USBPHYACR6);
 
 	if (!index) {
 		/* switch 100uA current to SSUSB */
-		tmp = readl(port_base + U3P_USBPHYACR5);
+		tmp = readl(com + U3P_USBPHYACR5);
 		tmp |= PA5_RG_U2_HS_100U_U3_EN;
-		writel(tmp, port_base + U3P_USBPHYACR5);
+		writel(tmp, com + U3P_USBPHYACR5);
 	}
 
-	tmp = readl(port_base + U3P_U2PHYDTM1);
+	tmp = readl(com + U3P_U2PHYDTM1);
 	tmp |= P2C_RG_VBUSVALID | P2C_RG_AVALID;
 	tmp &= ~P2C_RG_SESSEND;
-	writel(tmp, port_base + U3P_U2PHYDTM1);
+	writel(tmp, com + U3P_U2PHYDTM1);
 
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
-		tmp = readl(port_base + U3D_U2PHYDCR0);
+		tmp = readl(com + U3D_U2PHYDCR0);
 		tmp |= P2C_RG_SIF_U2PLL_FORCE_ON;
-		writel(tmp, port_base + U3D_U2PHYDCR0);
+		writel(tmp, com + U3D_U2PHYDCR0);
 
-		tmp = readl(port_base + U3P_U2PHYDTM0);
+		tmp = readl(com + U3P_U2PHYDTM0);
 		tmp |= P2C_RG_SUSPENDM | P2C_FORCE_SUSPENDM;
-		writel(tmp, port_base + U3P_U2PHYDTM0);
+		writel(tmp, com + U3P_U2PHYDTM0);
 	}
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, index);
 }
@@ -358,42 +392,43 @@ static void phy_instance_power_on(struct mt65xx_u3phy *u3phy,
 static void phy_instance_power_off(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *com = u2_banks->com;
 	u32 index = instance->index;
 	u32 tmp;
 
-	tmp = readl(port_base + U3P_U2PHYDTM0);
+	tmp = readl(com + U3P_U2PHYDTM0);
 	tmp &= ~(P2C_RG_XCVRSEL | P2C_RG_DATAIN);
 	tmp |= P2C_FORCE_SUSPENDM;
-	writel(tmp, port_base + U3P_U2PHYDTM0);
+	writel(tmp, com + U3P_U2PHYDTM0);
 
 	/* OTG Disable */
-	tmp = readl(port_base + U3P_USBPHYACR6);
+	tmp = readl(com + U3P_USBPHYACR6);
 	tmp &= ~PA6_RG_U2_OTG_VBUSCMP_EN;
-	writel(tmp, port_base + U3P_USBPHYACR6);
+	writel(tmp, com + U3P_USBPHYACR6);
 
 	if (!index) {
 		/* switch 100uA current back to USB2.0 */
-		tmp = readl(port_base + U3P_USBPHYACR5);
+		tmp = readl(com + U3P_USBPHYACR5);
 		tmp &= ~PA5_RG_U2_HS_100U_U3_EN;
-		writel(tmp, port_base + U3P_USBPHYACR5);
+		writel(tmp, com + U3P_USBPHYACR5);
 	}
 
 	/* let suspendm=0, set utmi into analog power down */
-	tmp = readl(port_base + U3P_U2PHYDTM0);
+	tmp = readl(com + U3P_U2PHYDTM0);
 	tmp &= ~P2C_RG_SUSPENDM;
-	writel(tmp, port_base + U3P_U2PHYDTM0);
+	writel(tmp, com + U3P_U2PHYDTM0);
 	udelay(1);
 
-	tmp = readl(port_base + U3P_U2PHYDTM1);
+	tmp = readl(com + U3P_U2PHYDTM1);
 	tmp &= ~(P2C_RG_VBUSVALID | P2C_RG_AVALID);
 	tmp |= P2C_RG_SESSEND;
-	writel(tmp, port_base + U3P_U2PHYDTM1);
+	writel(tmp, com + U3P_U2PHYDTM1);
 
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
-		tmp = readl(port_base + U3D_U2PHYDCR0);
+		tmp = readl(com + U3D_U2PHYDCR0);
 		tmp &= ~P2C_RG_SIF_U2PLL_FORCE_ON;
-		writel(tmp, port_base + U3D_U2PHYDCR0);
+		writel(tmp, com + U3D_U2PHYDCR0);
 	}
 
 	dev_dbg(u3phy->dev, "%s(%d)\n", __func__, index);
@@ -402,18 +437,55 @@ static void phy_instance_power_off(struct mt65xx_u3phy *u3phy,
 static void phy_instance_exit(struct mt65xx_u3phy *u3phy,
 	struct mt65xx_phy_instance *instance)
 {
-	void __iomem *port_base = instance->port_base;
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	void __iomem *com = u2_banks->com;
 	u32 index = instance->index;
 	u32 tmp;
 
 	if (u3phy->pdata->avoid_rx_sen_degradation && index) {
-		tmp = readl(port_base + U3D_U2PHYDCR0);
+		tmp = readl(com + U3D_U2PHYDCR0);
 		tmp &= ~P2C_RG_SIF_U2PLL_FORCE_ON;
-		writel(tmp, port_base + U3D_U2PHYDCR0);
+		writel(tmp, com + U3D_U2PHYDCR0);
 
-		tmp = readl(port_base + U3P_U2PHYDTM0);
+		tmp = readl(com + U3P_U2PHYDTM0);
 		tmp &= ~P2C_FORCE_SUSPENDM;
-		writel(tmp, port_base + U3P_U2PHYDTM0);
+		writel(tmp, com + U3P_U2PHYDTM0);
+	}
+}
+
+static void phy_v1_banks_init(struct mt65xx_u3phy *u3phy,
+	struct mt65xx_phy_instance *instance)
+{
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	struct u3phy_banks *u3_banks = &instance->u3_banks;
+
+	if (instance->type == PHY_TYPE_USB2) {
+		u2_banks->misc = NULL;
+		u2_banks->fmreg = u3phy->sif_base + SSUSB_SIFSLV_V1_U2FREQ;
+		u2_banks->com = instance->port_base + SSUSB_SIFSLV_V1_U2PHY_COM;
+	} else if (instance->type == PHY_TYPE_USB3) {
+		u3_banks->spllc = u3phy->sif_base + SSUSB_SIFSLV_V1_SPLLC;
+		u3_banks->chip = NULL;
+		u3_banks->phyd = instance->port_base + SSUSB_SIFSLV_V1_U3PHYD;
+		u3_banks->phya = instance->port_base + SSUSB_SIFSLV_V1_U3PHYA;
+	}
+}
+
+static void phy_v2_banks_init(struct mt65xx_u3phy *u3phy,
+	struct mt65xx_phy_instance *instance)
+{
+	struct u2phy_banks *u2_banks = &instance->u2_banks;
+	struct u3phy_banks *u3_banks = &instance->u3_banks;
+
+	if (instance->type == PHY_TYPE_USB2) {
+		u2_banks->misc = instance->port_base + SSUSB_SIFSLV_V2_MISC;
+		u2_banks->fmreg = instance->port_base + SSUSB_SIFSLV_V2_U2FREQ;
+		u2_banks->com = instance->port_base + SSUSB_SIFSLV_V2_U2PHY_COM;
+	} else if (instance->type == PHY_TYPE_USB3) {
+		u3_banks->spllc = instance->port_base + SSUSB_SIFSLV_V2_SPLLC;
+		u3_banks->chip = instance->port_base + SSUSB_SIFSLV_V2_CHIP;
+		u3_banks->phyd = instance->port_base + SSUSB_SIFSLV_V2_U3PHYD;
+		u3_banks->phya = instance->port_base + SSUSB_SIFSLV_V2_U3PHYA;
 	}
 }
 
@@ -490,7 +562,6 @@ static struct phy *mt65xx_phy_xlate(struct device *dev,
 	struct device_node *phy_np = args->np;
 	int index;
 
-
 	if (args->args_count != 1) {
 		dev_err(dev, "invalid number of cells in 'phy' property\n");
 		return ERR_PTR(-EINVAL);
@@ -508,13 +579,21 @@ static struct phy *mt65xx_phy_xlate(struct device *dev,
 	}
 
 	instance->type = args->args[0];
-
 	if (!(instance->type == PHY_TYPE_USB2 ||
 	      instance->type == PHY_TYPE_USB3)) {
 		dev_err(dev, "unsupported device type: %d\n", instance->type);
 		return ERR_PTR(-EINVAL);
 	}
 
+	if (u3phy->pdata->version == MT_PHY_V1) {
+		phy_v1_banks_init(u3phy, instance);
+	} else if (u3phy->pdata->version == MT_PHY_V2) {
+		phy_v2_banks_init(u3phy, instance);
+	} else {
+		dev_err(dev, "phy version is not supported\n");
+		return ERR_PTR(-EINVAL);
+	}
+
 	return instance->phy;
 }
 
@@ -528,14 +607,22 @@ static struct phy *mt65xx_phy_xlate(struct device *dev,
 
 static const struct mt65xx_phy_pdata mt2701_pdata = {
 	.avoid_rx_sen_degradation = false,
+	.version = MT_PHY_V1,
+};
+
+static const struct mt65xx_phy_pdata mt2712_pdata = {
+	.avoid_rx_sen_degradation = false,
+	.version = MT_PHY_V2,
 };
 
 static const struct mt65xx_phy_pdata mt8173_pdata = {
 	.avoid_rx_sen_degradation = true,
+	.version = MT_PHY_V1,
 };
 
 static const struct of_device_id mt65xx_u3phy_id_table[] = {
 	{ .compatible = "mediatek,mt2701-u3phy", .data = &mt2701_pdata },
+	{ .compatible = "mediatek,mt2712-u3phy", .data = &mt2712_pdata },
 	{ .compatible = "mediatek,mt8173-u3phy", .data = &mt8173_pdata },
 	{ },
 };
@@ -571,11 +658,14 @@ static int mt65xx_u3phy_probe(struct platform_device *pdev)
 	u3phy->dev = dev;
 	platform_set_drvdata(pdev, u3phy);
 
-	sif_res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-	u3phy->sif_base = devm_ioremap_resource(dev, sif_res);
-	if (IS_ERR(u3phy->sif_base)) {
-		dev_err(dev, "failed to remap sif regs\n");
-		return PTR_ERR(u3phy->sif_base);
+	if (u3phy->pdata->version == MT_PHY_V1) {
+		/* get banks shared by multiple phys */
+		sif_res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+		u3phy->sif_base = devm_ioremap_resource(dev, sif_res);
+		if (IS_ERR(u3phy->sif_base)) {
+			dev_err(dev, "failed to remap sif regs\n");
+			return PTR_ERR(u3phy->sif_base);
+		}
 	}
 
 	u3phy->u2ref_clk = devm_clk_get(dev, "u2ref_clk");
-- 
1.7.9.5

--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply related

* [RESEND PATCH 4/6] arm64: dts: mt8173: add a new reference clock for usb3 analog phy
From: Chunfeng Yun @ 2017-01-18  6:00 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Mark Rutland, devicetree, Felipe Balbi, Ian Campbell, linux-usb,
	linux-kernel, Chunfeng Yun, Rob Herring, linux-mediatek,
	Matthias Brugger, linux-arm-kernel
In-Reply-To: <1484719214-11989-1-git-send-email-chunfeng.yun@mediatek.com>

add a new reference clock which comes from 26M oscillator directly
for SuperSpeed analog phy. and the old one which comes for PLL is
48M for HighSpeed analog phy.

Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
---
 arch/arm64/boot/dts/mediatek/mt8173.dtsi |    4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/arch/arm64/boot/dts/mediatek/mt8173.dtsi b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
index 12e7027..5d1663b 100644
--- a/arch/arm64/boot/dts/mediatek/mt8173.dtsi
+++ b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
@@ -754,8 +754,8 @@
 		u3phy: usb-phy@11290000 {
 			compatible = "mediatek,mt8173-u3phy";
 			reg = <0 0x11290000 0 0x800>;
-			clocks = <&apmixedsys CLK_APMIXED_REF2USB_TX>;
-			clock-names = "u3phya_ref";
+			clocks = <&apmixedsys CLK_APMIXED_REF2USB_TX>, <&clk26m>;
+			clock-names = "u2ref_clk", "u3ref_clk";
 			#address-cells = <2>;
 			#size-cells = <2>;
 			ranges;
-- 
1.7.9.5

^ permalink raw reply related

* [RESEND PATCH 5/6] arm64: dts: mt8173: split usb SuperSpeed port into two ports
From: Chunfeng Yun @ 2017-01-18  6:00 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Felipe Balbi,
	Ian Campbell, linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Chunfeng Yun, Rob Herring,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Matthias Brugger,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r
In-Reply-To: <1484719214-11989-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

split the old SuperSpeed port node into a HighSpeed one and a new
SuperSpeed one.

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 arch/arm64/boot/dts/mediatek/mt8173.dtsi |   19 +++++++++++++------
 1 file changed, 13 insertions(+), 6 deletions(-)

diff --git a/arch/arm64/boot/dts/mediatek/mt8173.dtsi b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
index 5d1663b..07fd2eb 100644
--- a/arch/arm64/boot/dts/mediatek/mt8173.dtsi
+++ b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
@@ -724,8 +724,9 @@
 			      <0 0x11280700 0 0x0100>;
 			reg-names = "mac", "ippc";
 			interrupts = <GIC_SPI 64 IRQ_TYPE_LEVEL_LOW>;
-			phys = <&phy_port0 PHY_TYPE_USB3>,
-			       <&phy_port1 PHY_TYPE_USB2>;
+			phys = <&u2port0 PHY_TYPE_USB2>,
+			       <&u3port0 PHY_TYPE_USB3>,
+			       <&u2port1 PHY_TYPE_USB2>;
 			power-domains = <&scpsys MT8173_POWER_DOMAIN_USB>;
 			clocks = <&topckgen CLK_TOP_USB30_SEL>,
 				 <&pericfg CLK_PERI_USB0>,
@@ -761,14 +762,20 @@
 			ranges;
 			status = "okay";
 
-			phy_port0: port@11290800 {
-				reg = <0 0x11290800 0 0x800>;
+			u2port0: port@11290800 {
+				reg = <0 0x11290800 0 0x100>;
 				#phy-cells = <1>;
 				status = "okay";
 			};
 
-			phy_port1: port@11291000 {
-				reg = <0 0x11291000 0 0x800>;
+			u3port0: port@11290900 {
+				reg = <0 0x11290900 0 0x700>;
+				#phy-cells = <1>;
+				status = "okay";
+			};
+
+			u2port1: port@11291000 {
+				reg = <0 0x11291000 0 0x100>;
 				#phy-cells = <1>;
 				status = "okay";
 			};
-- 
1.7.9.5

^ permalink raw reply related

* [RESEND PATCH 6/6] dt-bindings: phy-mt65xx-usb: add support for mt2712 platform
From: Chunfeng Yun @ 2017-01-18  6:00 UTC (permalink / raw)
  To: Kishon Vijay Abraham I
  Cc: Matthias Brugger, Felipe Balbi, Rob Herring, Mark Rutland,
	Ian Campbell, Chunfeng Yun, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	devicetree-u79uwXL29TY76Z2rM5mHXA
In-Reply-To: <1484719214-11989-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

add a new compatible string for "mt2712", and a new reference clock
for SuperSpeed analog phy;

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 .../devicetree/bindings/phy/phy-mt65xx-usb.txt     |   81 +++++++++++++++++---
 1 file changed, 70 insertions(+), 11 deletions(-)

diff --git a/Documentation/devicetree/bindings/phy/phy-mt65xx-usb.txt b/Documentation/devicetree/bindings/phy/phy-mt65xx-usb.txt
index 33a2b1e..8f91136 100644
--- a/Documentation/devicetree/bindings/phy/phy-mt65xx-usb.txt
+++ b/Documentation/devicetree/bindings/phy/phy-mt65xx-usb.txt
@@ -6,19 +6,25 @@ This binding describes a usb3.0 phy for mt65xx platforms of Medaitek SoC.
 Required properties (controller (parent) node):
  - compatible	: should be one of
 		  "mediatek,mt2701-u3phy"
+		  "mediatek,mt2712-u3phy"
 		  "mediatek,mt8173-u3phy"
- - reg		: offset and length of register for phy, exclude port's
-		  register.
  - clocks	: a list of phandle + clock-specifier pairs, one for each
 		  entry in clock-names
  - clock-names	: must contain
-		  "u3phya_ref": for reference clock of usb3.0 analog phy.
+		  "u2ref_clk": 48M reference clock of HighSpeed analog phy.
+		  "u3ref_clk": 26M reference clock of SuperSpeed analog phy,
+			sometimes is 24M, 25M or 27M, depended on platform.
 
 Required nodes	: a sub-node is required for each port the controller
 		  provides. Address range information including the usual
 		  'reg' property is used inside these nodes to describe
 		  the controller's topology.
 
+Optional properties (controller (parent) node):
+ - reg		: offset and length of register shared by multiple ports,
+		  exclude port's private register. It is needed on mt2701
+		  and mt8173, but not on mt2712.
+
 Required properties (port (child) node):
 - reg		: address and length of the register set for the port.
 - #phy-cells	: should be 1 (See second example)
@@ -31,21 +37,27 @@ Example:
 u3phy: usb-phy@11290000 {
 	compatible = "mediatek,mt8173-u3phy";
 	reg = <0 0x11290000 0 0x800>;
-	clocks = <&apmixedsys CLK_APMIXED_REF2USB_TX>;
-	clock-names = "u3phya_ref";
+	clocks = <&apmixedsys CLK_APMIXED_REF2USB_TX>, <&clk26m>;
+	clock-names = "u2ref_clk", "u3ref_clk";
 	#address-cells = <2>;
 	#size-cells = <2>;
 	ranges;
 	status = "okay";
 
-	phy_port0: port@11290800 {
-		reg = <0 0x11290800 0 0x800>;
+	u2port0: port@11290800 {
+		reg = <0 0x11290800 0 0x100>;
+		#phy-cells = <1>;
+		status = "okay";
+	};
+
+	u3port0: port@11290900 {
+		reg = <0 0x11290800 0 0x700>;
 		#phy-cells = <1>;
 		status = "okay";
 	};
 
-	phy_port1: port@11291000 {
-		reg = <0 0x11291000 0 0x800>;
+	u2port1: port@11291000 {
+		reg = <0 0x11291000 0 0x100>;
 		#phy-cells = <1>;
 		status = "okay";
 	};
@@ -64,7 +76,54 @@ Example:
 
 usb30: usb@11270000 {
 	...
-	phys = <&phy_port0 PHY_TYPE_USB3>;
-	phy-names = "usb3-0";
+	phys = <&u2port0 PHY_TYPE_USB2>, <&u3port0 PHY_TYPE_USB3>;
+	phy-names = "usb2-0", "usb3-0";
 	...
 };
+
+
+Layout differences of banks between mt8173/mt2701 and mt2712
+-------------------------------------------------------------
+mt8173 and mt2701:
+port        offset    bank
+shared      0x0000    SPLLC
+            0x0100    FMREG
+u2 port0    0x0800    U2PHY_COM
+u3 port0    0x0900    U3PHYD
+            0x0a00    U3PHYD_BANK2
+            0x0b00    U3PHYA
+            0x0c00    U3PHYA_DA
+u2 port1    0x1000    U2PHY_COM
+u3 port1    0x1100    U3PHYD
+            0x1200    U3PHYD_BANK2
+            0x1300    U3PHYA
+            0x1400    U3PHYA_DA
+u2 port2    0x1800    U2PHY_COM
+            ...
+
+mt2712:
+port        offset    bank
+u2 port0    0x0000    MISC
+            0x0100    FMREG
+            0x0300    U2PHY_COM
+u3 port0    0x0700    SPLLC
+            0x0800    CHIP
+            0x0900    U3PHYD
+            0x0a00    U3PHYD_BANK2
+            0x0b00    U3PHYA
+            0x0c00    U3PHYA_DA
+u2 port1    0x1000    MISC
+            0x1100    FMREG
+            0x1300    U2PHY_COM
+u3 port1    0x1700    SPLLC
+            0x1800    CHIP
+            0x1900    U3PHYD
+            0x1a00    U3PHYD_BANK2
+            0x1b00    U3PHYA
+            0x1c00    U3PHYA_DA
+u2 port2    0x2000    MISC
+            ...
+
+    SPLLC shared by u3 ports and FMREG shared by u2 ports on
+mt8173/mt2701 are put back into each port; a new bank MISC for
+u2 ports and CHIP for u3 ports are added on mt2712.
-- 
1.7.9.5

--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply related

* [PATCH 1/6] usb: mtu3: get resources that cause deferred probe earlier
From: Chunfeng Yun @ 2017-01-18  6:08 UTC (permalink / raw)
  To: Mathias Nyman, Felipe Balbi
  Cc: Greg Kroah-Hartman, Matthias Brugger, Rob Herring, Mark Rutland,
	Ian Campbell, Chunfeng Yun, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	devicetree-u79uwXL29TY76Z2rM5mHXA

Some resources such as regulator, clock usually cause deferred
probe, get them earlier to avoid more ineffective processing.

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 drivers/usb/mtu3/mtu3_plat.c |   24 ++++++++++++------------
 1 file changed, 12 insertions(+), 12 deletions(-)

diff --git a/drivers/usb/mtu3/mtu3_plat.c b/drivers/usb/mtu3/mtu3_plat.c
index 7833678..6344859 100644
--- a/drivers/usb/mtu3/mtu3_plat.c
+++ b/drivers/usb/mtu3/mtu3_plat.c
@@ -204,6 +204,18 @@ static int get_ssusb_rscs(struct platform_device *pdev, struct ssusb_mtk *ssusb)
 	int i;
 	int ret;
 
+	ssusb->vusb33 = devm_regulator_get(&pdev->dev, "vusb33");
+	if (IS_ERR(ssusb->vusb33)) {
+		dev_err(dev, "failed to get vusb33\n");
+		return PTR_ERR(ssusb->vusb33);
+	}
+
+	ssusb->sys_clk = devm_clk_get(dev, "sys_ck");
+	if (IS_ERR(ssusb->sys_clk)) {
+		dev_err(dev, "failed to get sys clock\n");
+		return PTR_ERR(ssusb->sys_clk);
+	}
+
 	ssusb->num_phys = of_count_phandle_with_args(node,
 			"phys", "#phy-cells");
 	if (ssusb->num_phys > 0) {
@@ -230,18 +242,6 @@ static int get_ssusb_rscs(struct platform_device *pdev, struct ssusb_mtk *ssusb)
 		return PTR_ERR(ssusb->ippc_base);
 	}
 
-	ssusb->vusb33 = devm_regulator_get(&pdev->dev, "vusb33");
-	if (IS_ERR(ssusb->vusb33)) {
-		dev_err(dev, "failed to get vusb33\n");
-		return PTR_ERR(ssusb->vusb33);
-	}
-
-	ssusb->sys_clk = devm_clk_get(dev, "sys_ck");
-	if (IS_ERR(ssusb->sys_clk)) {
-		dev_err(dev, "failed to get sys clock\n");
-		return PTR_ERR(ssusb->sys_clk);
-	}
-
 	ssusb->dr_mode = usb_get_dr_mode(dev);
 	if (ssusb->dr_mode == USB_DR_MODE_UNKNOWN) {
 		dev_err(dev, "dr_mode is error\n");
-- 
1.7.9.5

--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply related

* [PATCH 2/6] usb: mtu3: add reference clock
From: Chunfeng Yun @ 2017-01-18  6:08 UTC (permalink / raw)
  To: Mathias Nyman, Felipe Balbi
  Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Ian Campbell,
	Greg Kroah-Hartman, linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Chunfeng Yun, Rob Herring,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Matthias Brugger,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r
In-Reply-To: <1484719707-12107-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

usually, the reference clock comes from 26M oscillator directly,
but some SoCs are not, add it for compatibility.

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 drivers/usb/mtu3/mtu3.h      |    1 +
 drivers/usb/mtu3/mtu3_plat.c |   21 +++++++++++++++++++--
 2 files changed, 20 insertions(+), 2 deletions(-)

diff --git a/drivers/usb/mtu3/mtu3.h b/drivers/usb/mtu3/mtu3.h
index ba9df71..aa6fd6a 100644
--- a/drivers/usb/mtu3/mtu3.h
+++ b/drivers/usb/mtu3/mtu3.h
@@ -225,6 +225,7 @@ struct ssusb_mtk {
 	/* common power & clock */
 	struct regulator *vusb33;
 	struct clk *sys_clk;
+	struct clk *ref_clk;
 	/* otg */
 	struct otg_switch_mtk otg_switch;
 	enum usb_dr_mode dr_mode;
diff --git a/drivers/usb/mtu3/mtu3_plat.c b/drivers/usb/mtu3/mtu3_plat.c
index 6344859..19a345d 100644
--- a/drivers/usb/mtu3/mtu3_plat.c
+++ b/drivers/usb/mtu3/mtu3_plat.c
@@ -123,7 +123,13 @@ static int ssusb_rscs_init(struct ssusb_mtk *ssusb)
 	ret = clk_prepare_enable(ssusb->sys_clk);
 	if (ret) {
 		dev_err(ssusb->dev, "failed to enable sys_clk\n");
-		goto clk_err;
+		goto sys_clk_err;
+	}
+
+	ret = clk_prepare_enable(ssusb->ref_clk);
+	if (ret) {
+		dev_err(ssusb->dev, "failed to enable ref_clk\n");
+		goto ref_clk_err;
 	}
 
 	ret = ssusb_phy_init(ssusb);
@@ -143,8 +149,10 @@ static int ssusb_rscs_init(struct ssusb_mtk *ssusb)
 phy_err:
 	ssusb_phy_exit(ssusb);
 phy_init_err:
+	clk_disable_unprepare(ssusb->ref_clk);
+ref_clk_err:
 	clk_disable_unprepare(ssusb->sys_clk);
-clk_err:
+sys_clk_err:
 	regulator_disable(ssusb->vusb33);
 vusb33_err:
 
@@ -154,6 +162,7 @@ static int ssusb_rscs_init(struct ssusb_mtk *ssusb)
 static void ssusb_rscs_exit(struct ssusb_mtk *ssusb)
 {
 	clk_disable_unprepare(ssusb->sys_clk);
+	clk_disable_unprepare(ssusb->ref_clk);
 	regulator_disable(ssusb->vusb33);
 	ssusb_phy_power_off(ssusb);
 	ssusb_phy_exit(ssusb);
@@ -216,6 +225,12 @@ static int get_ssusb_rscs(struct platform_device *pdev, struct ssusb_mtk *ssusb)
 		return PTR_ERR(ssusb->sys_clk);
 	}
 
+	ssusb->ref_clk = devm_clk_get(dev, "ref_ck");
+	if (IS_ERR(ssusb->ref_clk)) {
+		dev_err(dev, "failed to get ref clock\n");
+		return PTR_ERR(ssusb->ref_clk);
+	}
+
 	ssusb->num_phys = of_count_phandle_with_args(node,
 			"phys", "#phy-cells");
 	if (ssusb->num_phys > 0) {
@@ -428,6 +443,7 @@ static int __maybe_unused mtu3_suspend(struct device *dev)
 	ssusb_host_disable(ssusb, true);
 	ssusb_phy_power_off(ssusb);
 	clk_disable_unprepare(ssusb->sys_clk);
+	clk_disable_unprepare(ssusb->ref_clk);
 	ssusb_wakeup_enable(ssusb);
 
 	return 0;
@@ -445,6 +461,7 @@ static int __maybe_unused mtu3_resume(struct device *dev)
 
 	ssusb_wakeup_disable(ssusb);
 	clk_prepare_enable(ssusb->sys_clk);
+	clk_prepare_enable(ssusb->ref_clk);
 	ssusb_phy_power_on(ssusb);
 	ssusb_host_enable(ssusb);
 
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 3/6] usb: xhci-mtk: add reference clock
From: Chunfeng Yun @ 2017-01-18  6:08 UTC (permalink / raw)
  To: Mathias Nyman, Felipe Balbi
  Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Ian Campbell,
	Greg Kroah-Hartman, linux-usb-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Chunfeng Yun, Rob Herring,
	linux-mediatek-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Matthias Brugger,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r
In-Reply-To: <1484719707-12107-1-git-send-email-chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>

usually, the reference clock comes from 26M oscillator directly,
but some SoCs are not, add it for compatibility.

Signed-off-by: Chunfeng Yun <chunfeng.yun-NuS5LvNUpcJWk0Htik3J/w@public.gmane.org>
---
 drivers/usb/host/xhci-mtk.c |   15 +++++++++++++++
 drivers/usb/host/xhci-mtk.h |    1 +
 2 files changed, 16 insertions(+)

diff --git a/drivers/usb/host/xhci-mtk.c b/drivers/usb/host/xhci-mtk.c
index 1094ebd..4d75ac5 100644
--- a/drivers/usb/host/xhci-mtk.c
+++ b/drivers/usb/host/xhci-mtk.c
@@ -212,6 +212,12 @@ static int xhci_mtk_clks_enable(struct xhci_hcd_mtk *mtk)
 {
 	int ret;
 
+	ret = clk_prepare_enable(mtk->ref_clk);
+	if (ret) {
+		dev_err(mtk->dev, "failed to enable ref_clk\n");
+		goto ref_clk_err;
+	}
+
 	ret = clk_prepare_enable(mtk->sys_clk);
 	if (ret) {
 		dev_err(mtk->dev, "failed to enable sys_clk\n");
@@ -238,6 +244,8 @@ static int xhci_mtk_clks_enable(struct xhci_hcd_mtk *mtk)
 usb_p0_err:
 	clk_disable_unprepare(mtk->sys_clk);
 sys_clk_err:
+	clk_disable_unprepare(mtk->ref_clk);
+ref_clk_err:
 	return -EINVAL;
 }
 
@@ -248,6 +256,7 @@ static void xhci_mtk_clks_disable(struct xhci_hcd_mtk *mtk)
 		clk_disable_unprepare(mtk->wk_deb_p0);
 	}
 	clk_disable_unprepare(mtk->sys_clk);
+	clk_disable_unprepare(mtk->ref_clk);
 }
 
 /* only clocks can be turn off for ip-sleep wakeup mode */
@@ -550,6 +559,12 @@ static int xhci_mtk_probe(struct platform_device *pdev)
 		return PTR_ERR(mtk->sys_clk);
 	}
 
+	mtk->ref_clk = devm_clk_get(dev, "ref_ck");
+	if (IS_ERR(mtk->ref_clk)) {
+		dev_err(dev, "fail to get ref_ck\n");
+		return PTR_ERR(mtk->ref_clk);
+	}
+
 	mtk->lpm_support = of_property_read_bool(node, "usb3-lpm-capable");
 
 	ret = usb_wakeup_of_property_parse(mtk, node);
diff --git a/drivers/usb/host/xhci-mtk.h b/drivers/usb/host/xhci-mtk.h
index 2845c49..3aa5e1d 100644
--- a/drivers/usb/host/xhci-mtk.h
+++ b/drivers/usb/host/xhci-mtk.h
@@ -124,6 +124,7 @@ struct xhci_hcd_mtk {
 	struct regulator *vusb33;
 	struct regulator *vbus;
 	struct clk *sys_clk;	/* sys and mac clock */
+	struct clk *ref_clk;
 	struct clk *wk_deb_p0;	/* port0's wakeup debounce clock */
 	struct clk *wk_deb_p1;
 	struct regmap *pericfg;
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 4/6] arm64: dts: mt8173: add reference clock for usb
From: Chunfeng Yun @ 2017-01-18  6:08 UTC (permalink / raw)
  To: Mathias Nyman, Felipe Balbi
  Cc: Greg Kroah-Hartman, Matthias Brugger, Rob Herring, Mark Rutland,
	Ian Campbell, Chunfeng Yun, linux-kernel, linux-arm-kernel,
	linux-usb, linux-mediatek, devicetree
In-Reply-To: <1484719707-12107-1-git-send-email-chunfeng.yun@mediatek.com>

add 26M reference clock for ssusb and xhci nodes

Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
---
 arch/arm64/boot/dts/mediatek/mt8173.dtsi |    6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/arch/arm64/boot/dts/mediatek/mt8173.dtsi b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
index 07fd2eb..e2862b6 100644
--- a/arch/arm64/boot/dts/mediatek/mt8173.dtsi
+++ b/arch/arm64/boot/dts/mediatek/mt8173.dtsi
@@ -729,9 +729,11 @@
 			       <&u2port1 PHY_TYPE_USB2>;
 			power-domains = <&scpsys MT8173_POWER_DOMAIN_USB>;
 			clocks = <&topckgen CLK_TOP_USB30_SEL>,
+				 <&clk26m>,
 				 <&pericfg CLK_PERI_USB0>,
 				 <&pericfg CLK_PERI_USB1>;
 			clock-names = "sys_ck",
+				      "ref_ck",
 				      "wakeup_deb_p0",
 				      "wakeup_deb_p1";
 			mediatek,syscon-wakeup = <&pericfg>;
@@ -746,8 +748,8 @@
 				reg-names = "mac";
 				interrupts = <GIC_SPI 115 IRQ_TYPE_LEVEL_LOW>;
 				power-domains = <&scpsys MT8173_POWER_DOMAIN_USB>;
-				clocks = <&topckgen CLK_TOP_USB30_SEL>;
-				clock-names = "sys_ck";
+				clocks = <&topckgen CLK_TOP_USB30_SEL>, <&clk26m>;
+				clock-names = "sys_ck", "ref_ck";
 				status = "disabled";
 			};
 		};
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 5/6] dt-bindings: mt8173-xhci: add reference clock
From: Chunfeng Yun @ 2017-01-18  6:08 UTC (permalink / raw)
  To: Mathias Nyman, Felipe Balbi
  Cc: Greg Kroah-Hartman, Matthias Brugger, Rob Herring, Mark Rutland,
	Ian Campbell, Chunfeng Yun, linux-kernel, linux-arm-kernel,
	linux-usb, linux-mediatek, devicetree
In-Reply-To: <1484719707-12107-1-git-send-email-chunfeng.yun@mediatek.com>

add a reference clock for compatibility

Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
---
 .../devicetree/bindings/usb/mt8173-xhci.txt        |   10 ++++++----
 1 file changed, 6 insertions(+), 4 deletions(-)

diff --git a/Documentation/devicetree/bindings/usb/mt8173-xhci.txt b/Documentation/devicetree/bindings/usb/mt8173-xhci.txt
index 2a930bd..ab8bb27 100644
--- a/Documentation/devicetree/bindings/usb/mt8173-xhci.txt
+++ b/Documentation/devicetree/bindings/usb/mt8173-xhci.txt
@@ -23,6 +23,7 @@ Required properties:
 	entry in clock-names
  - clock-names : must contain
 	"sys_ck": for clock of xHCI MAC
+	"ref_ck": for reference clock of xHCI MAC
 	"wakeup_deb_p0": for USB wakeup debounce clock of port0
 	"wakeup_deb_p1": for USB wakeup debounce clock of port1
 
@@ -47,10 +48,10 @@ usb30: usb@11270000 {
 	reg-names = "mac", "ippc";
 	interrupts = <GIC_SPI 115 IRQ_TYPE_LEVEL_LOW>;
 	power-domains = <&scpsys MT8173_POWER_DOMAIN_USB>;
-	clocks = <&topckgen CLK_TOP_USB30_SEL>,
+	clocks = <&topckgen CLK_TOP_USB30_SEL>, <&clk26m>,
 		 <&pericfg CLK_PERI_USB0>,
 		 <&pericfg CLK_PERI_USB1>;
-	clock-names = "sys_ck",
+	clock-names = "sys_ck", "ref_ck",
 		      "wakeup_deb_p0",
 		      "wakeup_deb_p1";
 	phys = <&phy_port0 PHY_TYPE_USB3>,
@@ -82,6 +83,7 @@ Required properties:
 	entry in clock-names
  - clock-names : must be
 	"sys_ck": for clock of xHCI MAC
+	"ref_ck": for reference clock of xHCI MAC
 
 Optional properties:
  - vbus-supply : reference to the VBUS regulator;
@@ -94,8 +96,8 @@ usb30: usb@11270000 {
 	reg-names = "mac";
 	interrupts = <GIC_SPI 115 IRQ_TYPE_LEVEL_LOW>;
 	power-domains = <&scpsys MT8173_POWER_DOMAIN_USB>;
-	clocks = <&topckgen CLK_TOP_USB30_SEL>;
-	clock-names = "sys_ck";
+	clocks = <&topckgen CLK_TOP_USB30_SEL>, <&clk26m>;
+	clock-names = "sys_ck", "ref_ck";
 	vusb33-supply = <&mt6397_vusb_reg>;
 	usb3-lpm-capable;
 };
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 6/6] dt-bindings: mt8173-mtu3: add reference clock
From: Chunfeng Yun @ 2017-01-18  6:08 UTC (permalink / raw)
  To: Mathias Nyman, Felipe Balbi
  Cc: Greg Kroah-Hartman, Matthias Brugger, Rob Herring, Mark Rutland,
	Ian Campbell, Chunfeng Yun, linux-kernel, linux-arm-kernel,
	linux-usb, linux-mediatek, devicetree
In-Reply-To: <1484719707-12107-1-git-send-email-chunfeng.yun@mediatek.com>

add a reference clock for compatibility

Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
---
 .../devicetree/bindings/usb/mt8173-mtu3.txt        |   10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/Documentation/devicetree/bindings/usb/mt8173-mtu3.txt b/Documentation/devicetree/bindings/usb/mt8173-mtu3.txt
index e049d19..8c976cd 100644
--- a/Documentation/devicetree/bindings/usb/mt8173-mtu3.txt
+++ b/Documentation/devicetree/bindings/usb/mt8173-mtu3.txt
@@ -10,7 +10,7 @@ Required properties:
  - vusb33-supply : regulator of USB avdd3.3v
  - clocks : a list of phandle + clock-specifier pairs, one for each
 	entry in clock-names
- - clock-names : must contain "sys_ck" for clock of controller;
+ - clock-names : must contain "sys_ck" and "ref_ck" for clock of controller;
 	"wakeup_deb_p0" and "wakeup_deb_p1" are optional, they are
 	depends on "mediatek,enable-wakeup"
  - phys : a list of phandle + phy specifier pairs
@@ -56,10 +56,10 @@ ssusb: usb@11271000 {
 	phys = <&phy_port0 PHY_TYPE_USB3>,
 	       <&phy_port1 PHY_TYPE_USB2>;
 	power-domains = <&scpsys MT8173_POWER_DOMAIN_USB>;
-	clocks = <&topckgen CLK_TOP_USB30_SEL>,
+	clocks = <&topckgen CLK_TOP_USB30_SEL>, <&clk26m>,
 		 <&pericfg CLK_PERI_USB0>,
 		 <&pericfg CLK_PERI_USB1>;
-	clock-names = "sys_ck",
+	clock-names = "sys_ck", "ref_ck",
 		      "wakeup_deb_p0",
 		      "wakeup_deb_p1";
 	vusb33-supply = <&mt6397_vusb_reg>;
@@ -79,8 +79,8 @@ ssusb: usb@11271000 {
 		reg-names = "mac";
 		interrupts = <GIC_SPI 115 IRQ_TYPE_LEVEL_LOW>;
 		power-domains = <&scpsys MT8173_POWER_DOMAIN_USB>;
-		clocks = <&topckgen CLK_TOP_USB30_SEL>;
-		clock-names = "sys_ck";
+		clocks = <&topckgen CLK_TOP_USB30_SEL>, <&clk26m>;
+		clock-names = "sys_ck", "ref_ck";
 		vusb33-supply = <&mt6397_vusb_reg>;
 		status = "disabled";
 	};
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH] mm/memblock.c: remove unnecessary log and clean up
From: Miles Chen @ 2017-01-18  6:16 UTC (permalink / raw)
  To: Andrew Morton
  Cc: linux-kernel, linux-mm, wsd_upstream, linux-mediatek, Miles Chen

There is no variable named flags in memblock_add() and memblock_reserve()
so remove it from the log messages.
This patch also cleans up the type casting for phys_addr_t by using
%pa to print them.

Signed-off-by: Miles Chen <miles.chen@mediatek.com>
---
 mm/memblock.c | 54 +++++++++++++++++++++++++-----------------------------
 1 file changed, 25 insertions(+), 29 deletions(-)

diff --git a/mm/memblock.c b/mm/memblock.c
index 7608bc3..8683f02 100644
--- a/mm/memblock.c
+++ b/mm/memblock.c
@@ -611,10 +611,10 @@ int __init_memblock memblock_add_node(phys_addr_t base, phys_addr_t size,
 
 int __init_memblock memblock_add(phys_addr_t base, phys_addr_t size)
 {
-	memblock_dbg("memblock_add: [%#016llx-%#016llx] flags %#02lx %pF\n",
-		     (unsigned long long)base,
-		     (unsigned long long)base + size - 1,
-		     0UL, (void *)_RET_IP_);
+	phys_addr_t end = base + size - 1;
+
+	memblock_dbg("memblock_add: [%pa-%pa] %pF\n",
+		     &base, &end, (void *)_RET_IP_);
 
 	return memblock_add_range(&memblock.memory, base, size, MAX_NUMNODES, 0);
 }
@@ -718,10 +718,10 @@ int __init_memblock memblock_remove(phys_addr_t base, phys_addr_t size)
 
 int __init_memblock memblock_free(phys_addr_t base, phys_addr_t size)
 {
-	memblock_dbg("   memblock_free: [%#016llx-%#016llx] %pF\n",
-		     (unsigned long long)base,
-		     (unsigned long long)base + size - 1,
-		     (void *)_RET_IP_);
+	phys_addr_t end = base + size - 1;
+
+	memblock_dbg("   memblock_free: [%pa-%pa] %pF\n",
+		     &base, &end, (void *)_RET_IP_);
 
 	kmemleak_free_part_phys(base, size);
 	return memblock_remove_range(&memblock.reserved, base, size);
@@ -729,10 +729,10 @@ int __init_memblock memblock_free(phys_addr_t base, phys_addr_t size)
 
 int __init_memblock memblock_reserve(phys_addr_t base, phys_addr_t size)
 {
-	memblock_dbg("memblock_reserve: [%#016llx-%#016llx] flags %#02lx %pF\n",
-		     (unsigned long long)base,
-		     (unsigned long long)base + size - 1,
-		     0UL, (void *)_RET_IP_);
+	phys_addr_t end = base + size - 1;
+
+	memblock_dbg("memblock_reserve: [%pa-%pa] %pF\n",
+		     &base, &end, (void *)_RET_IP_);
 
 	return memblock_add_range(&memblock.reserved, base, size, MAX_NUMNODES, 0);
 }
@@ -1202,8 +1202,8 @@ phys_addr_t __init memblock_alloc_base(phys_addr_t size, phys_addr_t align, phys
 	alloc = __memblock_alloc_base(size, align, max_addr);
 
 	if (alloc == 0)
-		panic("ERROR: Failed to allocate 0x%llx bytes below 0x%llx.\n",
-		      (unsigned long long) size, (unsigned long long) max_addr);
+		panic("ERROR: Failed to allocate %pa bytes below %pa.\n",
+		      &size, &max_addr);
 
 	return alloc;
 }
@@ -1673,7 +1673,7 @@ phys_addr_t __init_memblock memblock_get_current_limit(void)
 
 static void __init_memblock memblock_dump(struct memblock_type *type, char *name)
 {
-	unsigned long long base, size;
+	phys_addr_t base, end, size;
 	unsigned long flags;
 	int idx;
 	struct memblock_region *rgn;
@@ -1685,23 +1685,24 @@ static void __init_memblock memblock_dump(struct memblock_type *type, char *name
 
 		base = rgn->base;
 		size = rgn->size;
+		end = base + size - 1;
 		flags = rgn->flags;
 #ifdef CONFIG_HAVE_MEMBLOCK_NODE_MAP
 		if (memblock_get_region_node(rgn) != MAX_NUMNODES)
 			snprintf(nid_buf, sizeof(nid_buf), " on node %d",
 				 memblock_get_region_node(rgn));
 #endif
-		pr_info(" %s[%#x]\t[%#016llx-%#016llx], %#llx bytes%s flags: %#lx\n",
-			name, idx, base, base + size - 1, size, nid_buf, flags);
+		pr_info(" %s[%#x]\t[%pa-%pa], %pa bytes%s flags: %#lx\n",
+			name, idx, &base, &end, &size, nid_buf, flags);
 	}
 }
 
 void __init_memblock __memblock_dump_all(void)
 {
 	pr_info("MEMBLOCK configuration:\n");
-	pr_info(" memory size = %#llx reserved size = %#llx\n",
-		(unsigned long long)memblock.memory.total_size,
-		(unsigned long long)memblock.reserved.total_size);
+	pr_info(" memory size = %pa reserved size = %pa\n",
+		&memblock.memory.total_size,
+		&memblock.reserved.total_size);
 
 	memblock_dump(&memblock.memory, "memory");
 	memblock_dump(&memblock.reserved, "reserved");
@@ -1727,19 +1728,14 @@ static int memblock_debug_show(struct seq_file *m, void *private)
 	struct memblock_type *type = m->private;
 	struct memblock_region *reg;
 	int i;
+	phys_addr_t end;
 
 	for (i = 0; i < type->cnt; i++) {
 		reg = &type->regions[i];
-		seq_printf(m, "%4d: ", i);
-		if (sizeof(phys_addr_t) == 4)
-			seq_printf(m, "0x%08lx..0x%08lx\n",
-				   (unsigned long)reg->base,
-				   (unsigned long)(reg->base + reg->size - 1));
-		else
-			seq_printf(m, "0x%016llx..0x%016llx\n",
-				   (unsigned long long)reg->base,
-				   (unsigned long long)(reg->base + reg->size - 1));
+		end = reg->base + reg->size - 1;
 
+		seq_printf(m, "%4d: ", i);
+		seq_printf(m, "%pa..%pa\n", &reg->base, &end);
 	}
 	return 0;
 }
-- 
1.9.1

--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org.  For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>

^ permalink raw reply related

* Re: [PATCH v11 08/12] drm/mediatek: add dsi interrupt control
From: CK Hu @ 2017-01-18  6:21 UTC (permalink / raw)
  To: YT Shen
  Cc: Mark Rutland, devicetree, srv_heupstream, emil.l.velikov,
	linux-kernel, dri-devel, Rob Herring, linux-mediatek,
	Matthias Brugger, yingjoe.chen, shaoming chen, linux-arm-kernel
In-Reply-To: <1484117473-46644-9-git-send-email-yt.shen@mediatek.com>

Hi, YT:

On Wed, 2017-01-11 at 14:51 +0800, YT Shen wrote:
> From: shaoming chen <shaoming.chen@mediatek.com>
> 
> add dsi interrupt control
> 
> Signed-off-by: shaoming chen <shaoming.chen@mediatek.com>

Acked-by: CK Hu <ck.hu@mediatek.com>

> ---
>  drivers/gpu/drm/mediatek/mtk_dsi.c | 92 ++++++++++++++++++++++++++++++++++++++
>  1 file changed, 92 insertions(+)
> 
> diff --git a/drivers/gpu/drm/mediatek/mtk_dsi.c b/drivers/gpu/drm/mediatek/mtk_dsi.c
> index 6f4b3bb..474861a 100644
> --- a/drivers/gpu/drm/mediatek/mtk_dsi.c
> +++ b/drivers/gpu/drm/mediatek/mtk_dsi.c
> @@ -18,6 +18,7 @@
>  #include <drm/drm_panel.h>
>  #include <linux/clk.h>
>  #include <linux/component.h>
> +#include <linux/irq.h>
>  #include <linux/of.h>
>  #include <linux/of_platform.h>
>  #include <linux/of_graph.h>
> @@ -29,6 +30,16 @@
>  
>  #define DSI_START		0x00
>  
> +#define DSI_INTEN		0x08
> +
> +#define DSI_INTSTA		0x0c
> +#define LPRX_RD_RDY_INT_FLAG		BIT(0)
> +#define CMD_DONE_INT_FLAG		BIT(1)
> +#define TE_RDY_INT_FLAG			BIT(2)
> +#define VM_DONE_INT_FLAG		BIT(3)
> +#define EXT_TE_RDY_INT_FLAG		BIT(4)
> +#define DSI_BUSY			BIT(31)
> +
>  #define DSI_CON_CTRL		0x10
>  #define DSI_RESET			BIT(0)
>  #define DSI_EN				BIT(1)
> @@ -71,6 +82,9 @@
>  
>  #define DSI_HSTX_CKL_WC		0x64
>  
> +#define DSI_RACK		0x84
> +#define RACK				BIT(0)
> +
>  #define DSI_PHY_LCCON		0x104
>  #define LC_HS_TX_EN			BIT(0)
>  #define LC_ULPM_EN			BIT(1)
> @@ -137,6 +151,8 @@ struct mtk_dsi {
>  	struct videomode vm;
>  	int refcount;
>  	bool enabled;
> +	u32 irq_data;
> +	wait_queue_head_t irq_wait_queue;
>  };
>  
>  static inline struct mtk_dsi *encoder_to_dsi(struct drm_encoder *e)
> @@ -469,6 +485,64 @@ static void mtk_dsi_start(struct mtk_dsi *dsi)
>  	writel(1, dsi->regs + DSI_START);
>  }
>  
> +static void mtk_dsi_set_interrupt_enable(struct mtk_dsi *dsi)
> +{
> +	u32 inten = LPRX_RD_RDY_INT_FLAG | CMD_DONE_INT_FLAG | VM_DONE_INT_FLAG;
> +
> +	writel(inten, dsi->regs + DSI_INTEN);
> +}
> +
> +static void mtk_dsi_irq_data_set(struct mtk_dsi *dsi, u32 irq_bit)
> +{
> +	dsi->irq_data |= irq_bit;
> +}
> +
> +static __maybe_unused void mtk_dsi_irq_data_clear(struct mtk_dsi *dsi, u32 irq_bit)
> +{
> +	dsi->irq_data &= ~irq_bit;
> +}
> +
> +static __maybe_unused s32 mtk_dsi_wait_for_irq_done(struct mtk_dsi *dsi, u32 irq_flag,
> +				     unsigned int timeout)
> +{
> +	s32 ret = 0;
> +	unsigned long jiffies = msecs_to_jiffies(timeout);
> +
> +	ret = wait_event_interruptible_timeout(dsi->irq_wait_queue,
> +					       dsi->irq_data & irq_flag,
> +					       jiffies);
> +	if (ret == 0) {
> +		DRM_WARN("Wait DSI IRQ(0x%08x) Timeout\n", irq_flag);
> +
> +		mtk_dsi_enable(dsi);
> +		mtk_dsi_reset_engine(dsi);
> +	}
> +
> +	return ret;
> +}
> +
> +static irqreturn_t mtk_dsi_irq(int irq, void *dev_id)
> +{
> +	struct mtk_dsi *dsi = dev_id;
> +	u32 status, tmp;
> +	u32 flag = LPRX_RD_RDY_INT_FLAG | CMD_DONE_INT_FLAG | VM_DONE_INT_FLAG;
> +
> +	status = readl(dsi->regs + DSI_INTSTA) & flag;
> +
> +	if (status) {
> +		do {
> +			mtk_dsi_mask(dsi, DSI_RACK, RACK, RACK);
> +			tmp = readl(dsi->regs + DSI_INTSTA);
> +		} while (tmp & DSI_BUSY);
> +
> +		mtk_dsi_mask(dsi, DSI_INTSTA, status, 0);
> +		mtk_dsi_irq_data_set(dsi, status);
> +		wake_up_interruptible(&dsi->irq_wait_queue);
> +	}
> +
> +	return IRQ_HANDLED;
> +}
> +
>  static void mtk_dsi_poweroff(struct mtk_dsi *dsi)
>  {
>  	if (WARN_ON(dsi->refcount == 0))
> @@ -517,6 +591,7 @@ static void mtk_output_dsi_enable(struct mtk_dsi *dsi)
>  
>  	mtk_dsi_ps_control_vact(dsi);
>  	mtk_dsi_config_vdo_timing(dsi);
> +	mtk_dsi_set_interrupt_enable(dsi);
>  
>  	mtk_dsi_set_mode(dsi);
>  	mtk_dsi_clk_hs_mode(dsi, 1);
> @@ -818,6 +893,7 @@ static int mtk_dsi_probe(struct platform_device *pdev)
>  	struct device *dev = &pdev->dev;
>  	struct device_node *remote_node, *endpoint;
>  	struct resource *regs;
> +	int irq_num;
>  	int comp_id;
>  	int ret;
>  
> @@ -894,6 +970,22 @@ static int mtk_dsi_probe(struct platform_device *pdev)
>  		return ret;
>  	}
>  
> +	irq_num = platform_get_irq(pdev, 0);
> +	if (irq_num < 0) {
> +		dev_err(&pdev->dev, "failed to request dsi irq resource\n");
> +		return -EPROBE_DEFER;
> +	}
> +
> +	irq_set_status_flags(irq_num, IRQ_TYPE_LEVEL_LOW);
> +	ret = devm_request_irq(&pdev->dev, irq_num, mtk_dsi_irq,
> +			       IRQF_TRIGGER_LOW, dev_name(&pdev->dev), dsi);
> +	if (ret) {
> +		dev_err(&pdev->dev, "failed to request mediatek dsi irq\n");
> +		return -EPROBE_DEFER;
> +	}
> +
> +	init_waitqueue_head(&dsi->irq_wait_queue);
> +
>  	platform_set_drvdata(pdev, dsi);
>  
>  	return component_add(&pdev->dev, &mtk_dsi_component_ops);


_______________________________________________
dri-devel mailing list
dri-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/dri-devel

^ permalink raw reply

* Re: [PATCH v11 09/12] drm/mediatek: add dsi transfer function
From: CK Hu @ 2017-01-18  7:49 UTC (permalink / raw)
  To: YT Shen
  Cc: Mark Rutland, devicetree, srv_heupstream, emil.l.velikov,
	linux-kernel, dri-devel, Rob Herring, linux-mediatek,
	Matthias Brugger, yingjoe.chen, shaoming chen, linux-arm-kernel
In-Reply-To: <1484117473-46644-10-git-send-email-yt.shen@mediatek.com>

Hi, YT:

On Wed, 2017-01-11 at 14:51 +0800, YT Shen wrote:
> From: shaoming chen <shaoming.chen@mediatek.com>
> 
> add dsi read/write commands for transfer function
> 
> Signed-off-by: shaoming chen <shaoming.chen@mediatek.com>

Acked-by: CK Hu <ck.hu@mediatek.com>

> ---
>  drivers/gpu/drm/mediatek/mtk_dsi.c | 168 ++++++++++++++++++++++++++++++++++++-
>  1 file changed, 166 insertions(+), 2 deletions(-)
> 
> diff --git a/drivers/gpu/drm/mediatek/mtk_dsi.c b/drivers/gpu/drm/mediatek/mtk_dsi.c
> index 474861a..b3c7fd8 100644
> --- a/drivers/gpu/drm/mediatek/mtk_dsi.c
> +++ b/drivers/gpu/drm/mediatek/mtk_dsi.c
> @@ -24,6 +24,7 @@
>  #include <linux/of_graph.h>
>  #include <linux/phy/phy.h>
>  #include <linux/platform_device.h>
> +#include <video/mipi_display.h>
>  #include <video/videomode.h>
>  
>  #include "mtk_drm_ddp_comp.h"
> @@ -80,8 +81,16 @@
>  #define DSI_HBP_WC		0x54
>  #define DSI_HFP_WC		0x58
>  
> +#define DSI_CMDQ_SIZE		0x60
> +#define CMDQ_SIZE			0x3f
> +
>  #define DSI_HSTX_CKL_WC		0x64
>  
> +#define DSI_RX_DATA0		0x74
> +#define DSI_RX_DATA1		0x78
> +#define DSI_RX_DATA2		0x7c
> +#define DSI_RX_DATA3		0x80
> +
>  #define DSI_RACK		0x84
>  #define RACK				BIT(0)
>  
> @@ -117,6 +126,15 @@
>  #define CLK_HS_POST			(0xff << 8)
>  #define CLK_HS_EXIT			(0xff << 16)
>  
> +#define DSI_CMDQ0		0x180
> +#define CONFIG				(0xff << 0)
> +#define SHORT_PACKET			0
> +#define LONG_PACKET			2
> +#define BTA				BIT(2)
> +#define DATA_ID				(0xff << 8)
> +#define DATA_0				(0xff << 16)
> +#define DATA_1				(0xff << 24)
> +
>  #define T_LPX		5
>  #define T_HS_PREP	6
>  #define T_HS_TRAIL	8
> @@ -125,6 +143,12 @@
>  
>  #define NS_TO_CYCLE(n, c)    ((n) / (c) + (((n) % (c)) ? 1 : 0))
>  
> +#define MTK_DSI_HOST_IS_READ(type) \
> +	((type == MIPI_DSI_GENERIC_READ_REQUEST_0_PARAM) || \
> +	(type == MIPI_DSI_GENERIC_READ_REQUEST_1_PARAM) || \
> +	(type == MIPI_DSI_GENERIC_READ_REQUEST_2_PARAM) || \
> +	(type == MIPI_DSI_DCS_READ))
> +
>  struct phy;
>  
>  struct mtk_dsi {
> @@ -497,12 +521,12 @@ static void mtk_dsi_irq_data_set(struct mtk_dsi *dsi, u32 irq_bit)
>  	dsi->irq_data |= irq_bit;
>  }
>  
> -static __maybe_unused void mtk_dsi_irq_data_clear(struct mtk_dsi *dsi, u32 irq_bit)
> +static void mtk_dsi_irq_data_clear(struct mtk_dsi *dsi, u32 irq_bit)
>  {
>  	dsi->irq_data &= ~irq_bit;
>  }
>  
> -static __maybe_unused s32 mtk_dsi_wait_for_irq_done(struct mtk_dsi *dsi, u32 irq_flag,
> +static s32 mtk_dsi_wait_for_irq_done(struct mtk_dsi *dsi, u32 irq_flag,
>  				     unsigned int timeout)
>  {
>  	s32 ret = 0;
> @@ -832,9 +856,149 @@ static int mtk_dsi_host_detach(struct mipi_dsi_host *host,
>  	return 0;
>  }
>  
> +static void mtk_dsi_wait_for_idle(struct mtk_dsi *dsi)
> +{
> +	u32 timeout_ms = 500000; /* total 1s ~ 2s timeout */
> +
> +	while (timeout_ms--) {
> +		if (!(readl(dsi->regs + DSI_INTSTA) & DSI_BUSY))
> +			break;
> +
> +		usleep_range(2, 4);
> +	}
> +
> +	if (timeout_ms == 0) {
> +		DRM_WARN("polling dsi wait not busy timeout!\n");
> +
> +		mtk_dsi_enable(dsi);
> +		mtk_dsi_reset_engine(dsi);
> +	}
> +}
> +
> +static u32 mtk_dsi_recv_cnt(u8 type, u8 *read_data)
> +{
> +	switch (type) {
> +	case MIPI_DSI_RX_GENERIC_SHORT_READ_RESPONSE_1BYTE:
> +	case MIPI_DSI_RX_DCS_SHORT_READ_RESPONSE_1BYTE:
> +		return 1;
> +	case MIPI_DSI_RX_GENERIC_SHORT_READ_RESPONSE_2BYTE:
> +	case MIPI_DSI_RX_DCS_SHORT_READ_RESPONSE_2BYTE:
> +		return 2;
> +	case MIPI_DSI_RX_GENERIC_LONG_READ_RESPONSE:
> +	case MIPI_DSI_RX_DCS_LONG_READ_RESPONSE:
> +		return read_data[1] + read_data[2] * 16;
> +	case MIPI_DSI_RX_ACKNOWLEDGE_AND_ERROR_REPORT:
> +		DRM_INFO("type is 0x02, try again\n");
> +		break;
> +	default:
> +		DRM_INFO("type(0x%x) cannot be non-recognite\n", type);
> +		break;
> +	}
> +
> +	return 0;
> +}
> +
> +static void mtk_dsi_cmdq(struct mtk_dsi *dsi, const struct mipi_dsi_msg *msg)
> +{
> +	const char *tx_buf = msg->tx_buf;
> +	u8 config, cmdq_size, cmdq_off, type = msg->type;
> +	u32 reg_val, cmdq_mask, i;
> +
> +	if (MTK_DSI_HOST_IS_READ(type))
> +		config = BTA;
> +	else
> +		config = (msg->tx_len > 2) ? LONG_PACKET : SHORT_PACKET;
> +
> +	if (msg->tx_len > 2) {
> +		cmdq_size = 1 + (msg->tx_len + 3) / 4;
> +		cmdq_off = 4;
> +		cmdq_mask = CONFIG | DATA_ID | DATA_0 | DATA_1;
> +		reg_val = (msg->tx_len << 16) | (type << 8) | config;
> +	} else {
> +		cmdq_size = 1;
> +		cmdq_off = 2;
> +		cmdq_mask = CONFIG | DATA_ID;
> +		reg_val = (type << 8) | config;
> +	}
> +
> +	for (i = 0; i < msg->tx_len; i++)
> +		writeb(tx_buf[i], dsi->regs + DSI_CMDQ0 + cmdq_off + i);
> +
> +	mtk_dsi_mask(dsi, DSI_CMDQ0, cmdq_mask, reg_val);
> +	mtk_dsi_mask(dsi, DSI_CMDQ_SIZE, CMDQ_SIZE, cmdq_size);
> +}
> +
> +static ssize_t mtk_dsi_host_send_cmd(struct mtk_dsi *dsi,
> +				     const struct mipi_dsi_msg *msg, u8 flag)
> +{
> +	mtk_dsi_wait_for_idle(dsi);
> +	mtk_dsi_irq_data_clear(dsi, flag);
> +	mtk_dsi_cmdq(dsi, msg);
> +	mtk_dsi_start(dsi);
> +
> +	if (!mtk_dsi_wait_for_irq_done(dsi, flag, 2000))
> +		return -ETIME;
> +	else
> +		return 0;
> +}
> +
> +static ssize_t mtk_dsi_host_transfer(struct mipi_dsi_host *host,
> +				     const struct mipi_dsi_msg *msg)
> +{
> +	struct mtk_dsi *dsi = host_to_dsi(host);
> +	u32 recv_cnt, i;
> +	u8 read_data[16];
> +	void *src_addr;
> +	u8 irq_flag = CMD_DONE_INT_FLAG;
> +
> +	if (readl(dsi->regs + DSI_MODE_CTRL) & MODE) {
> +		DRM_ERROR("dsi engine is not command mode\n");
> +		return -EINVAL;
> +	}
> +
> +	if (MTK_DSI_HOST_IS_READ(msg->type))
> +		irq_flag |= LPRX_RD_RDY_INT_FLAG;
> +
> +	if (mtk_dsi_host_send_cmd(dsi, msg, irq_flag) < 0)
> +		return -ETIME;
> +
> +	if (!MTK_DSI_HOST_IS_READ(msg->type))
> +		return 0;
> +
> +	if (!msg->rx_buf) {
> +		DRM_ERROR("dsi receive buffer size may be NULL\n");
> +		return -EINVAL;
> +	}
> +
> +	for (i = 0; i < 16; i++)
> +		*(read_data + i) = readb(dsi->regs + DSI_RX_DATA0 + i);
> +
> +	recv_cnt = mtk_dsi_recv_cnt(read_data[0], read_data);
> +
> +	if (recv_cnt > 2)
> +		src_addr = &read_data[4];
> +	else
> +		src_addr = &read_data[1];
> +
> +	if (recv_cnt > 10)
> +		recv_cnt = 10;
> +
> +	if (recv_cnt > msg->rx_len)
> +		recv_cnt = msg->rx_len;
> +
> +	if (recv_cnt)
> +		memcpy(msg->rx_buf, src_addr, recv_cnt);
> +
> +	DRM_INFO("dsi get %d byte data from the panel address(0x%x)\n",
> +		 recv_cnt, *((u8 *)(msg->tx_buf)));
> +
> +	return recv_cnt;
> +}
> +
>  static const struct mipi_dsi_host_ops mtk_dsi_ops = {
>  	.attach = mtk_dsi_host_attach,
>  	.detach = mtk_dsi_host_detach,
> +	.transfer = mtk_dsi_host_transfer,
>  };
>  
>  static int mtk_dsi_bind(struct device *dev, struct device *master, void *data)


_______________________________________________
dri-devel mailing list
dri-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/dri-devel

^ permalink raw reply

* [RESEND PATCH 0/2] Add i2c DT binding and device node for Mediatek MT2701 Soc
From: Jun Gao @ 2017-01-18  9:40 UTC (permalink / raw)
  To: Wolfram Sang, Matthias Brugger
  Cc: devicetree, srv_heupstream, linux-kernel, linux-mediatek,
	linux-i2c, linux-arm-kernel

This patch series based on v4.10-rc2, include MT2701 i2c DT binding and device node.

Dependent on "Add clock and power domain DT nodes for Mediatek MT2701"[1].

[1] http://lists.infradead.org/pipermail/linux-mediatek/2016-December/007637.html

Jun Gao (2):
  Documentation: devicetree: Add i2c binding for mediatek MT2701 Soc
    Platform
  arm: dts: mt2701: Add i2c device node

 .../devicetree/bindings/i2c/i2c-mt6577.txt         |   11 ++---
 arch/arm/boot/dts/mt2701-evb.dts                   |   44 ++++++++++++++++++++
 arch/arm/boot/dts/mt2701.dtsi                      |   42 +++++++++++++++++++
 3 files changed, 92 insertions(+), 5 deletions(-)

--
1.7.9.5

^ permalink raw reply

* [RESEND PATCH 1/2] Documentation: devicetree: Add i2c binding for mediatek MT2701 Soc Platform
From: Jun Gao @ 2017-01-18  9:41 UTC (permalink / raw)
  To: Wolfram Sang, Matthias Brugger
  Cc: devicetree, srv_heupstream, Jun Gao, linux-kernel, linux-mediatek,
	linux-i2c, linux-arm-kernel
In-Reply-To: <1484732461-13594-1-git-send-email-jun.gao@mediatek.com>

From: Jun Gao <jun.gao@mediatek.com>

This add i2c DT binding to i2c-mt6577.txt for MT2701.

Signed-off-by: Jun Gao <jun.gao@mediatek.com>
---
 .../devicetree/bindings/i2c/i2c-mt6577.txt         |   11 ++++++-----
 1 file changed, 6 insertions(+), 5 deletions(-)

diff --git a/Documentation/devicetree/bindings/i2c/i2c-mt6577.txt b/Documentation/devicetree/bindings/i2c/i2c-mt6577.txt
index 0ce6fa3..ef22ecf 100644
--- a/Documentation/devicetree/bindings/i2c/i2c-mt6577.txt
+++ b/Documentation/devicetree/bindings/i2c/i2c-mt6577.txt
@@ -4,11 +4,12 @@ The Mediatek's I2C controller is used to interface with I2C devices.
 
 Required properties:
   - compatible: value should be either of the following.
-      (a) "mediatek,mt6577-i2c", for i2c compatible with mt6577 i2c.
-      (b) "mediatek,mt6589-i2c", for i2c compatible with mt6589 i2c.
-      (c) "mediatek,mt8127-i2c", for i2c compatible with mt8127 i2c.
-      (d) "mediatek,mt8135-i2c", for i2c compatible with mt8135 i2c.
-      (e) "mediatek,mt8173-i2c", for i2c compatible with mt8173 i2c.
+	"mediatek,mt2701-i2c", for i2c compatible with mt2701 i2c.
+	"mediatek,mt6577-i2c", for i2c compatible with mt6577 i2c.
+	"mediatek,mt6589-i2c", for i2c compatible with mt6589 i2c.
+	"mediatek,mt8127-i2c", for i2c compatible with mt8127 i2c.
+	"mediatek,mt8135-i2c", for i2c compatible with mt8135 i2c.
+	"mediatek,mt8173-i2c", for i2c compatible with mt8173 i2c.
   - reg: physical base address of the controller and dma base, length of memory
     mapped region.
   - interrupts: interrupt number to the cpu.
-- 
1.7.9.5

^ permalink raw reply related

* [RESEND PATCH 2/2] arm: dts: mt2701: Add i2c device node
From: Jun Gao @ 2017-01-18  9:41 UTC (permalink / raw)
  To: Wolfram Sang, Matthias Brugger
  Cc: srv_heupstream, devicetree, linux-i2c, linux-arm-kernel,
	linux-kernel, linux-mediatek, Jun Gao
In-Reply-To: <1484732461-13594-1-git-send-email-jun.gao@mediatek.com>

From: Jun Gao <jun.gao@mediatek.com>

Add i2c device node for MT2701.

Signed-off-by: Jun Gao <jun.gao@mediatek.com>
---
 arch/arm/boot/dts/mt2701-evb.dts |   44 ++++++++++++++++++++++++++++++++++++++
 arch/arm/boot/dts/mt2701.dtsi    |   42 ++++++++++++++++++++++++++++++++++++
 2 files changed, 86 insertions(+)

diff --git a/arch/arm/boot/dts/mt2701-evb.dts b/arch/arm/boot/dts/mt2701-evb.dts
index 082ca88..a908e94 100644
--- a/arch/arm/boot/dts/mt2701-evb.dts
+++ b/arch/arm/boot/dts/mt2701-evb.dts
@@ -24,6 +24,50 @@
 	};
 };
 
+&i2c0 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&i2c0_pins_a>;
+	status = "okay";
+};
+
+&i2c1 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&i2c1_pins_a>;
+	status = "okay";
+};
+
+&i2c2 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&i2c2_pins_a>;
+	status = "okay";
+};
+
+&pio {
+	i2c0_pins_a: i2c0@0 {
+		pins1 {
+			pinmux = <MT2701_PIN_75_SDA0__FUNC_SDA0>,
+				 <MT2701_PIN_76_SCL0__FUNC_SCL0>;
+			bias-disable;
+		};
+	};
+
+	i2c1_pins_a: i2c1@0 {
+		pins1 {
+			pinmux = <MT2701_PIN_57_SDA1__FUNC_SDA1>,
+				 <MT2701_PIN_58_SCL1__FUNC_SCL1>;
+			bias-disable;
+		};
+	};
+
+	i2c2_pins_a: i2c2@0 {
+		pins1 {
+			pinmux = <MT2701_PIN_77_SDA2__FUNC_SDA2>,
+				 <MT2701_PIN_78_SCL2__FUNC_SCL2>;
+			bias-disable;
+		};
+	};
+};
+
 &uart0 {
 	status = "okay";
 };
diff --git a/arch/arm/boot/dts/mt2701.dtsi b/arch/arm/boot/dts/mt2701.dtsi
index bdf8954..0d1539f 100644
--- a/arch/arm/boot/dts/mt2701.dtsi
+++ b/arch/arm/boot/dts/mt2701.dtsi
@@ -227,6 +227,48 @@
 		status = "disabled";
 	};
 
+	i2c0: i2c@11007000 {
+		compatible = "mediatek,mt2701-i2c",
+			     "mediatek,mt6577-i2c";
+		reg = <0 0x11007000 0 0x70>,
+		      <0 0x11000200 0 0x80>;
+		interrupts = <GIC_SPI 44 IRQ_TYPE_LEVEL_LOW>;
+		clock-div = <16>;
+		clocks = <&pericfg CLK_PERI_I2C0>, <&pericfg CLK_PERI_AP_DMA>;
+		clock-names = "main", "dma";
+		#address-cells = <1>;
+		#size-cells = <0>;
+		status = "disabled";
+	};
+
+	i2c1: i2c@11008000 {
+		compatible = "mediatek,mt2701-i2c",
+			     "mediatek,mt6577-i2c";
+		reg = <0 0x11008000 0 0x70>,
+		      <0 0x11000280 0 0x80>;
+		interrupts = <GIC_SPI 45 IRQ_TYPE_LEVEL_LOW>;
+		clock-div = <16>;
+		clocks = <&pericfg CLK_PERI_I2C1>, <&pericfg CLK_PERI_AP_DMA>;
+		clock-names = "main", "dma";
+		#address-cells = <1>;
+		#size-cells = <0>;
+		status = "disabled";
+	};
+
+	i2c2: i2c@11009000 {
+		compatible = "mediatek,mt2701-i2c",
+			     "mediatek,mt6577-i2c";
+		reg = <0 0x11009000 0 0x70>,
+		      <0 0x11000300 0 0x80>;
+		interrupts = <GIC_SPI 46 IRQ_TYPE_LEVEL_LOW>;
+		clock-div = <16>;
+		clocks = <&pericfg CLK_PERI_I2C2>, <&pericfg CLK_PERI_AP_DMA>;
+		clock-names = "main", "dma";
+		#address-cells = <1>;
+		#size-cells = <0>;
+		status = "disabled";
+	};
+
 	mmsys: syscon@14000000 {
 		compatible = "mediatek,mt2701-mmsys", "syscon";
 		reg = <0 0x14000000 0 0x1000>;
-- 
1.7.9.5

^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox