summaryrefslogtreecommitdiff
path: root/src/soc/rockchip
diff options
context:
space:
mode:
Diffstat (limited to 'src/soc/rockchip')
-rw-r--r--src/soc/rockchip/common/i2c.c11
-rw-r--r--src/soc/rockchip/rk3399/clock.c43
-rw-r--r--src/soc/rockchip/rk3399/display.c2
-rw-r--r--src/soc/rockchip/rk3399/include/soc/clock.h6
4 files changed, 32 insertions, 30 deletions
diff --git a/src/soc/rockchip/common/i2c.c b/src/soc/rockchip/common/i2c.c
index 1bd88bbe9d..a00d538ba2 100644
--- a/src/soc/rockchip/common/i2c.c
+++ b/src/soc/rockchip/common/i2c.c
@@ -273,16 +273,19 @@ void i2c_init(unsigned int bus, unsigned int hz)
unsigned int divl;
unsigned int divh;
unsigned int i2c_src_clk;
+ unsigned int i2c_clk;
struct rk_i2c_regs *regs = (struct rk_i2c_regs *)(i2c_bus[bus]);
i2c_src_clk = rkclk_i2c_clock_for_bus(bus);
- /*SCL Divisor = 8*(CLKDIVL + 1 + CLKDIVH + 1)
- SCL = PCLK/ SCLK Divisor
- */
+ /* SCL Divisor = 8*(CLKDIVL + 1 + CLKDIVH + 1)
+ SCL = PCLK / SCLK Divisor */
clk_div = div_round_up(i2c_src_clk, hz * 8);
divh = clk_div * 3 / 7 - 1;
divl = clk_div - divh - 2;
- assert((divh < 65536) && (divl < 65536));
+ i2c_clk = i2c_src_clk / (8 * (divl + 1 + divh + 1));
+ printk(BIOS_DEBUG, "I2C bus %u: %uHz (divh = %u, divl = %u)\n",
+ bus, i2c_clk, divh, divl);
+ assert((divh < 65536) && (divl < 65536) && hz - i2c_clk < 10*KHz);
write32(&regs->i2c_clkdiv, (divh << 16) | (divl << 0));
}
diff --git a/src/soc/rockchip/rk3399/clock.c b/src/soc/rockchip/rk3399/clock.c
index 2596853618..ced78b3ded 100644
--- a/src/soc/rockchip/rk3399/clock.c
+++ b/src/soc/rockchip/rk3399/clock.c
@@ -40,12 +40,12 @@ struct pll_div {
.postdiv1 = _postdiv1, .postdiv2 = _postdiv2, .freq = hz};\
_Static_assert(((u64)hz * _refdiv * _postdiv1 * _postdiv2 / OSC_HZ) *\
OSC_HZ / (_refdiv * _postdiv1 * _postdiv2) == hz,\
- #hz "Hz cannot be hit with PLL "\
+ STRINGIFY(hz) " Hz cannot be hit with PLL "\
"divisors on line " STRINGIFY(__LINE__))
-static const struct pll_div gpll_init_cfg = PLL_DIVISORS(GPLL_HZ, 2, 2, 1);
-static const struct pll_div cpll_init_cfg = PLL_DIVISORS(CPLL_HZ, 1, 2, 2);
-static const struct pll_div ppll_init_cfg = PLL_DIVISORS(PPLL_HZ, 2, 2, 1);
+static const struct pll_div gpll_init_cfg = PLL_DIVISORS(GPLL_HZ, 1, 4, 1);
+static const struct pll_div cpll_init_cfg = PLL_DIVISORS(CPLL_HZ, 1, 3, 1);
+static const struct pll_div ppll_init_cfg = PLL_DIVISORS(PPLL_HZ, 3, 2, 1);
static const struct pll_div apll_1512_cfg = PLL_DIVISORS(1512*MHz, 1, 1, 1);
static const struct pll_div apll_600_cfg = PLL_DIVISORS(600*MHz, 1, 3, 1);
@@ -402,7 +402,8 @@ void rkclk_init(void)
/* configure pmu pclk */
pclk_div = PPLL_HZ / PMU_PCLK_HZ - 1;
- assert((pclk_div + 1) * PMU_PCLK_HZ == PPLL_HZ && pclk_div <= 0x1f);
+ assert((unsigned int)(PPLL_HZ - (pclk_div + 1) * PMU_PCLK_HZ) <= pclk_div
+ && pclk_div <= 0x1f);
write32(&pmucru_ptr->pmucru_clksel[0],
RK_CLRSETBITS(PMU_PCLK_DIV_CON_MASK << PMU_PCLK_DIV_CON_SHIFT,
pclk_div << PMU_PCLK_DIV_CON_SHIFT));
@@ -631,15 +632,20 @@ void rkclk_configure_spi(unsigned int bus, unsigned int hz)
RK_CLRSETBITS(I2C_DIV_CON_MASK << I2C ##bus## _DIV_CON_SHIFT, \
(clk_div - 1) << I2C ##bus## _DIV_CON_SHIFT)
-static void rkclk_configure_i2c(unsigned int bus, unsigned int hz)
+uint32_t rkclk_i2c_clock_for_bus(unsigned int bus)
{
- int src_clk_div;
- int pll;
-
- /* i2c0,4,8 src clock from ppll, i2c1,2,3,5,6,7 src clock from gpll*/
- pll = (bus == 0 || bus == 4 || bus == 8) ? PPLL_HZ : GPLL_HZ;
- src_clk_div = pll / hz;
- assert((src_clk_div - 1 <= 127) && (src_clk_div * hz == pll));
+ int src_clk_div, pll, freq;
+
+ /* i2c0,4,8 src clock from ppll, i2c1,2,3,5,6,7 src clock from gpll */
+ if (bus == 0 || bus == 4 || bus == 8) {
+ pll = PPLL_HZ;
+ freq = 338*MHz;
+ } else {
+ pll = GPLL_HZ;
+ freq = 198*MHz;
+ }
+ src_clk_div = pll / freq;
+ assert((src_clk_div - 1 <= 127) && (src_clk_div * freq == pll));
switch (bus) {
case 0:
@@ -679,15 +685,8 @@ static void rkclk_configure_i2c(unsigned int bus, unsigned int hz)
PMU_I2C_CLK_REG_VALUE(8, src_clk_div));
break;
default:
- printk(BIOS_ERR, "do not support this i2c bus\n");
+ die("unknown i2c bus\n");
}
-}
-
-uint32_t rkclk_i2c_clock_for_bus(unsigned bus)
-{
- uint32_t freq = 198 * 1000 * 1000;
-
- rkclk_configure_i2c(bus, freq);
return freq;
}
@@ -724,7 +723,7 @@ void rkclk_configure_i2s(unsigned int hz)
v = clk_gcd(CPLL_HZ, hz);
n = (CPLL_HZ / v) & (0xffff);
d = (hz / v) & (0xffff);
- assert(hz == CPLL_HZ / n * d);
+ assert(hz == (u64)CPLL_HZ * d / n);
write32(&cru_ptr->clksel_con[96], d << 16 | n);
/**
diff --git a/src/soc/rockchip/rk3399/display.c b/src/soc/rockchip/rk3399/display.c
index 5b884789bb..671e518fc3 100644
--- a/src/soc/rockchip/rk3399/display.c
+++ b/src/soc/rockchip/rk3399/display.c
@@ -52,7 +52,7 @@ void rk_display_init(device_t dev)
/* try EDP first, then HDMI */
case VOP_MODE_EDP:
printk(BIOS_DEBUG, "Attempting to set up EDP display.\n");
- rkclk_configure_vop_aclk(vop_id, 192 * MHz);
+ rkclk_configure_vop_aclk(vop_id, 200 * MHz);
/* select edp signal from vop0 */
write32(&rk3399_grf->soc_con20, RK_CLRBITS(1 << 5));
diff --git a/src/soc/rockchip/rk3399/include/soc/clock.h b/src/soc/rockchip/rk3399/include/soc/clock.h
index 59260510bc..82bf215389 100644
--- a/src/soc/rockchip/rk3399/include/soc/clock.h
+++ b/src/soc/rockchip/rk3399/include/soc/clock.h
@@ -74,10 +74,10 @@ static struct rk3399_cru_reg * const cru_ptr = (void *)CRU_BASE;
#define OSC_HZ (24*MHz)
#define GPLL_HZ (594*MHz)
-#define CPLL_HZ (384*MHz)
-#define PPLL_HZ (594*MHz)
+#define CPLL_HZ (800*MHz)
+#define PPLL_HZ (676*MHz)
-#define PMU_PCLK_HZ (99*MHz)
+#define PMU_PCLK_HZ 96571428
#define ACLKM_CORE_HZ (300*MHz)
#define ATCLK_CORE_HZ (300*MHz)