diff options
author | Sascha Hauer <s.hauer@pengutronix.de> | 2010-12-06 03:13:21 -0500 |
---|---|---|
committer | Sascha Hauer <s.hauer@pengutronix.de> | 2011-01-03 10:30:56 -0500 |
commit | b848169b37f71c494ea59b260ba665290c23c350 (patch) | |
tree | f12c9815603bb94af5e5b08df3ea8244319f55b0 /arch/arm/mach-mx5/clock-mx51-mx53.c | |
parent | c67a3e09a5316bb34a14e2751cee719339934235 (diff) |
ARM i.MX51: Add ipu clock support
Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
Diffstat (limited to 'arch/arm/mach-mx5/clock-mx51-mx53.c')
-rw-r--r-- | arch/arm/mach-mx5/clock-mx51-mx53.c | 140 |
1 files changed, 140 insertions, 0 deletions
diff --git a/arch/arm/mach-mx5/clock-mx51-mx53.c b/arch/arm/mach-mx5/clock-mx51-mx53.c index 2f9eae21309..ba9432c8f84 100644 --- a/arch/arm/mach-mx5/clock-mx51-mx53.c +++ b/arch/arm/mach-mx5/clock-mx51-mx53.c | |||
@@ -39,6 +39,9 @@ static struct clk periph_apm_clk; | |||
39 | static struct clk ahb_clk; | 39 | static struct clk ahb_clk; |
40 | static struct clk ipg_clk; | 40 | static struct clk ipg_clk; |
41 | static struct clk usboh3_clk; | 41 | static struct clk usboh3_clk; |
42 | static struct clk emi_fast_clk; | ||
43 | static struct clk ipu_clk; | ||
44 | static struct clk mipi_hsc1_clk; | ||
42 | 45 | ||
43 | #define MAX_DPLL_WAIT_TRIES 1000 /* 1000 * udelay(1) = 1ms */ | 46 | #define MAX_DPLL_WAIT_TRIES 1000 /* 1000 * udelay(1) = 1ms */ |
44 | 47 | ||
@@ -688,6 +691,19 @@ static unsigned long clk_emi_slow_get_rate(struct clk *clk) | |||
688 | return clk_get_rate(clk->parent) / div; | 691 | return clk_get_rate(clk->parent) / div; |
689 | } | 692 | } |
690 | 693 | ||
694 | static unsigned long _clk_ddr_hf_get_rate(struct clk *clk) | ||
695 | { | ||
696 | unsigned long rate; | ||
697 | u32 reg, div; | ||
698 | |||
699 | reg = __raw_readl(MXC_CCM_CBCDR); | ||
700 | div = ((reg & MXC_CCM_CBCDR_DDR_PODF_MASK) >> | ||
701 | MXC_CCM_CBCDR_DDR_PODF_OFFSET) + 1; | ||
702 | rate = clk_get_rate(clk->parent) / div; | ||
703 | |||
704 | return rate; | ||
705 | } | ||
706 | |||
691 | /* External high frequency clock */ | 707 | /* External high frequency clock */ |
692 | static struct clk ckih_clk = { | 708 | static struct clk ckih_clk = { |
693 | .get_rate = get_high_reference_clock_rate, | 709 | .get_rate = get_high_reference_clock_rate, |
@@ -846,6 +862,109 @@ static struct clk emi_slow_clk = { | |||
846 | .get_rate = clk_emi_slow_get_rate, | 862 | .get_rate = clk_emi_slow_get_rate, |
847 | }; | 863 | }; |
848 | 864 | ||
865 | static int clk_ipu_enable(struct clk *clk) | ||
866 | { | ||
867 | u32 reg; | ||
868 | |||
869 | _clk_ccgr_enable(clk); | ||
870 | |||
871 | /* Enable handshake with IPU when certain clock rates are changed */ | ||
872 | reg = __raw_readl(MXC_CCM_CCDR); | ||
873 | reg &= ~MXC_CCM_CCDR_IPU_HS_MASK; | ||
874 | __raw_writel(reg, MXC_CCM_CCDR); | ||
875 | |||
876 | /* Enable handshake with IPU when LPM is entered */ | ||
877 | reg = __raw_readl(MXC_CCM_CLPCR); | ||
878 | reg &= ~MXC_CCM_CLPCR_BYPASS_IPU_LPM_HS; | ||
879 | __raw_writel(reg, MXC_CCM_CLPCR); | ||
880 | |||
881 | return 0; | ||
882 | } | ||
883 | |||
884 | static void clk_ipu_disable(struct clk *clk) | ||
885 | { | ||
886 | u32 reg; | ||
887 | |||
888 | _clk_ccgr_disable(clk); | ||
889 | |||
890 | /* Disable handshake with IPU whe dividers are changed */ | ||
891 | reg = __raw_readl(MXC_CCM_CCDR); | ||
892 | reg |= MXC_CCM_CCDR_IPU_HS_MASK; | ||
893 | __raw_writel(reg, MXC_CCM_CCDR); | ||
894 | |||
895 | /* Disable handshake with IPU when LPM is entered */ | ||
896 | reg = __raw_readl(MXC_CCM_CLPCR); | ||
897 | reg |= MXC_CCM_CLPCR_BYPASS_IPU_LPM_HS; | ||
898 | __raw_writel(reg, MXC_CCM_CLPCR); | ||
899 | } | ||
900 | |||
901 | static struct clk ahbmux1_clk = { | ||
902 | .parent = &ahb_clk, | ||
903 | .secondary = &ahb_max_clk, | ||
904 | .enable_reg = MXC_CCM_CCGR0, | ||
905 | .enable_shift = MXC_CCM_CCGRx_CG8_OFFSET, | ||
906 | .enable = _clk_ccgr_enable, | ||
907 | .disable = _clk_ccgr_disable_inwait, | ||
908 | }; | ||
909 | |||
910 | static struct clk ipu_sec_clk = { | ||
911 | .parent = &emi_fast_clk, | ||
912 | .secondary = &ahbmux1_clk, | ||
913 | }; | ||
914 | |||
915 | static struct clk ddr_hf_clk = { | ||
916 | .parent = &pll1_sw_clk, | ||
917 | .get_rate = _clk_ddr_hf_get_rate, | ||
918 | }; | ||
919 | |||
920 | static struct clk ddr_clk = { | ||
921 | .parent = &ddr_hf_clk, | ||
922 | }; | ||
923 | |||
924 | /* clock definitions for MIPI HSC unit which has been removed | ||
925 | * from documentation, but not from hardware | ||
926 | */ | ||
927 | static int _clk_hsc_enable(struct clk *clk) | ||
928 | { | ||
929 | u32 reg; | ||
930 | |||
931 | _clk_ccgr_enable(clk); | ||
932 | /* Handshake with IPU when certain clock rates are changed. */ | ||
933 | reg = __raw_readl(MXC_CCM_CCDR); | ||
934 | reg &= ~MXC_CCM_CCDR_HSC_HS_MASK; | ||
935 | __raw_writel(reg, MXC_CCM_CCDR); | ||
936 | |||
937 | reg = __raw_readl(MXC_CCM_CLPCR); | ||
938 | reg &= ~MXC_CCM_CLPCR_BYPASS_HSC_LPM_HS; | ||
939 | __raw_writel(reg, MXC_CCM_CLPCR); | ||
940 | |||
941 | return 0; | ||
942 | } | ||
943 | |||
944 | static void _clk_hsc_disable(struct clk *clk) | ||
945 | { | ||
946 | u32 reg; | ||
947 | |||
948 | _clk_ccgr_disable(clk); | ||
949 | /* No handshake with HSC as its not enabled. */ | ||
950 | reg = __raw_readl(MXC_CCM_CCDR); | ||
951 | reg |= MXC_CCM_CCDR_HSC_HS_MASK; | ||
952 | __raw_writel(reg, MXC_CCM_CCDR); | ||
953 | |||
954 | reg = __raw_readl(MXC_CCM_CLPCR); | ||
955 | reg |= MXC_CCM_CLPCR_BYPASS_HSC_LPM_HS; | ||
956 | __raw_writel(reg, MXC_CCM_CLPCR); | ||
957 | } | ||
958 | |||
959 | static struct clk mipi_hsp_clk = { | ||
960 | .parent = &ipu_clk, | ||
961 | .enable_reg = MXC_CCM_CCGR4, | ||
962 | .enable_shift = MXC_CCM_CCGRx_CG6_OFFSET, | ||
963 | .enable = _clk_hsc_enable, | ||
964 | .disable = _clk_hsc_disable, | ||
965 | .secondary = &mipi_hsc1_clk, | ||
966 | }; | ||
967 | |||
849 | #define DEFINE_CLOCK_CCGR(name, i, er, es, pfx, p, s) \ | 968 | #define DEFINE_CLOCK_CCGR(name, i, er, es, pfx, p, s) \ |
850 | static struct clk name = { \ | 969 | static struct clk name = { \ |
851 | .id = i, \ | 970 | .id = i, \ |
@@ -1112,6 +1231,23 @@ DEFINE_CLOCK_FULL(esdhc2_ipg_clk, 1, MXC_CCM_CCGR3, MXC_CCM_CCGRx_CG2_OFFSET, | |||
1112 | DEFINE_CLOCK_MAX(esdhc2_clk, 1, MXC_CCM_CCGR3, MXC_CCM_CCGRx_CG3_OFFSET, | 1231 | DEFINE_CLOCK_MAX(esdhc2_clk, 1, MXC_CCM_CCGR3, MXC_CCM_CCGRx_CG3_OFFSET, |
1113 | clk_esdhc2, &pll2_sw_clk, &esdhc2_ipg_clk); | 1232 | clk_esdhc2, &pll2_sw_clk, &esdhc2_ipg_clk); |
1114 | 1233 | ||
1234 | DEFINE_CLOCK(mipi_esc_clk, 0, MXC_CCM_CCGR4, MXC_CCM_CCGRx_CG5_OFFSET, NULL, NULL, NULL, &pll2_sw_clk); | ||
1235 | DEFINE_CLOCK(mipi_hsc2_clk, 0, MXC_CCM_CCGR4, MXC_CCM_CCGRx_CG4_OFFSET, NULL, NULL, &mipi_esc_clk, &pll2_sw_clk); | ||
1236 | DEFINE_CLOCK(mipi_hsc1_clk, 0, MXC_CCM_CCGR4, MXC_CCM_CCGRx_CG3_OFFSET, NULL, NULL, &mipi_hsc2_clk, &pll2_sw_clk); | ||
1237 | |||
1238 | /* IPU */ | ||
1239 | DEFINE_CLOCK_FULL(ipu_clk, 0, MXC_CCM_CCGR5, MXC_CCM_CCGRx_CG5_OFFSET, | ||
1240 | NULL, NULL, clk_ipu_enable, clk_ipu_disable, &ahb_clk, &ipu_sec_clk); | ||
1241 | |||
1242 | DEFINE_CLOCK_FULL(emi_fast_clk, 0, MXC_CCM_CCGR5, MXC_CCM_CCGRx_CG7_OFFSET, | ||
1243 | NULL, NULL, _clk_ccgr_enable, _clk_ccgr_disable_inwait, | ||
1244 | &ddr_clk, NULL); | ||
1245 | |||
1246 | DEFINE_CLOCK(ipu_di0_clk, 0, MXC_CCM_CCGR6, MXC_CCM_CCGRx_CG5_OFFSET, | ||
1247 | NULL, NULL, &pll3_sw_clk, NULL); | ||
1248 | DEFINE_CLOCK(ipu_di1_clk, 0, MXC_CCM_CCGR6, MXC_CCM_CCGRx_CG6_OFFSET, | ||
1249 | NULL, NULL, &pll3_sw_clk, NULL); | ||
1250 | |||
1115 | #define _REGISTER_CLOCK(d, n, c) \ | 1251 | #define _REGISTER_CLOCK(d, n, c) \ |
1116 | { \ | 1252 | { \ |
1117 | .dev_id = d, \ | 1253 | .dev_id = d, \ |
@@ -1155,6 +1291,10 @@ static struct clk_lookup mx51_lookups[] = { | |||
1155 | _REGISTER_CLOCK(NULL, "iim_clk", iim_clk) | 1291 | _REGISTER_CLOCK(NULL, "iim_clk", iim_clk) |
1156 | _REGISTER_CLOCK("imx2-wdt.0", NULL, dummy_clk) | 1292 | _REGISTER_CLOCK("imx2-wdt.0", NULL, dummy_clk) |
1157 | _REGISTER_CLOCK("imx2-wdt.1", NULL, dummy_clk) | 1293 | _REGISTER_CLOCK("imx2-wdt.1", NULL, dummy_clk) |
1294 | _REGISTER_CLOCK(NULL, "mipi_hsp", mipi_hsp_clk) | ||
1295 | _REGISTER_CLOCK("imx-ipuv3", NULL, ipu_clk) | ||
1296 | _REGISTER_CLOCK("imx-ipuv3", "di0", ipu_di0_clk) | ||
1297 | _REGISTER_CLOCK("imx-ipuv3", "di1", ipu_di1_clk) | ||
1158 | }; | 1298 | }; |
1159 | 1299 | ||
1160 | static struct clk_lookup mx53_lookups[] = { | 1300 | static struct clk_lookup mx53_lookups[] = { |