1 // SPDX-License-Identifier: GPL-2.0
3 * Copyright (c) 2023 MediaTek Inc.
4 * Author: Sam Shih <sam.shih@mediatek.com>
5 * Author: Xiufeng Li <Xiufeng.Li@mediatek.com>
8 #include <linux/clk-provider.h>
10 #include <linux/of_address.h>
11 #include <linux/of_device.h>
12 #include <linux/platform_device.h>
16 #include <dt-bindings/clock/mediatek,mt7988-clk.h>
18 static DEFINE_SPINLOCK(mt7988_clk_lock
);
20 static const char *const infra_mux_uart0_parents
[] __initconst
= {
21 "csw_infra_f26m_sel", "uart_sel"
24 static const char *const infra_mux_uart1_parents
[] __initconst
= {
25 "csw_infra_f26m_sel", "uart_sel"
28 static const char *const infra_mux_uart2_parents
[] __initconst
= {
29 "csw_infra_f26m_sel", "uart_sel"
32 static const char *const infra_mux_spi0_parents
[] __initconst
= { "i2c_sel",
35 static const char *const infra_mux_spi1_parents
[] __initconst
= {
36 "i2c_sel", "spim_mst_sel"
39 static const char *const infra_pwm_bck_parents
[] __initconst
= {
40 "top_rtc_32p7k", "csw_infra_f26m_sel", "sysaxi_sel", "pwm_sel"
43 static const char *const infra_pcie_gfmux_tl_ck_o_p0_parents
[] __initconst
= {
44 "top_rtc_32p7k", "csw_infra_f26m_sel", "csw_infra_f26m_sel",
48 static const char *const infra_pcie_gfmux_tl_ck_o_p1_parents
[] __initconst
= {
49 "top_rtc_32p7k", "csw_infra_f26m_sel", "csw_infra_f26m_sel",
53 static const char *const infra_pcie_gfmux_tl_ck_o_p2_parents
[] __initconst
= {
54 "top_rtc_32p7k", "csw_infra_f26m_sel", "csw_infra_f26m_sel",
58 static const char *const infra_pcie_gfmux_tl_ck_o_p3_parents
[] __initconst
= {
59 "top_rtc_32p7k", "csw_infra_f26m_sel", "csw_infra_f26m_sel",
63 static const struct mtk_mux infra_muxes
[] = {
64 /* MODULE_CLK_SEL_0 */
65 MUX_GATE_CLR_SET_UPD(CLK_INFRA_MUX_UART0_SEL
, "infra_mux_uart0_sel",
66 infra_mux_uart0_parents
, 0x0018, 0x0010, 0x0014,
68 MUX_GATE_CLR_SET_UPD(CLK_INFRA_MUX_UART1_SEL
, "infra_mux_uart1_sel",
69 infra_mux_uart1_parents
, 0x0018, 0x0010, 0x0014,
71 MUX_GATE_CLR_SET_UPD(CLK_INFRA_MUX_UART2_SEL
, "infra_mux_uart2_sel",
72 infra_mux_uart2_parents
, 0x0018, 0x0010, 0x0014,
74 MUX_GATE_CLR_SET_UPD(CLK_INFRA_MUX_SPI0_SEL
, "infra_mux_spi0_sel",
75 infra_mux_spi0_parents
, 0x0018, 0x0010, 0x0014, 4,
77 MUX_GATE_CLR_SET_UPD(CLK_INFRA_MUX_SPI1_SEL
, "infra_mux_spi1_sel",
78 infra_mux_spi1_parents
, 0x0018, 0x0010, 0x0014, 5,
80 MUX_GATE_CLR_SET_UPD(CLK_INFRA_MUX_SPI2_SEL
, "infra_mux_spi2_sel",
81 infra_mux_spi0_parents
, 0x0018, 0x0010, 0x0014, 6,
83 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_SEL
, "infra_pwm_sel",
84 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 14,
86 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_CK1_SEL
, "infra_pwm_ck1_sel",
87 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 16,
89 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_CK2_SEL
, "infra_pwm_ck2_sel",
90 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 18,
92 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_CK3_SEL
, "infra_pwm_ck3_sel",
93 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 20,
95 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_CK4_SEL
, "infra_pwm_ck4_sel",
96 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 22,
98 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_CK5_SEL
, "infra_pwm_ck5_sel",
99 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 24,
101 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_CK6_SEL
, "infra_pwm_ck6_sel",
102 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 26,
104 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_CK7_SEL
, "infra_pwm_ck7_sel",
105 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 28,
107 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PWM_CK8_SEL
, "infra_pwm_ck8_sel",
108 infra_pwm_bck_parents
, 0x0018, 0x0010, 0x0014, 30,
110 /* MODULE_CLK_SEL_1 */
111 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PCIE_GFMUX_TL_O_P0_SEL
,
112 "infra_pcie_gfmux_tl_o_p0_sel",
113 infra_pcie_gfmux_tl_ck_o_p0_parents
, 0x0028,
114 0x0020, 0x0024, 0, 2, -1, -1, -1),
115 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PCIE_GFMUX_TL_O_P1_SEL
,
116 "infra_pcie_gfmux_tl_o_p1_sel",
117 infra_pcie_gfmux_tl_ck_o_p1_parents
, 0x0028,
118 0x0020, 0x0024, 2, 2, -1, -1, -1),
119 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PCIE_GFMUX_TL_O_P2_SEL
,
120 "infra_pcie_gfmux_tl_o_p2_sel",
121 infra_pcie_gfmux_tl_ck_o_p2_parents
, 0x0028,
122 0x0020, 0x0024, 4, 2, -1, -1, -1),
123 MUX_GATE_CLR_SET_UPD(CLK_INFRA_PCIE_GFMUX_TL_O_P3_SEL
,
124 "infra_pcie_gfmux_tl_o_p3_sel",
125 infra_pcie_gfmux_tl_ck_o_p3_parents
, 0x0028,
126 0x0020, 0x0024, 6, 2, -1, -1, -1),
129 static const struct mtk_gate_regs infra0_cg_regs
= {
135 static const struct mtk_gate_regs infra1_cg_regs
= {
141 static const struct mtk_gate_regs infra2_cg_regs
= {
147 static const struct mtk_gate_regs infra3_cg_regs
= {
153 #define GATE_INFRA0_FLAGS(_id, _name, _parent, _shift, _flags) \
155 .id = _id, .name = _name, .parent_name = _parent, \
156 .regs = &infra0_cg_regs, .shift = _shift, \
157 .ops = &mtk_clk_gate_ops_setclr, .flags = _flags, \
160 #define GATE_INFRA1_FLAGS(_id, _name, _parent, _shift, _flags) \
162 .id = _id, .name = _name, .parent_name = _parent, \
163 .regs = &infra1_cg_regs, .shift = _shift, \
164 .ops = &mtk_clk_gate_ops_setclr, .flags = _flags, \
167 #define GATE_INFRA2_FLAGS(_id, _name, _parent, _shift, _flags) \
169 .id = _id, .name = _name, .parent_name = _parent, \
170 .regs = &infra2_cg_regs, .shift = _shift, \
171 .ops = &mtk_clk_gate_ops_setclr, .flags = _flags, \
174 #define GATE_INFRA3_FLAGS(_id, _name, _parent, _shift, _flags) \
176 .id = _id, .name = _name, .parent_name = _parent, \
177 .regs = &infra3_cg_regs, .shift = _shift, \
178 .ops = &mtk_clk_gate_ops_setclr, .flags = _flags, \
181 #define GATE_INFRA0(_id, _name, _parent, _shift) \
182 GATE_INFRA0_FLAGS(_id, _name, _parent, _shift, 0)
184 #define GATE_INFRA1(_id, _name, _parent, _shift) \
185 GATE_INFRA1_FLAGS(_id, _name, _parent, _shift, 0)
187 #define GATE_INFRA2(_id, _name, _parent, _shift) \
188 GATE_INFRA2_FLAGS(_id, _name, _parent, _shift, 0)
190 #define GATE_INFRA3(_id, _name, _parent, _shift) \
191 GATE_INFRA3_FLAGS(_id, _name, _parent, _shift, 0)
193 #define GATE_CRITICAL(_id, _name, _parent, _regs, _shift) { \
194 .id = _id, .name = _name, .parent_name = _parent, \
195 .regs = _regs, .shift = _shift, \
196 .flags = CLK_IS_CRITICAL, \
197 .ops = &mtk_clk_gate_ops_setclr, \
200 static const struct mtk_gate infra_clks
[] = {
202 GATE_INFRA0(CLK_INFRA_PCIE_PERI_26M_CK_P0
,
203 "infra_pcie_peri_ck_26m_ck_p0", "csw_infra_f26m_sel", 7),
204 GATE_INFRA0(CLK_INFRA_PCIE_PERI_26M_CK_P1
,
205 "infra_pcie_peri_ck_26m_ck_p1", "csw_infra_f26m_sel", 8),
206 GATE_INFRA0(CLK_INFRA_PCIE_PERI_26M_CK_P2
,
207 "infra_pcie_peri_ck_26m_ck_p2", "csw_infra_f26m_sel", 9),
208 GATE_INFRA0(CLK_INFRA_PCIE_PERI_26M_CK_P3
,
209 "infra_pcie_peri_ck_26m_ck_p3", "csw_infra_f26m_sel", 10),
211 GATE_INFRA1(CLK_INFRA_66M_GPT_BCK
, "infra_hf_66m_gpt_bck",
213 GATE_INFRA1(CLK_INFRA_66M_PWM_HCK
, "infra_hf_66m_pwm_hck",
215 GATE_INFRA1(CLK_INFRA_66M_PWM_BCK
, "infra_hf_66m_pwm_bck",
217 GATE_INFRA1(CLK_INFRA_66M_PWM_CK1
, "infra_hf_66m_pwm_ck1",
218 "infra_pwm_ck1_sel", 3),
219 GATE_INFRA1(CLK_INFRA_66M_PWM_CK2
, "infra_hf_66m_pwm_ck2",
220 "infra_pwm_ck2_sel", 4),
221 GATE_INFRA1(CLK_INFRA_66M_PWM_CK3
, "infra_hf_66m_pwm_ck3",
222 "infra_pwm_ck3_sel", 5),
223 GATE_INFRA1(CLK_INFRA_66M_PWM_CK4
, "infra_hf_66m_pwm_ck4",
224 "infra_pwm_ck4_sel", 6),
225 GATE_INFRA1(CLK_INFRA_66M_PWM_CK5
, "infra_hf_66m_pwm_ck5",
226 "infra_pwm_ck5_sel", 7),
227 GATE_INFRA1(CLK_INFRA_66M_PWM_CK6
, "infra_hf_66m_pwm_ck6",
228 "infra_pwm_ck6_sel", 8),
229 GATE_INFRA1(CLK_INFRA_66M_PWM_CK7
, "infra_hf_66m_pwm_ck7",
230 "infra_pwm_ck7_sel", 9),
231 GATE_INFRA1(CLK_INFRA_66M_PWM_CK8
, "infra_hf_66m_pwm_ck8",
232 "infra_pwm_ck8_sel", 10),
233 GATE_INFRA1(CLK_INFRA_133M_CQDMA_BCK
, "infra_hf_133m_cqdma_bck",
235 GATE_INFRA1(CLK_INFRA_66M_AUD_SLV_BCK
, "infra_66m_aud_slv_bck",
237 GATE_INFRA1(CLK_INFRA_AUD_26M
, "infra_f_faud_26m",
238 "csw_infra_f26m_sel", 14),
239 GATE_INFRA1(CLK_INFRA_AUD_L
, "infra_f_faud_l", "aud_l_sel", 15),
240 GATE_INFRA1(CLK_INFRA_AUD_AUD
, "infra_f_aud_aud", "a1sys_sel", 16),
241 GATE_INFRA1(CLK_INFRA_AUD_EG2
, "infra_f_faud_eg2", "a_tuner_sel", 18),
242 GATE_INFRA1_FLAGS(CLK_INFRA_DRAMC_F26M
, "infra_dramc_f26m",
243 "csw_infra_f26m_sel", 19, CLK_IS_CRITICAL
),
245 GATE_INFRA1_FLAGS(CLK_INFRA_133M_DBG_ACKM
, "infra_hf_133m_dbg_ackm",
246 "sysaxi_sel", 20, CLK_IS_CRITICAL
),
247 GATE_INFRA1(CLK_INFRA_66M_AP_DMA_BCK
, "infra_66m_ap_dma_bck",
249 GATE_INFRA1(CLK_INFRA_66M_SEJ_BCK
, "infra_hf_66m_sej_bck",
251 GATE_INFRA1(CLK_INFRA_PRE_CK_SEJ_F13M
, "infra_pre_ck_sej_f13m",
252 "csw_infra_f26m_sel", 30),
254 GATE_INFRA2(CLK_INFRA_26M_THERM_SYSTEM
, "infra_hf_26m_therm_system",
255 "csw_infra_f26m_sel", 0),
256 GATE_INFRA2(CLK_INFRA_I2C_BCK
, "infra_i2c_bck", "i2c_sel", 1),
257 GATE_INFRA2(CLK_INFRA_52M_UART0_CK
, "infra_f_52m_uart0",
258 "infra_mux_uart0_sel", 3),
259 GATE_INFRA2(CLK_INFRA_52M_UART1_CK
, "infra_f_52m_uart1",
260 "infra_mux_uart1_sel", 4),
261 GATE_INFRA2(CLK_INFRA_52M_UART2_CK
, "infra_f_52m_uart2",
262 "infra_mux_uart2_sel", 5),
263 GATE_INFRA2(CLK_INFRA_NFI
, "infra_f_fnfi", "nfi1x_sel", 9),
264 GATE_INFRA2(CLK_INFRA_SPINFI
, "infra_f_fspinfi", "spinfi_sel", 10),
265 GATE_INFRA2_FLAGS(CLK_INFRA_66M_NFI_HCK
, "infra_hf_66m_nfi_hck",
266 "sysaxi_sel", 11, CLK_IS_CRITICAL
),
267 GATE_INFRA2_FLAGS(CLK_INFRA_104M_SPI0
, "infra_hf_104m_spi0",
268 "infra_mux_spi0_sel", 12, CLK_IS_CRITICAL
),
269 GATE_INFRA2(CLK_INFRA_104M_SPI1
, "infra_hf_104m_spi1",
270 "infra_mux_spi1_sel", 13),
271 GATE_INFRA2(CLK_INFRA_104M_SPI2_BCK
, "infra_hf_104m_spi2_bck",
272 "infra_mux_spi2_sel", 14),
273 GATE_INFRA2_FLAGS(CLK_INFRA_66M_SPI0_HCK
, "infra_hf_66m_spi0_hck",
274 "sysaxi_sel", 15, CLK_IS_CRITICAL
),
275 GATE_INFRA2(CLK_INFRA_66M_SPI1_HCK
, "infra_hf_66m_spi1_hck",
277 GATE_INFRA2(CLK_INFRA_66M_SPI2_HCK
, "infra_hf_66m_spi2_hck",
279 GATE_INFRA2(CLK_INFRA_66M_FLASHIF_AXI
, "infra_hf_66m_flashif_axi",
281 GATE_CRITICAL(CLK_INFRA_RTC
, "infra_f_frtc", "top_rtc_32k", &infra2_cg_regs
, 19),
282 GATE_INFRA2(CLK_INFRA_26M_ADC_BCK
, "infra_f_26m_adc_bck",
283 "csw_infra_f26m_sel", 20),
284 GATE_INFRA2(CLK_INFRA_RC_ADC
, "infra_f_frc_adc", "infra_f_26m_adc_bck",
286 GATE_INFRA2(CLK_INFRA_MSDC400
, "infra_f_fmsdc400", "emmc_400m_sel",
288 GATE_INFRA2(CLK_INFRA_MSDC2_HCK
, "infra_f_fmsdc2_hck", "emmc_250m_sel",
290 GATE_INFRA2(CLK_INFRA_133M_MSDC_0_HCK
, "infra_hf_133m_msdc_0_hck",
292 GATE_INFRA2(CLK_INFRA_66M_MSDC_0_HCK
, "infra_66m_msdc_0_hck",
294 GATE_INFRA2(CLK_INFRA_133M_CPUM_BCK
, "infra_hf_133m_cpum_bck",
296 GATE_INFRA2(CLK_INFRA_BIST2FPC
, "infra_hf_fbist2fpc", "nfi1x_sel", 27),
297 GATE_INFRA2(CLK_INFRA_I2C_X16W_MCK_CK_P1
,
298 "infra_hf_i2c_x16w_mck_ck_p1", "sysaxi_sel", 29),
299 GATE_INFRA2(CLK_INFRA_I2C_X16W_PCK_CK_P1
,
300 "infra_hf_i2c_x16w_pck_ck_p1", "sysaxi_sel", 31),
302 GATE_INFRA3(CLK_INFRA_133M_USB_HCK
, "infra_133m_usb_hck", "sysaxi_sel",
304 GATE_INFRA3(CLK_INFRA_133M_USB_HCK_CK_P1
, "infra_133m_usb_hck_ck_p1",
306 GATE_INFRA3(CLK_INFRA_66M_USB_HCK
, "infra_66m_usb_hck", "sysaxi_sel",
308 GATE_INFRA3(CLK_INFRA_66M_USB_HCK_CK_P1
, "infra_66m_usb_hck_ck_p1",
310 GATE_INFRA3(CLK_INFRA_USB_SYS
, "infra_usb_sys", "usb_sys_sel", 4),
311 GATE_INFRA3(CLK_INFRA_USB_SYS_CK_P1
, "infra_usb_sys_ck_p1",
312 "usb_sys_p1_sel", 5),
313 GATE_INFRA3(CLK_INFRA_USB_REF
, "infra_usb_ref", "top_xtal", 6),
314 GATE_INFRA3(CLK_INFRA_USB_CK_P1
, "infra_usb_ck_p1", "top_xtal", 7),
315 GATE_INFRA3_FLAGS(CLK_INFRA_USB_FRMCNT
, "infra_usb_frmcnt",
316 "usb_frmcnt_sel", 8, CLK_IS_CRITICAL
),
317 GATE_INFRA3_FLAGS(CLK_INFRA_USB_FRMCNT_CK_P1
, "infra_usb_frmcnt_ck_p1",
318 "usb_frmcnt_p1_sel", 9, CLK_IS_CRITICAL
),
319 GATE_INFRA3(CLK_INFRA_USB_PIPE
, "infra_usb_pipe", "sspxtp_sel", 10),
320 GATE_INFRA3(CLK_INFRA_USB_PIPE_CK_P1
, "infra_usb_pipe_ck_p1",
322 GATE_INFRA3(CLK_INFRA_USB_UTMI
, "infra_usb_utmi", "top_xtal", 12),
323 GATE_INFRA3(CLK_INFRA_USB_UTMI_CK_P1
, "infra_usb_utmi_ck_p1",
325 GATE_INFRA3(CLK_INFRA_USB_XHCI
, "infra_usb_xhci", "usb_xhci_sel", 14),
326 GATE_INFRA3(CLK_INFRA_USB_XHCI_CK_P1
, "infra_usb_xhci_ck_p1",
327 "usb_xhci_p1_sel", 15),
328 GATE_INFRA3(CLK_INFRA_PCIE_GFMUX_TL_P0
, "infra_pcie_gfmux_tl_ck_p0",
329 "infra_pcie_gfmux_tl_o_p0_sel", 20),
330 GATE_INFRA3(CLK_INFRA_PCIE_GFMUX_TL_P1
, "infra_pcie_gfmux_tl_ck_p1",
331 "infra_pcie_gfmux_tl_o_p1_sel", 21),
332 GATE_INFRA3(CLK_INFRA_PCIE_GFMUX_TL_P2
, "infra_pcie_gfmux_tl_ck_p2",
333 "infra_pcie_gfmux_tl_o_p2_sel", 22),
334 GATE_INFRA3(CLK_INFRA_PCIE_GFMUX_TL_P3
, "infra_pcie_gfmux_tl_ck_p3",
335 "infra_pcie_gfmux_tl_o_p3_sel", 23),
336 GATE_INFRA3(CLK_INFRA_PCIE_PIPE_P0
, "infra_pcie_pipe_ck_p0",
338 GATE_INFRA3(CLK_INFRA_PCIE_PIPE_P1
, "infra_pcie_pipe_ck_p1",
340 GATE_INFRA3(CLK_INFRA_PCIE_PIPE_P2
, "infra_pcie_pipe_ck_p2",
342 GATE_INFRA3(CLK_INFRA_PCIE_PIPE_P3
, "infra_pcie_pipe_ck_p3",
344 GATE_INFRA3(CLK_INFRA_133M_PCIE_CK_P0
, "infra_133m_pcie_ck_p0",
346 GATE_INFRA3(CLK_INFRA_133M_PCIE_CK_P1
, "infra_133m_pcie_ck_p1",
348 GATE_INFRA3(CLK_INFRA_133M_PCIE_CK_P2
, "infra_133m_pcie_ck_p2",
350 GATE_INFRA3(CLK_INFRA_133M_PCIE_CK_P3
, "infra_133m_pcie_ck_p3",
354 static const struct mtk_clk_desc infra_desc
= {
356 .num_clks
= ARRAY_SIZE(infra_clks
),
357 .mux_clks
= infra_muxes
,
358 .num_mux_clks
= ARRAY_SIZE(infra_muxes
),
359 .clk_lock
= &mt7988_clk_lock
,
362 static const struct of_device_id of_match_clk_mt7988_infracfg
[] = {
363 { .compatible
= "mediatek,mt7988-infracfg", .data
= &infra_desc
},
366 MODULE_DEVICE_TABLE(of
, of_match_clk_mt7988_infracfg
);
368 static struct platform_driver clk_mt7988_infracfg_drv
= {
370 .name
= "clk-mt7988-infracfg",
371 .of_match_table
= of_match_clk_mt7988_infracfg
,
373 .probe
= mtk_clk_simple_probe
,
374 .remove
= mtk_clk_simple_remove
,
376 module_platform_driver(clk_mt7988_infracfg_drv
);