From: Vivek Gautam <gautam.vivek@samsung.com>
To: kgene.kim@samsung.com, l.majewski@samsung.com,
kyungmin.park@samsung.com, thomas.abraham@linaro.org,
linux-samsung-soc@vger.kernel.org,
linux-arm-kernel@lists.infradead.org,
devicetree-discuss@lists.ozlabs.org, m.szyprowski@samsung.com
Cc: a.kesavan@samsung.com, yulgon.kim@samsung.com,
boyko.lee@samsung.com, av.tikhomirov@samsung.com,
joshi@samsung.com, olofj@google.com, prashanth.g@samsung.com
Subject: [PATCH 8/8] ARM: EXYNOS5: Add PHY initialization code for usb 3.0
Date: Wed, 18 Jul 2012 19:15:28 +0530 [thread overview]
Message-ID: <1342619128-25013-9-git-send-email-gautam.vivek@samsung.com> (raw)
In-Reply-To: <1342619128-25013-1-git-send-email-gautam.vivek@samsung.com>
This patch adds PHY setup functions for usb 3.0 support on exynos5
Signed-off-by: Yulgon Kim <yulgon.kim@samsung.com>
Signed-off-by: Anton Tikhomirov <av.tikhomirov@samsung.com>
Signed-off-by: Vivek Gautam <gautam.vivek@samsung.com>
diff --git a/arch/arm/mach-exynos/setup-usb-phy.c b/arch/arm/mach-exynos/setup-usb-phy.c
index 3f7a26a..f8f64c8 100644
--- a/arch/arm/mach-exynos/setup-usb-phy.c
+++ b/arch/arm/mach-exynos/setup-usb-phy.c
@@ -18,12 +18,14 @@
#include <mach/regs-usb-phy.h>
#include <plat/cpu.h>
#include <plat/usb-phy.h>
+#include <plat/regs-usb3-exynos-drd-phy.h>
#define PHY_ENABLE 1
#define PHY_DISABLE 0
enum usb_phy_type {
USB_PHY = (0x1 << 0),
+ USB_PHY_DRD = (0x1 << 1),
};
static atomic_t host_usage;
@@ -163,11 +165,44 @@ static int exynos4210_usb_phy_clkset(struct platform_device *pdev)
return phyclk;
}
+static u32 exynos_usb_phy30_set_clock(struct platform_device *pdev)
+{
+ u32 reg, refclk;
+
+ refclk = exynos4210_usb_phy_clkset(pdev);
+ reg = EXYNOS_USB3_PHYCLKRST_REFCLKSEL(3) |
+ EXYNOS_USB3_PHYCLKRST_FSEL(refclk);
+
+ switch (refclk) {
+ case EXYNOS5_CLKSEL_50M:
+ reg |= (EXYNOS_USB3_PHYCLKRST_MPLL_MULTIPLIER(0x02) |
+ EXYNOS_USB3_PHYCLKRST_SSC_REF_CLK_SEL(0x00));
+ break;
+ case EXYNOS5_CLKSEL_20M:
+ reg |= (EXYNOS_USB3_PHYCLKRST_MPLL_MULTIPLIER(0x7d) |
+ EXYNOS_USB3_PHYCLKRST_SSC_REF_CLK_SEL(0x00));
+ break;
+ case EXYNOS5_CLKSEL_19200K:
+ reg |= (EXYNOS_USB3_PHYCLKRST_MPLL_MULTIPLIER(0x02) |
+ EXYNOS_USB3_PHYCLKRST_SSC_REF_CLK_SEL(0x88));
+ break;
+ case EXYNOS5_CLKSEL_24M:
+ default:
+ reg |= (EXYNOS_USB3_PHYCLKRST_MPLL_MULTIPLIER(0x68) |
+ EXYNOS_USB3_PHYCLKRST_SSC_REF_CLK_SEL(0x88));
+ break;
+ }
+
+ return reg;
+}
+
static void exynos_usb_phy_control(enum usb_phy_type phy_type , int on)
{
if (soc_is_exynos5250()) {
if (phy_type & USB_PHY)
writel(on, S5P_USBHOST_PHY_CONTROL);
+ if (phy_type & USB_PHY_DRD)
+ writel(on, S5P_USBDRD_PHY_CONTROL);
}
}
@@ -415,6 +450,88 @@ static int exynos5_usb_phy20_exit(struct platform_device *pdev)
return 0;
}
+static int exynos5_usb_phy30_init(struct platform_device *pdev)
+{
+ struct clk *host_clk;
+ u32 reg;
+
+ host_clk = exynos_usb_clock_enable(pdev);
+ if (host_clk == NULL) {
+ dev_err(&pdev->dev, "Failed to enable USB3.0 host clock this time\n");
+ return -1;
+ }
+
+ exynos_usb_phy_control(USB_PHY_DRD, PHY_ENABLE);
+
+ /* Reset USB 3.0 PHY */
+ writel(0x00000000, EXYNOS_USB3_PHYREG0);
+ writel(0x24d4e6e4, EXYNOS_USB3_PHYPARAM0);
+ writel(0x03fff81c, EXYNOS_USB3_PHYPARAM1);
+ writel(0x00000000, EXYNOS_USB3_PHYRESUME);
+
+ writel(0x08000040, EXYNOS_USB3_LINKSYSTEM);
+ writel(0x00000004, EXYNOS_USB3_PHYBATCHG);
+
+ /* PHYTEST POWERDOWN Control */
+ reg = readl(EXYNOS_USB3_PHYTEST);
+ reg &= ~(EXYNOS_USB3_PHYTEST_POWERDOWN_SSP |
+ EXYNOS_USB3_PHYTEST_POWERDOWN_HSP);
+ writel(reg, EXYNOS_USB3_PHYTEST);
+
+ /* UTMI Power Control */
+ writel(EXYNOS_USB3_PHYUTMI_OTGDISABLE, EXYNOS_USB3_PHYUTMI);
+
+ reg = exynos_usb_phy30_set_clock(pdev);
+
+ reg |= (EXYNOS_USB3_PHYCLKRST_PORTRESET |
+ /* Digital power supply in normal operating mode */
+ EXYNOS_USB3_PHYCLKRST_RETENABLEN |
+ /* Enable ref clock for SS function */
+ EXYNOS_USB3_PHYCLKRST_REF_SSP_EN |
+ /* Enable spread spectrum */
+ EXYNOS_USB3_PHYCLKRST_SSC_EN) |
+ EXYNOS_USB3_PHYCLKRST_COMMONONN;
+ writel(reg, EXYNOS_USB3_PHYCLKRST);
+
+ udelay(10);
+
+ reg &= ~(EXYNOS_USB3_PHYCLKRST_PORTRESET);
+ writel(reg, EXYNOS_USB3_PHYCLKRST);
+
+ clk_disable(host_clk);
+ clk_put(host_clk);
+ return 0;
+}
+
+static int exynos5_usb_phy30_exit(struct platform_device *pdev)
+{
+ struct clk *host_clk;
+ u32 reg;
+
+ host_clk = exynos_usb_clock_enable(pdev);
+ if (host_clk == NULL) {
+ dev_err(&pdev->dev, "Failed to enable USB3.0 host clock this time\n");
+ return -1;
+ }
+
+ reg = EXYNOS_USB3_PHYUTMI_OTGDISABLE |
+ EXYNOS_USB3_PHYUTMI_FORCESUSPEND |
+ EXYNOS_USB3_PHYUTMI_FORCESLEEP;
+ writel(reg, EXYNOS_USB3_PHYUTMI);
+
+ /* Control PHYTEST to remove leakage current */
+ reg = readl(EXYNOS_USB3_PHYTEST);
+ reg |= (EXYNOS_USB3_PHYTEST_POWERDOWN_SSP |
+ EXYNOS_USB3_PHYTEST_POWERDOWN_HSP);
+ writel(reg, EXYNOS_USB3_PHYTEST);
+
+ exynos_usb_phy_control(USB_PHY_DRD, PHY_DISABLE);
+
+ clk_disable(host_clk);
+ clk_put(host_clk);
+ return 0;
+}
+
int s5p_usb_phy_init(struct platform_device *pdev, int type)
{
if (type == S5P_USB_PHY_DEVICE)
@@ -424,6 +541,11 @@ int s5p_usb_phy_init(struct platform_device *pdev, int type)
return exynos5_usb_phy20_init(pdev);
else
return exynos4210_usb_phy1_init(pdev);
+ } else if (type == S5P_USB_PHY_DRD) {
+ if (soc_is_exynos5250())
+ return exynos5_usb_phy30_init(pdev);
+ else
+ dev_err(&pdev->dev, "USB 3.0 DRD not present\n");
}
return -EINVAL;
@@ -438,6 +560,11 @@ int s5p_usb_phy_exit(struct platform_device *pdev, int type)
return exynos5_usb_phy20_exit(pdev);
else
return exynos4210_usb_phy1_exit(pdev);
+ } else if (type == S5P_USB_PHY_DRD) {
+ if (soc_is_exynos5250())
+ return exynos5_usb_phy30_exit(pdev);
+ else
+ dev_err(&pdev->dev, "USB 3.0 DRD not present\n");
}
return -EINVAL;
}
diff --git a/arch/arm/plat-samsung/include/plat/regs-usb3-exynos-drd-phy.h b/arch/arm/plat-samsung/include/plat/regs-usb3-exynos-drd-phy.h
new file mode 100644
index 0000000..8efd5c7
--- /dev/null
+++ b/arch/arm/plat-samsung/include/plat/regs-usb3-exynos-drd-phy.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2012 Samsung Electronics Co. Ltd
+ *
+ * Exynos SuperSpeed USB 3.0 DRD Controller PHY registers
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#ifndef __PLAT_SAMSUNG_REGS_USB3_EXYNOS_DRD_PHY_H
+#define __PLAT_SAMSUNG_REGS_USB3_EXYNOS_DRD_PHY_H __FILE__
+
+#define EXYNOS_USB3_PHYREG(x) ((x) + S5P_VA_DRD_PHY)
+
+#define EXYNOS_USB3_LINKSYSTEM EXYNOS_USB3_PHYREG(0x04)
+#define EXYNOS_USB3_PHYUTMI EXYNOS_USB3_PHYREG(0x08)
+
+#define EXYNOS_USB3_PHYUTMI_OTGDISABLE (1 << 6)
+#define EXYNOS_USB3_PHYUTMI_FORCESUSPEND (1 << 1)
+#define EXYNOS_USB3_PHYUTMI_FORCESLEEP (1 << 0)
+
+#define EXYNOS_USB3_PHYPIPE EXYNOS_USB3_PHYREG(0x0C)
+#define EXYNOS_USB3_PHYCLKRST EXYNOS_USB3_PHYREG(0x10)
+
+#define EXYNOS_USB3_PHYCLKRST_SSC_REF_CLK_SEL_MASK (0xff << 23)
+#define EXYNOS_USB3_PHYCLKRST_SSC_REF_CLK_SEL_SHIFT (23)
+#define EXYNOS_USB3_PHYCLKRST_SSC_REF_CLK_SEL_LIMIT (0xff)
+#define EXYNOS_USB3_PHYCLKRST_SSC_REF_CLK_SEL(_x) ((_x) << 23)
+
+#define EXYNOS_USB3_PHYCLKRST_SSC_RANGE_MASK (0x03 << 21)
+#define EXYNOS_USB3_PHYCLKRST_SSC_RANGE_SHIFT (21)
+#define EXYNOS_USB3_PHYCLKRST_SSC_RANGE_LIMIT (0x03)
+#define EXYNOS_USB3_PHYCLKRST_SSC_RANGE(_x) ((_x) << 21)
+
+#define EXYNOS_USB3_PHYCLKRST_SSC_EN (1 << 20)
+#define EXYNOS_USB3_PHYCLKRST_REF_SSP_EN (1 << 19)
+#define EXYNOS_USB3_PHYCLKRST_REF_CLKDIV2 (1 << 18)
+
+#define EXYNOS_USB3_PHYCLKRST_MPLL_MULTIPLIER_MASK (0x7f << 11)
+#define EXYNOS_USB3_PHYCLKRST_MPLL_MULTIPLIER_SHIFT (11)
+#define EXYNOS_USB3_PHYCLKRST_MPLL_MULTIPLIER_LIMIT (0x7f)
+#define EXYNOS_USB3_PHYCLKRST_MPLL_MULTIPLIER(_x) ((_x) << 11)
+
+#define EXYNOS_USB3_PHYCLKRST_FSEL_MASK (0x3f << 5)
+#define EXYNOS_USB3_PHYCLKRST_FSEL_SHIFT (5)
+#define EXYNOS_USB3_PHYCLKRST_FSEL_LIMIT (0x3f)
+#define EXYNOS_USB3_PHYCLKRST_FSEL(_x) ((_x) << 5)
+
+#define EXYNOS_USB3_PHYCLKRST_RETENABLEN (1 << 4)
+
+#define EXYNOS_USB3_PHYCLKRST_REFCLKSEL_MASK (0x03 << 2)
+#define EXYNOS_USB3_PHYCLKRST_REFCLKSEL_SHIFT (2)
+#define EXYNOS_USB3_PHYCLKRST_REFCLKSEL_LIMIT (0x03)
+#define EXYNOS_USB3_PHYCLKRST_REFCLKSEL(_x) ((_x) << 2)
+
+#define EXYNOS_USB3_PHYCLKRST_PORTRESET (1 << 1)
+#define EXYNOS_USB3_PHYCLKRST_COMMONONN (1 << 0)
+
+#define EXYNOS_USB3_PHYREG0 EXYNOS_USB3_PHYREG(0x14)
+#define EXYNOS_USB3_PHYREG1 EXYNOS_USB3_PHYREG(0x18)
+#define EXYNOS_USB3_PHYPARAM0 EXYNOS_USB3_PHYREG(0x1C)
+#define EXYNOS_USB3_PHYPARAM1 EXYNOS_USB3_PHYREG(0x20)
+#define EXYNOS_USB3_PHYTERM EXYNOS_USB3_PHYREG(0x24)
+
+#define EXYNOS_USB3_PHYTEST EXYNOS_USB3_PHYREG(0x28)
+
+#define EXYNOS_USB3_PHYTEST_POWERDOWN_SSP (1 << 3)
+#define EXYNOS_USB3_PHYTEST_POWERDOWN_HSP (1 << 3)
+
+#define EXYNOS_USB3_PHYADP EXYNOS_USB3_PHYREG(0x2C)
+#define EXYNOS_USB3_PHYBATCHG EXYNOS_USB3_PHYREG(0x30)
+#define EXYNOS_USB3_PHYRESUME EXYNOS_USB3_PHYREG(0x34)
+#define EXYNOS_USB3_LINKPORT EXYNOS_USB3_PHYREG(0x44)
+#endif /* __PLAT_SAMSUNG_REGS_USB3_EXYNOS_DRD_PHY_H */
diff --git a/arch/arm/plat-samsung/include/plat/usb-phy.h b/arch/arm/plat-samsung/include/plat/usb-phy.h
index 959bcdb..f784101 100644
--- a/arch/arm/plat-samsung/include/plat/usb-phy.h
+++ b/arch/arm/plat-samsung/include/plat/usb-phy.h
@@ -14,6 +14,7 @@
enum s5p_usb_phy_type {
S5P_USB_PHY_DEVICE,
S5P_USB_PHY_HOST,
+ S5P_USB_PHY_DRD,
};
extern int s5p_usb_phy_init(struct platform_device *pdev, int type);
--
1.7.0.4
prev parent reply other threads:[~2012-07-18 13:45 UTC|newest]
Thread overview: 11+ messages / expand[flat|nested] mbox.gz Atom feed top
2012-07-18 13:45 [PATCH 0/8] EXYNOS5: USB: Add USB 2.0 and USB 3.0 support for exynos5 Vivek Gautam
2012-07-18 13:45 ` [PATCH 1/8] EXYNOS4: USB: Generalising setup-usb-phy driver for exynos Vivek Gautam
2012-07-19 4:23 ` Pankaj Jangra
2012-07-18 13:45 ` [PATCH 2/8] ARM: EXYNOS5: Add machine data for USB 2.0 Vivek Gautam
2012-07-18 13:45 ` [PATCH 3/8] ARM: EXYNOS5: Add OHCI device from device tree Vivek Gautam
2012-07-19 4:06 ` Sachin Kamat
2012-07-18 13:45 ` [PATCH 4/8] ARM: EXYNOS5: Add EHCI " Vivek Gautam
2012-07-18 13:45 ` [PATCH 5/8] ARM: EXYNOS5: Add PHY initialization code for usb 2.0 Vivek Gautam
2012-07-18 13:45 ` [PATCH 6/8] ARM: EXYNOS5: Add machine data for USB3.0 Vivek Gautam
2012-07-18 13:45 ` [PATCH 7/8] ARM: EXYNOS5: Add XHCI device from device tree Vivek Gautam
2012-07-18 13:45 ` Vivek Gautam [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1342619128-25013-9-git-send-email-gautam.vivek@samsung.com \
--to=gautam.vivek@samsung.com \
--cc=a.kesavan@samsung.com \
--cc=av.tikhomirov@samsung.com \
--cc=boyko.lee@samsung.com \
--cc=devicetree-discuss@lists.ozlabs.org \
--cc=joshi@samsung.com \
--cc=kgene.kim@samsung.com \
--cc=kyungmin.park@samsung.com \
--cc=l.majewski@samsung.com \
--cc=linux-arm-kernel@lists.infradead.org \
--cc=linux-samsung-soc@vger.kernel.org \
--cc=m.szyprowski@samsung.com \
--cc=olofj@google.com \
--cc=prashanth.g@samsung.com \
--cc=thomas.abraham@linaro.org \
--cc=yulgon.kim@samsung.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).