mirror of
https://github.com/smaeul/u-boot.git
synced 2025-11-02 13:08:16 +00:00
clk/qcom: sdm845: add register map for simple gate clocks
Many gate clocks can be enabled with a single register write, add support for defining these simple gate clocks and add the ones found on SDM845. While we're here, inline clk_init_uart() into msm_set_rate(). Reviewed-by: Sumit Garg <sumit.garg@linaro.org> Signed-off-by: Caleb Connolly <caleb.connolly@linaro.org>
This commit is contained in:
parent
3ead661633
commit
0e7fec02ce
@ -5,6 +5,8 @@
|
||||
#ifndef _CLOCK_QCOM_H
|
||||
#define _CLOCK_QCOM_H
|
||||
|
||||
#include <asm/io.h>
|
||||
|
||||
#define CFG_CLK_SRC_CXO (0 << 8)
|
||||
#define CFG_CLK_SRC_GPLL0 (1 << 8)
|
||||
#define CFG_CLK_SRC_GPLL0_EVEN (6 << 8)
|
||||
@ -30,6 +32,18 @@ struct bcr_regs {
|
||||
uintptr_t D;
|
||||
};
|
||||
|
||||
struct gate_clk {
|
||||
uintptr_t reg;
|
||||
u32 en_val;
|
||||
const char *name;
|
||||
};
|
||||
|
||||
#ifdef DEBUG
|
||||
#define GATE_CLK(clk, reg, val) [clk] = { reg, val, #clk }
|
||||
#else
|
||||
#define GATE_CLK(clk, reg, val) [clk] = { reg, val, NULL }
|
||||
#endif
|
||||
|
||||
struct qcom_reset_map {
|
||||
unsigned int reg;
|
||||
u8 bit;
|
||||
@ -38,6 +52,8 @@ struct qcom_reset_map {
|
||||
struct msm_clk_data {
|
||||
const struct qcom_reset_map *resets;
|
||||
unsigned long num_resets;
|
||||
const struct gate_clk *clks;
|
||||
unsigned long num_clks;
|
||||
};
|
||||
|
||||
struct msm_clk_priv {
|
||||
@ -55,4 +71,14 @@ void clk_rcg_set_rate_mnd(phys_addr_t base, const struct bcr_regs *regs,
|
||||
void clk_rcg_set_rate(phys_addr_t base, const struct bcr_regs *regs, int div,
|
||||
int source);
|
||||
|
||||
static inline void qcom_gate_clk_en(const struct msm_clk_priv *priv, unsigned long id)
|
||||
{
|
||||
u32 val;
|
||||
if (id >= priv->data->num_clks || priv->data->clks[id].reg == 0)
|
||||
return;
|
||||
|
||||
val = readl(priv->base + priv->data->clks[id].reg);
|
||||
writel(val | priv->data->clks[id].en_val, priv->base + priv->data->clks[id].reg);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@ -11,6 +11,7 @@
|
||||
#include <common.h>
|
||||
#include <clk-uclass.h>
|
||||
#include <dm.h>
|
||||
#include <linux/delay.h>
|
||||
#include <errno.h>
|
||||
#include <asm/io.h>
|
||||
#include <linux/bitops.h>
|
||||
@ -71,30 +72,90 @@ const struct freq_tbl *qcom_find_freq(const struct freq_tbl *f, uint rate)
|
||||
return f - 1;
|
||||
}
|
||||
|
||||
static int clk_init_uart(struct msm_clk_priv *priv, uint rate)
|
||||
{
|
||||
const struct freq_tbl *freq = qcom_find_freq(ftbl_gcc_qupv3_wrap0_s0_clk_src, rate);
|
||||
|
||||
clk_rcg_set_rate_mnd(priv->base, &uart2_regs,
|
||||
freq->pre_div, freq->m, freq->n, freq->src);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
ulong msm_set_rate(struct clk *clk, ulong rate)
|
||||
{
|
||||
struct msm_clk_priv *priv = dev_get_priv(clk->dev);
|
||||
const struct freq_tbl *freq;
|
||||
|
||||
switch (clk->id) {
|
||||
case GCC_QUPV3_WRAP1_S1_CLK: /*UART2*/
|
||||
return clk_init_uart(priv, rate);
|
||||
case GCC_QUPV3_WRAP1_S1_CLK: /* UART9 */
|
||||
freq = qcom_find_freq(ftbl_gcc_qupv3_wrap0_s0_clk_src, rate);
|
||||
clk_rcg_set_rate_mnd(priv->base, &uart2_regs,
|
||||
freq->pre_div, freq->m, freq->n, freq->src);
|
||||
|
||||
return freq->freq;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
static const struct gate_clk sdm845_clks[] = {
|
||||
GATE_CLK(GCC_QUPV3_WRAP0_S0_CLK, 0x5200c, 0x00000400),
|
||||
GATE_CLK(GCC_QUPV3_WRAP0_S1_CLK, 0x5200c, 0x00000800),
|
||||
GATE_CLK(GCC_QUPV3_WRAP0_S2_CLK, 0x5200c, 0x00001000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP0_S3_CLK, 0x5200c, 0x00002000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP0_S4_CLK, 0x5200c, 0x00004000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP0_S5_CLK, 0x5200c, 0x00008000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP0_S6_CLK, 0x5200c, 0x00010000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP0_S7_CLK, 0x5200c, 0x00020000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP1_S0_CLK, 0x5200c, 0x00400000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP1_S1_CLK, 0x5200c, 0x00800000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP1_S3_CLK, 0x5200c, 0x02000000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP1_S4_CLK, 0x5200c, 0x04000000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP1_S5_CLK, 0x5200c, 0x08000000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP1_S6_CLK, 0x5200c, 0x10000000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP1_S7_CLK, 0x5200c, 0x20000000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP_0_M_AHB_CLK, 0x5200c, 0x00000040),
|
||||
GATE_CLK(GCC_QUPV3_WRAP_0_S_AHB_CLK, 0x5200c, 0x00000080),
|
||||
GATE_CLK(GCC_QUPV3_WRAP_1_M_AHB_CLK, 0x5200c, 0x00100000),
|
||||
GATE_CLK(GCC_QUPV3_WRAP_1_S_AHB_CLK, 0x5200c, 0x00200000),
|
||||
GATE_CLK(GCC_SDCC2_AHB_CLK, 0x14008, 0x00000001),
|
||||
GATE_CLK(GCC_SDCC2_APPS_CLK, 0x14004, 0x00000001),
|
||||
GATE_CLK(GCC_SDCC4_AHB_CLK, 0x16008, 0x00000001),
|
||||
GATE_CLK(GCC_SDCC4_APPS_CLK, 0x16004, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_AHB_CLK, 0x75010, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_AXI_CLK, 0x7500c, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_CLKREF_CLK, 0x8c004, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_ICE_CORE_CLK, 0x75058, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_PHY_AUX_CLK, 0x7508c, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_RX_SYMBOL_0_CLK, 0x75018, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_RX_SYMBOL_1_CLK, 0x750a8, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_TX_SYMBOL_0_CLK, 0x75014, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_CARD_UNIPRO_CORE_CLK, 0x75054, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_MEM_CLKREF_CLK, 0x8c000, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_PHY_AHB_CLK, 0x77010, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_PHY_AXI_CLK, 0x7700c, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_PHY_ICE_CORE_CLK, 0x77058, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_PHY_PHY_AUX_CLK, 0x7708c, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_PHY_RX_SYMBOL_0_CLK, 0x77018, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_PHY_RX_SYMBOL_1_CLK, 0x770a8, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_PHY_TX_SYMBOL_0_CLK, 0x77014, 0x00000001),
|
||||
GATE_CLK(GCC_UFS_PHY_UNIPRO_CORE_CLK, 0x77054, 0x00000001),
|
||||
GATE_CLK(GCC_USB30_PRIM_MASTER_CLK, 0x0f00c, 0x00000001),
|
||||
GATE_CLK(GCC_USB30_PRIM_MOCK_UTMI_CLK, 0x0f014, 0x00000001),
|
||||
GATE_CLK(GCC_USB30_PRIM_SLEEP_CLK, 0x0f010, 0x00000001),
|
||||
GATE_CLK(GCC_USB30_SEC_MASTER_CLK, 0x1000c, 0x00000001),
|
||||
GATE_CLK(GCC_USB30_SEC_MOCK_UTMI_CLK, 0x10014, 0x00000001),
|
||||
GATE_CLK(GCC_USB30_SEC_SLEEP_CLK, 0x10010, 0x00000001),
|
||||
GATE_CLK(GCC_USB3_PRIM_CLKREF_CLK, 0x8c008, 0x00000001),
|
||||
GATE_CLK(GCC_USB3_PRIM_PHY_AUX_CLK, 0x0f04c, 0x00000001),
|
||||
GATE_CLK(GCC_USB3_PRIM_PHY_COM_AUX_CLK, 0x0f050, 0x00000001),
|
||||
GATE_CLK(GCC_USB3_PRIM_PHY_PIPE_CLK, 0x0f054, 0x00000001),
|
||||
GATE_CLK(GCC_USB3_SEC_CLKREF_CLK, 0x8c028, 0x00000001),
|
||||
GATE_CLK(GCC_USB3_SEC_PHY_AUX_CLK, 0x1004c, 0x00000001),
|
||||
GATE_CLK(GCC_USB3_SEC_PHY_PIPE_CLK, 0x10054, 0x00000001),
|
||||
GATE_CLK(GCC_USB3_SEC_PHY_COM_AUX_CLK, 0x10050, 0x00000001),
|
||||
GATE_CLK(GCC_USB_PHY_CFG_AHB2PHY_CLK, 0x6a004, 0x00000001),
|
||||
};
|
||||
|
||||
int msm_enable(struct clk *clk)
|
||||
{
|
||||
struct msm_clk_priv *priv = dev_get_priv(clk->dev);
|
||||
|
||||
debug("%s: clk %s\n", __func__, sdm845_clks[clk->id].name);
|
||||
|
||||
qcom_gate_clk_en(priv, clk->id);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -121,6 +182,8 @@ static const struct qcom_reset_map sdm845_gcc_resets[] = {
|
||||
static const struct msm_clk_data qcs404_gcc_data = {
|
||||
.resets = sdm845_gcc_resets,
|
||||
.num_resets = ARRAY_SIZE(sdm845_gcc_resets),
|
||||
.clks = sdm845_clks,
|
||||
.num_clks = ARRAY_SIZE(sdm845_clks),
|
||||
};
|
||||
|
||||
static const struct udevice_id gcc_sdm845_of_match[] = {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user