Skip to contentSkip to conversation

Add support for the rockchip mmc clock phases using the framework

PATCH Superseded Alexandru M Stan 2 participants 7 messages Nov 15, 2014 – Nov 17, 2014

Subsystems (3)

v2 of 4 Superseded Latest is v4 →

lore
Share & tools
lore
#0 lore raw

v2 cover Add support for the rockchip mmc clock phases using the framework

For now all I have is the getter and setter for the phase, nothing that uses it (that is ready). You can test the getter like this:
localhost ~ # cat /sys/kernel/debug/clk/clk_summary|grep sample -C 1

    sclk_sdio1                            0            0    24000000          0 0
       sdio1_sample                       0            0    12000000          0 0
       sdio1_drv                          0            0    12000000          0 90
--
          sclk_sdmmc                      1            1   297000000          0 0
             sdmmc_sample                 0            0   148500000          0 134
             sdmmc_drv                    0            0   148500000          0 90
--
          sclk_sdio0                      1            1   100000000          0 0
             sdio0_sample                 0            0    50000000          0 0
             sdio0_drv                    0            0    50000000          0 90
          sclk_emmc                       1            1   100000000          0 0
             emmc_sample                  0            0    50000000          0 0
             emmc_drv                     0            0    50000000          0 180

Next thing that will come is some dts changes that will make use of these new clocks, and eventually mmc code will be changed to tune with these clocks.

Changes in v2:
- fixed my cc/to list
- removed dangling #DEFINE DEBUG

Alexandru M Stan (2):
clk: rockchip: add bindings for the mmc clock phases
clk: rockchip: Add support for the mmc clock phases using the
framework

 drivers/clk/rockchip/Makefile          |   1 +
 drivers/clk/rockchip/clk-mmc-phase.c   | 149 +++++++++++++++++++++++++++++++++
 drivers/clk/rockchip/clk-rk3288.c      |  12 +++
 drivers/clk/rockchip/clk.c             |   8 ++
 drivers/clk/rockchip/clk.h             |  23 +++++
 include/dt-bindings/clock/rk3288-cru.h |  10 +++
 6 files changed, 203 insertions(+)
 create mode 100644 drivers/clk/rockchip/clk-mmc-phase.c
Signature · 1 line
2.1.0.rc2.206.gedb03e5
#1 lore raw

PATCH v2 1/2 clk: rockchip: add bindings for the mmc clock phases

This will be used in a later patch for clock phase tuning.

---
Changes in v2: None

 include/dt-bindings/clock/rk3288-cru.h | 10 ++++++++++
 1 file changed, 10 insertions(+)
include/dt-bindings/clock/rk3288-cru.h +10 -0
index 100a08c..465d0f6 100644
@@ -72,6 +72,16 @@
 #define SCLK_HEVC_CABAC		111
 #define SCLK_HEVC_CORE		112
 
+#define SCLK_SDMMC_DRV_PHASE	113
+#define SCLK_SDIO0_DRV_PHASE	114
+#define SCLK_SDIO1_DRV_PHASE	115
+#define SCLK_EMMC_DRV_PHASE	116
+
+#define SCLK_SDMMC_SAMPLE_PHASE	117
+#define SCLK_SDIO0_SAMPLE_PHASE	118
+#define SCLK_SDIO1_SAMPLE_PHASE	119
+#define SCLK_EMMC_SAMPLE_PHASE	120
+
 #define DCLK_VOP0		190
 #define DCLK_VOP1		191
 
Signature · 1 line
2.1.0.rc2.206.gedb03e5
#2 lore raw

Re: [PATCH v2 1/2] clk: rockchip: add bindings for the mmc clock phases

Quoting Alexandru M Stan (2014-11-14 16:00:03)

Quoted 17 lines

This will be used in a later patch for clock phase tuning.

---
Changes in v2: None

 include/dt-bindings/clock/rk3288-cru.h | 10 ++++++++++
 1 file changed, 10 insertions(+)
include/dt-bindings/clock/rk3288-cru.h +0 -0
index 100a08c..465d0f6 100644
@@ -72,6 +72,16 @@
 #define SCLK_HEVC_CABAC                111
 #define SCLK_HEVC_CORE         112

include/dt-bindings/clock/rk3288-cru.h line 83

Quoted 10 lines
include/dt-bindings/clock/rk3288-cru.h +9 -0
 
+#define SCLK_SDMMC_DRV_PHASE   113
+#define SCLK_SDIO0_DRV_PHASE   114
+#define SCLK_SDIO1_DRV_PHASE   115
+#define SCLK_EMMC_DRV_PHASE    116
+
+#define SCLK_SDMMC_SAMPLE_PHASE        117
+#define SCLK_SDIO0_SAMPLE_PHASE        118
+#define SCLK_SDIO1_SAMPLE_PHASE        119
+#define SCLK_EMMC_SAMPLE_PHASE 120

It looks like you are adding new clocks to handle the phase requirement. Is that the right thing to do? Don't these clks already exist (e.g. SCLK_SDMMC)?

Regards,
Mike

Quoted 7 lines
include/dt-bindings/clock/rk3288-cru.h +1 -0
+
 #define DCLK_VOP0              190
 #define DCLK_VOP1              191
 
Signature · 1 line
2.1.0.rc2.206.gedb03e5
#3 lore raw

Re: [PATCH v2 1/2] clk: rockchip: add bindings for the mmc clock phases

I actually need to control 2 phases, one of them is used when outputting data, the other when sampling. Sunxi does something similar:
http://lists.infradead.org/pipermail/linux-arm-kernel/2014-July/273273.html

Another reason it wouldn't work is because the upstream clock(eg SCLK_SDMMC) is twice as fast as the real clock(see RK3288_CLKGEN_DIV in drivers/mmc/host/dw_mmc-rockchip.c), since that clock goes to a /2 divider to be able to do the 90 degree clock phases.

Alexandru Stan (amstan)

Quoted 45 lines · Mike Turquette

Quoting Alexandru M Stan (2014-11-14 16:00:03)

Review

Quoted 11 lines

This will be used in a later patch for clock phase tuning.

---
Changes in v2: None

 include/dt-bindings/clock/rk3288-cru.h | 10 ++++++++++
 1 file changed, 10 insertions(+)
(quoted diff) +0 -0

b/include/dt-bindings/clock/rk3288-cru.h

Quoted 6 lines

index 100a08c..465d0f6 100644

include/dt-bindings/clock/rk3288-cru.h +0 -0
@@ -72,6 +72,16 @@
 #define SCLK_HEVC_CABAC                111
 #define SCLK_HEVC_CORE         112

include/dt-bindings/clock/rk3288-cru.h line 83

Quoted 10 lines
include/dt-bindings/clock/rk3288-cru.h +9 -0
 
+#define SCLK_SDMMC_DRV_PHASE   113
+#define SCLK_SDIO0_DRV_PHASE   114
+#define SCLK_SDIO1_DRV_PHASE   115
+#define SCLK_EMMC_DRV_PHASE    116
+
+#define SCLK_SDMMC_SAMPLE_PHASE        117
+#define SCLK_SDIO0_SAMPLE_PHASE        118
+#define SCLK_SDIO1_SAMPLE_PHASE        119
+#define SCLK_EMMC_SAMPLE_PHASE 120

It looks like you are adding new clocks to handle the phase requirement. Is that the right thing to do? Don't these clks already exist (e.g. SCLK_SDMMC)?

Regards,
Mike

Quoted 7 lines
include/dt-bindings/clock/rk3288-cru.h +1 -1
+
 #define DCLK_VOP0              190
 #define DCLK_VOP1              191
 
--

2.1.0.rc2.206.gedb03e5

#4 lore raw

Re: [PATCH v2 1/2] clk: rockchip: add bindings for the mmc clock phases

In reply to Mike Turquette

Sorry for my previous mail, I sent it as HTML and also top posted. Here it goes again:

Quoted 3 lines · Mike Turquette

It looks like you are adding new clocks to handle the phase requirement. Is that the right thing to do? Don't these clks already exist (e.g. SCLK_SDMMC)?

I actually need to control 2 phases, one of them is used when outputting data, the other when sampling. Sunxi does something
similar: http://lists.infradead.org/pipermail/linux-arm-kernel/2014-July/273273.html

Another reason it wouldn't work is because the upstream clock(eg SCLK_SDMMC) is twice as fast as the real clock(see RK3288_CLKGEN_DIV in drivers/mmc/host/dw_mmc-rockchip.c), since that clock goes to a /2 divider to be able to do the 90 degree clock phases.

Alexandru Stan

#5 lore raw

PATCH v2 1/2 clk: rockchip: add bindings for the mmc clock phases

Quoting Alexandru Stan (2014-11-17 11:50:51)

Quoted 7 lines

Sorry for my previous mail, I sent it as HTML and also top posted. Here it goes again:

Quoted 3 lines · Mike Turquette

It looks like you are adding new clocks to handle the phase requirement. Is that the right thing to do? Don't these clks already exist (e.g. SCLK_SDMMC)?

Quoted 8 lines

I actually need to control 2 phases, one of them is used when outputting data, the other when sampling. Sunxi does something
similar: http://lists.infradead.org/pipermail/linux-arm-kernel/2014-July/273273.html

Another reason it wouldn't work is because the upstream clock(eg SCLK_SDMMC) is twice as fast as the real clock(see RK3288_CLKGEN_DIV in drivers/mmc/host/dw_mmc-rockchip.c), since that clock goes to a /2 divider to be able to do the 90 degree clock phases.

Thanks for the explanation.

Regards,
Mike

Quoted 2 lines

Alexandru Stan

#6 lore raw

PATCH v2 2/2 clk: rockchip: Add support for the mmc clock phases using the framework

In reply to Alexandru M Stan

The drive and sample phases are generated by dividing an upstream parent clock by 2, this allows us to adjust the phase by 90 deg.

There's also an option to have up to 255 delay elements (40-80 picoseconds long). This driver uses those elements (under the assumption that they're 60ps long) to generate a rough 45deg (which might be from 33deg to 66deg) setting.

---
Changes in v2:
- fixed my cc/to list
- removed dangling #DEFINE DEBUG

 drivers/clk/rockchip/Makefile        |   1 +
 drivers/clk/rockchip/clk-mmc-phase.c | 149 +++++++++++++++++++++++++++++++++++
 drivers/clk/rockchip/clk-rk3288.c    |  12 +++
 drivers/clk/rockchip/clk.c           |   8 ++
 drivers/clk/rockchip/clk.h           |  23 ++++++
 5 files changed, 193 insertions(+)
 create mode 100644 drivers/clk/rockchip/clk-mmc-phase.c
drivers/clk/rockchip/Makefile +1 -0
index bd8514d..2714097 100644
@@ -6,6 +6,7 @@ obj-y	+= clk-rockchip.o
 obj-y	+= clk.o
 obj-y	+= clk-pll.o
 obj-y	+= clk-cpu.o
+obj-y	+= clk-mmc-phase.o
 obj-$(CONFIG_RESET_CONTROLLER)	+= softrst.o
 
 obj-y	+= clk-rk3188.o
drivers/clk/rockchip/clk-mmc-phase.c new file +149 -0

149 lines not on this page · raw message

drivers/clk/rockchip/clk-rk3288.c +12 -0
index 2327829..273d28a 100644
@@ -483,6 +483,18 @@ static struct rockchip_clk_branch rk3288_clk_branches[] __initdata = {
 			RK3288_CLKSEL_CON(12), 14, 2, MFLAGS, 8, 6, DFLAGS,
 			RK3288_CLKGATE_CON(13), 3, GFLAGS),
 
+	MMC_PHASE(SCLK_SDMMC_DRV_PHASE,    "sdmmc_drv",    "sclk_sdmmc", RK3288_SDMMC_CON0, 1),
+	MMC_PHASE(SCLK_SDMMC_SAMPLE_PHASE, "sdmmc_sample", "sclk_sdmmc", RK3288_SDMMC_CON1, 0),
+
+	MMC_PHASE(SCLK_SDIO0_DRV_PHASE,    "sdio0_drv",    "sclk_sdio0", RK3288_SDIO0_CON0, 1),
+	MMC_PHASE(SCLK_SDIO0_SAMPLE_PHASE, "sdio0_sample", "sclk_sdio0", RK3288_SDIO0_CON1, 0),
+
+	MMC_PHASE(SCLK_SDIO1_DRV_PHASE,    "sdio1_drv",    "sclk_sdio1", RK3288_SDIO1_CON0, 1),
+	MMC_PHASE(SCLK_SDIO1_SAMPLE_PHASE, "sdio1_sample", "sclk_sdio1", RK3288_SDIO1_CON1, 0),
+
+	MMC_PHASE(SCLK_EMMC_DRV_PHASE,     "emmc_drv",     "sclk_emmc",  RK3288_EMMC_CON0,  1),
+	MMC_PHASE(SCLK_EMMC_SAMPLE_PHASE,  "emmc_sample",  "sclk_emmc",  RK3288_EMMC_CON1,  0),
+
 	COMPOSITE(0, "sclk_tspout", mux_tspout_p, 0,
 			RK3288_CLKSEL_CON(35), 14, 2, MFLAGS, 8, 5, DFLAGS,
 			RK3288_CLKGATE_CON(4), 11, GFLAGS),
drivers/clk/rockchip/clk.c +8 -0
index 1e68bff..3149905 100644
@@ -279,6 +279,14 @@ void __init rockchip_clk_register_branches(
 				list->gate_offset, list->gate_shift,
 				list->gate_flags, flags, &clk_lock);
 			break;
+		case branch_mmc_phase:
+			clk = rockchip_clk_register_mmc_phase(
+				list->name,
+				list->parent_names, list->num_parents,
+				reg_base + list->muxdiv_offset,
+				list->div_shift
+			);
+			break;
 		}
 
 		/* none of the cases above matched */
drivers/clk/rockchip/clk.h +23 -0
index ca009ab..9ff5e2e 100644
@@ -48,6 +48,14 @@
 #define RK3288_GLB_SRST_SND		0x1b4
 #define RK3288_SOFTRST_CON(x)		(x * 0x4 + 0x1b8)
 #define RK3288_MISC_CON			0x1e8
+#define RK3288_SDMMC_CON0		0x200
+#define RK3288_SDMMC_CON1		0x204
+#define RK3288_SDIO0_CON0		0x208
+#define RK3288_SDIO0_CON1		0x20c
+#define RK3288_SDIO1_CON0		0x210
+#define RK3288_SDIO1_CON1		0x214
+#define RK3288_EMMC_CON0		0x218
+#define RK3288_EMMC_CON1		0x21c
 
 enum rockchip_pll_type {
 	pll_rk3066,
@@ -152,6 +160,10 @@ struct clk *rockchip_clk_register_cpuclk(const char *name,
 			const struct rockchip_cpuclk_rate_table *rates,
 			int nrates, void __iomem *reg_base, spinlock_t *lock);
 
+struct clk *rockchip_clk_register_mmc_phase(const char *name,
+				const char **parent_names, u8 num_parents,
+				void __iomem *reg, int shift);
+
 #define PNAME(x) static const char *x[] __initconst
 
 enum rockchip_clk_branch_type {
@@ -160,6 +172,7 @@ enum rockchip_clk_branch_type {
 	branch_divider,
 	branch_fraction_divider,
 	branch_gate,
+	branch_mmc_phase,
 };
 
 struct rockchip_clk_branch {
@@ -352,6 +365,16 @@ struct rockchip_clk_branch {
 		.gate_flags	= gf,				\
 	}
 
+#define MMC_PHASE(_id, cname, pname, offset, shift)		\
+	{							\
+		.id		= _id,				\
+		.branch_type	= branch_mmc_phase,		\
+		.name		= cname,			\
+		.parent_names	= (const char *[]){ pname },	\
+		.num_parents	= 1,				\
+		.muxdiv_offset	= offset,			\
+		.div_shift	= shift,			\
+	}
 
 void rockchip_clk_init(struct device_node *np, void __iomem *base,
 		       unsigned long nr_clks);
Signature · 1 line
2.1.0.rc2.206.gedb03e5