18c2ecf20Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0 28c2ecf20Sopenharmony_ci/* 38c2ecf20Sopenharmony_ci * X1830 SoC CGU driver 48c2ecf20Sopenharmony_ci * Copyright (c) 2019 周琰杰 (Zhou Yanjie) <zhouyanjie@wanyeetech.com> 58c2ecf20Sopenharmony_ci */ 68c2ecf20Sopenharmony_ci 78c2ecf20Sopenharmony_ci#include <linux/clk-provider.h> 88c2ecf20Sopenharmony_ci#include <linux/delay.h> 98c2ecf20Sopenharmony_ci#include <linux/io.h> 108c2ecf20Sopenharmony_ci#include <linux/of.h> 118c2ecf20Sopenharmony_ci 128c2ecf20Sopenharmony_ci#include <dt-bindings/clock/x1830-cgu.h> 138c2ecf20Sopenharmony_ci 148c2ecf20Sopenharmony_ci#include "cgu.h" 158c2ecf20Sopenharmony_ci#include "pm.h" 168c2ecf20Sopenharmony_ci 178c2ecf20Sopenharmony_ci/* CGU register offsets */ 188c2ecf20Sopenharmony_ci#define CGU_REG_CPCCR 0x00 198c2ecf20Sopenharmony_ci#define CGU_REG_CPPCR 0x0c 208c2ecf20Sopenharmony_ci#define CGU_REG_APLL 0x10 218c2ecf20Sopenharmony_ci#define CGU_REG_MPLL 0x14 228c2ecf20Sopenharmony_ci#define CGU_REG_CLKGR0 0x20 238c2ecf20Sopenharmony_ci#define CGU_REG_OPCR 0x24 248c2ecf20Sopenharmony_ci#define CGU_REG_CLKGR1 0x28 258c2ecf20Sopenharmony_ci#define CGU_REG_DDRCDR 0x2c 268c2ecf20Sopenharmony_ci#define CGU_REG_USBPCR 0x3c 278c2ecf20Sopenharmony_ci#define CGU_REG_USBRDT 0x40 288c2ecf20Sopenharmony_ci#define CGU_REG_USBVBFIL 0x44 298c2ecf20Sopenharmony_ci#define CGU_REG_USBPCR1 0x48 308c2ecf20Sopenharmony_ci#define CGU_REG_MACCDR 0x54 318c2ecf20Sopenharmony_ci#define CGU_REG_EPLL 0x58 328c2ecf20Sopenharmony_ci#define CGU_REG_I2SCDR 0x60 338c2ecf20Sopenharmony_ci#define CGU_REG_LPCDR 0x64 348c2ecf20Sopenharmony_ci#define CGU_REG_MSC0CDR 0x68 358c2ecf20Sopenharmony_ci#define CGU_REG_I2SCDR1 0x70 368c2ecf20Sopenharmony_ci#define CGU_REG_SSICDR 0x74 378c2ecf20Sopenharmony_ci#define CGU_REG_CIMCDR 0x7c 388c2ecf20Sopenharmony_ci#define CGU_REG_MSC1CDR 0xa4 398c2ecf20Sopenharmony_ci#define CGU_REG_CMP_INTR 0xb0 408c2ecf20Sopenharmony_ci#define CGU_REG_CMP_INTRE 0xb4 418c2ecf20Sopenharmony_ci#define CGU_REG_DRCG 0xd0 428c2ecf20Sopenharmony_ci#define CGU_REG_CPCSR 0xd4 438c2ecf20Sopenharmony_ci#define CGU_REG_VPLL 0xe0 448c2ecf20Sopenharmony_ci#define CGU_REG_MACPHYC 0xe8 458c2ecf20Sopenharmony_ci 468c2ecf20Sopenharmony_ci/* bits within the OPCR register */ 478c2ecf20Sopenharmony_ci#define OPCR_GATE_USBPHYCLK BIT(23) 488c2ecf20Sopenharmony_ci#define OPCR_SPENDN0 BIT(7) 498c2ecf20Sopenharmony_ci#define OPCR_SPENDN1 BIT(6) 508c2ecf20Sopenharmony_ci 518c2ecf20Sopenharmony_ci/* bits within the USBPCR register */ 528c2ecf20Sopenharmony_ci#define USBPCR_SIDDQ BIT(21) 538c2ecf20Sopenharmony_ci#define USBPCR_OTG_DISABLE BIT(20) 548c2ecf20Sopenharmony_ci 558c2ecf20Sopenharmony_cistatic struct ingenic_cgu *cgu; 568c2ecf20Sopenharmony_ci 578c2ecf20Sopenharmony_cistatic int x1830_usb_phy_enable(struct clk_hw *hw) 588c2ecf20Sopenharmony_ci{ 598c2ecf20Sopenharmony_ci void __iomem *reg_opcr = cgu->base + CGU_REG_OPCR; 608c2ecf20Sopenharmony_ci void __iomem *reg_usbpcr = cgu->base + CGU_REG_USBPCR; 618c2ecf20Sopenharmony_ci 628c2ecf20Sopenharmony_ci writel((readl(reg_opcr) | OPCR_SPENDN0) & ~OPCR_GATE_USBPHYCLK, reg_opcr); 638c2ecf20Sopenharmony_ci writel(readl(reg_usbpcr) & ~USBPCR_OTG_DISABLE & ~USBPCR_SIDDQ, reg_usbpcr); 648c2ecf20Sopenharmony_ci return 0; 658c2ecf20Sopenharmony_ci} 668c2ecf20Sopenharmony_ci 678c2ecf20Sopenharmony_cistatic void x1830_usb_phy_disable(struct clk_hw *hw) 688c2ecf20Sopenharmony_ci{ 698c2ecf20Sopenharmony_ci void __iomem *reg_opcr = cgu->base + CGU_REG_OPCR; 708c2ecf20Sopenharmony_ci void __iomem *reg_usbpcr = cgu->base + CGU_REG_USBPCR; 718c2ecf20Sopenharmony_ci 728c2ecf20Sopenharmony_ci writel((readl(reg_opcr) & ~OPCR_SPENDN0) | OPCR_GATE_USBPHYCLK, reg_opcr); 738c2ecf20Sopenharmony_ci writel(readl(reg_usbpcr) | USBPCR_OTG_DISABLE | USBPCR_SIDDQ, reg_usbpcr); 748c2ecf20Sopenharmony_ci} 758c2ecf20Sopenharmony_ci 768c2ecf20Sopenharmony_cistatic int x1830_usb_phy_is_enabled(struct clk_hw *hw) 778c2ecf20Sopenharmony_ci{ 788c2ecf20Sopenharmony_ci void __iomem *reg_opcr = cgu->base + CGU_REG_OPCR; 798c2ecf20Sopenharmony_ci void __iomem *reg_usbpcr = cgu->base + CGU_REG_USBPCR; 808c2ecf20Sopenharmony_ci 818c2ecf20Sopenharmony_ci return (readl(reg_opcr) & OPCR_SPENDN0) && 828c2ecf20Sopenharmony_ci !(readl(reg_usbpcr) & USBPCR_SIDDQ) && 838c2ecf20Sopenharmony_ci !(readl(reg_usbpcr) & USBPCR_OTG_DISABLE); 848c2ecf20Sopenharmony_ci} 858c2ecf20Sopenharmony_ci 868c2ecf20Sopenharmony_cistatic const struct clk_ops x1830_otg_phy_ops = { 878c2ecf20Sopenharmony_ci .enable = x1830_usb_phy_enable, 888c2ecf20Sopenharmony_ci .disable = x1830_usb_phy_disable, 898c2ecf20Sopenharmony_ci .is_enabled = x1830_usb_phy_is_enabled, 908c2ecf20Sopenharmony_ci}; 918c2ecf20Sopenharmony_ci 928c2ecf20Sopenharmony_cistatic const s8 pll_od_encoding[64] = { 938c2ecf20Sopenharmony_ci 0x0, 0x1, -1, 0x2, -1, -1, -1, 0x3, 948c2ecf20Sopenharmony_ci -1, -1, -1, -1, -1, -1, -1, 0x4, 958c2ecf20Sopenharmony_ci -1, -1, -1, -1, -1, -1, -1, -1, 968c2ecf20Sopenharmony_ci -1, -1, -1, -1, -1, -1, -1, 0x5, 978c2ecf20Sopenharmony_ci -1, -1, -1, -1, -1, -1, -1, -1, 988c2ecf20Sopenharmony_ci -1, -1, -1, -1, -1, -1, -1, -1, 998c2ecf20Sopenharmony_ci -1, -1, -1, -1, -1, -1, -1, -1, 1008c2ecf20Sopenharmony_ci -1, -1, -1, -1, -1, -1, -1, 0x6, 1018c2ecf20Sopenharmony_ci}; 1028c2ecf20Sopenharmony_ci 1038c2ecf20Sopenharmony_cistatic const struct ingenic_cgu_clk_info x1830_cgu_clocks[] = { 1048c2ecf20Sopenharmony_ci 1058c2ecf20Sopenharmony_ci /* External clocks */ 1068c2ecf20Sopenharmony_ci 1078c2ecf20Sopenharmony_ci [X1830_CLK_EXCLK] = { "ext", CGU_CLK_EXT }, 1088c2ecf20Sopenharmony_ci [X1830_CLK_RTCLK] = { "rtc", CGU_CLK_EXT }, 1098c2ecf20Sopenharmony_ci 1108c2ecf20Sopenharmony_ci /* PLLs */ 1118c2ecf20Sopenharmony_ci 1128c2ecf20Sopenharmony_ci [X1830_CLK_APLL] = { 1138c2ecf20Sopenharmony_ci "apll", CGU_CLK_PLL, 1148c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 1158c2ecf20Sopenharmony_ci .pll = { 1168c2ecf20Sopenharmony_ci .reg = CGU_REG_APLL, 1178c2ecf20Sopenharmony_ci .rate_multiplier = 2, 1188c2ecf20Sopenharmony_ci .m_shift = 20, 1198c2ecf20Sopenharmony_ci .m_bits = 9, 1208c2ecf20Sopenharmony_ci .m_offset = 1, 1218c2ecf20Sopenharmony_ci .n_shift = 14, 1228c2ecf20Sopenharmony_ci .n_bits = 6, 1238c2ecf20Sopenharmony_ci .n_offset = 1, 1248c2ecf20Sopenharmony_ci .od_shift = 11, 1258c2ecf20Sopenharmony_ci .od_bits = 3, 1268c2ecf20Sopenharmony_ci .od_max = 64, 1278c2ecf20Sopenharmony_ci .od_encoding = pll_od_encoding, 1288c2ecf20Sopenharmony_ci .bypass_reg = CGU_REG_CPPCR, 1298c2ecf20Sopenharmony_ci .bypass_bit = 30, 1308c2ecf20Sopenharmony_ci .enable_bit = 0, 1318c2ecf20Sopenharmony_ci .stable_bit = 3, 1328c2ecf20Sopenharmony_ci }, 1338c2ecf20Sopenharmony_ci }, 1348c2ecf20Sopenharmony_ci 1358c2ecf20Sopenharmony_ci [X1830_CLK_MPLL] = { 1368c2ecf20Sopenharmony_ci "mpll", CGU_CLK_PLL, 1378c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 1388c2ecf20Sopenharmony_ci .pll = { 1398c2ecf20Sopenharmony_ci .reg = CGU_REG_MPLL, 1408c2ecf20Sopenharmony_ci .rate_multiplier = 2, 1418c2ecf20Sopenharmony_ci .m_shift = 20, 1428c2ecf20Sopenharmony_ci .m_bits = 9, 1438c2ecf20Sopenharmony_ci .m_offset = 1, 1448c2ecf20Sopenharmony_ci .n_shift = 14, 1458c2ecf20Sopenharmony_ci .n_bits = 6, 1468c2ecf20Sopenharmony_ci .n_offset = 1, 1478c2ecf20Sopenharmony_ci .od_shift = 11, 1488c2ecf20Sopenharmony_ci .od_bits = 3, 1498c2ecf20Sopenharmony_ci .od_max = 64, 1508c2ecf20Sopenharmony_ci .od_encoding = pll_od_encoding, 1518c2ecf20Sopenharmony_ci .bypass_reg = CGU_REG_CPPCR, 1528c2ecf20Sopenharmony_ci .bypass_bit = 28, 1538c2ecf20Sopenharmony_ci .enable_bit = 0, 1548c2ecf20Sopenharmony_ci .stable_bit = 3, 1558c2ecf20Sopenharmony_ci }, 1568c2ecf20Sopenharmony_ci }, 1578c2ecf20Sopenharmony_ci 1588c2ecf20Sopenharmony_ci [X1830_CLK_EPLL] = { 1598c2ecf20Sopenharmony_ci "epll", CGU_CLK_PLL, 1608c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 1618c2ecf20Sopenharmony_ci .pll = { 1628c2ecf20Sopenharmony_ci .reg = CGU_REG_EPLL, 1638c2ecf20Sopenharmony_ci .rate_multiplier = 2, 1648c2ecf20Sopenharmony_ci .m_shift = 20, 1658c2ecf20Sopenharmony_ci .m_bits = 9, 1668c2ecf20Sopenharmony_ci .m_offset = 1, 1678c2ecf20Sopenharmony_ci .n_shift = 14, 1688c2ecf20Sopenharmony_ci .n_bits = 6, 1698c2ecf20Sopenharmony_ci .n_offset = 1, 1708c2ecf20Sopenharmony_ci .od_shift = 11, 1718c2ecf20Sopenharmony_ci .od_bits = 3, 1728c2ecf20Sopenharmony_ci .od_max = 64, 1738c2ecf20Sopenharmony_ci .od_encoding = pll_od_encoding, 1748c2ecf20Sopenharmony_ci .bypass_reg = CGU_REG_CPPCR, 1758c2ecf20Sopenharmony_ci .bypass_bit = 24, 1768c2ecf20Sopenharmony_ci .enable_bit = 0, 1778c2ecf20Sopenharmony_ci .stable_bit = 3, 1788c2ecf20Sopenharmony_ci }, 1798c2ecf20Sopenharmony_ci }, 1808c2ecf20Sopenharmony_ci 1818c2ecf20Sopenharmony_ci [X1830_CLK_VPLL] = { 1828c2ecf20Sopenharmony_ci "vpll", CGU_CLK_PLL, 1838c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 1848c2ecf20Sopenharmony_ci .pll = { 1858c2ecf20Sopenharmony_ci .reg = CGU_REG_VPLL, 1868c2ecf20Sopenharmony_ci .rate_multiplier = 2, 1878c2ecf20Sopenharmony_ci .m_shift = 20, 1888c2ecf20Sopenharmony_ci .m_bits = 9, 1898c2ecf20Sopenharmony_ci .m_offset = 1, 1908c2ecf20Sopenharmony_ci .n_shift = 14, 1918c2ecf20Sopenharmony_ci .n_bits = 6, 1928c2ecf20Sopenharmony_ci .n_offset = 1, 1938c2ecf20Sopenharmony_ci .od_shift = 11, 1948c2ecf20Sopenharmony_ci .od_bits = 3, 1958c2ecf20Sopenharmony_ci .od_max = 64, 1968c2ecf20Sopenharmony_ci .od_encoding = pll_od_encoding, 1978c2ecf20Sopenharmony_ci .bypass_reg = CGU_REG_CPPCR, 1988c2ecf20Sopenharmony_ci .bypass_bit = 26, 1998c2ecf20Sopenharmony_ci .enable_bit = 0, 2008c2ecf20Sopenharmony_ci .stable_bit = 3, 2018c2ecf20Sopenharmony_ci }, 2028c2ecf20Sopenharmony_ci }, 2038c2ecf20Sopenharmony_ci 2048c2ecf20Sopenharmony_ci /* Custom (SoC-specific) OTG PHY */ 2058c2ecf20Sopenharmony_ci 2068c2ecf20Sopenharmony_ci [X1830_CLK_OTGPHY] = { 2078c2ecf20Sopenharmony_ci "otg_phy", CGU_CLK_CUSTOM, 2088c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 2098c2ecf20Sopenharmony_ci .custom = { &x1830_otg_phy_ops }, 2108c2ecf20Sopenharmony_ci }, 2118c2ecf20Sopenharmony_ci 2128c2ecf20Sopenharmony_ci /* Muxes & dividers */ 2138c2ecf20Sopenharmony_ci 2148c2ecf20Sopenharmony_ci [X1830_CLK_SCLKA] = { 2158c2ecf20Sopenharmony_ci "sclk_a", CGU_CLK_MUX, 2168c2ecf20Sopenharmony_ci .parents = { -1, X1830_CLK_EXCLK, X1830_CLK_APLL, -1 }, 2178c2ecf20Sopenharmony_ci .mux = { CGU_REG_CPCCR, 30, 2 }, 2188c2ecf20Sopenharmony_ci }, 2198c2ecf20Sopenharmony_ci 2208c2ecf20Sopenharmony_ci [X1830_CLK_CPUMUX] = { 2218c2ecf20Sopenharmony_ci "cpu_mux", CGU_CLK_MUX, 2228c2ecf20Sopenharmony_ci .parents = { -1, X1830_CLK_SCLKA, X1830_CLK_MPLL, -1 }, 2238c2ecf20Sopenharmony_ci .mux = { CGU_REG_CPCCR, 28, 2 }, 2248c2ecf20Sopenharmony_ci }, 2258c2ecf20Sopenharmony_ci 2268c2ecf20Sopenharmony_ci [X1830_CLK_CPU] = { 2278c2ecf20Sopenharmony_ci "cpu", CGU_CLK_DIV | CGU_CLK_GATE, 2288c2ecf20Sopenharmony_ci .parents = { X1830_CLK_CPUMUX, -1, -1, -1 }, 2298c2ecf20Sopenharmony_ci .div = { CGU_REG_CPCCR, 0, 1, 4, 22, -1, -1 }, 2308c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR1, 15 }, 2318c2ecf20Sopenharmony_ci }, 2328c2ecf20Sopenharmony_ci 2338c2ecf20Sopenharmony_ci [X1830_CLK_L2CACHE] = { 2348c2ecf20Sopenharmony_ci "l2cache", CGU_CLK_DIV, 2358c2ecf20Sopenharmony_ci .parents = { X1830_CLK_CPUMUX, -1, -1, -1 }, 2368c2ecf20Sopenharmony_ci .div = { CGU_REG_CPCCR, 4, 1, 4, 22, -1, -1 }, 2378c2ecf20Sopenharmony_ci }, 2388c2ecf20Sopenharmony_ci 2398c2ecf20Sopenharmony_ci [X1830_CLK_AHB0] = { 2408c2ecf20Sopenharmony_ci "ahb0", CGU_CLK_MUX | CGU_CLK_DIV, 2418c2ecf20Sopenharmony_ci .parents = { -1, X1830_CLK_SCLKA, X1830_CLK_MPLL, -1 }, 2428c2ecf20Sopenharmony_ci .mux = { CGU_REG_CPCCR, 26, 2 }, 2438c2ecf20Sopenharmony_ci .div = { CGU_REG_CPCCR, 8, 1, 4, 21, -1, -1 }, 2448c2ecf20Sopenharmony_ci }, 2458c2ecf20Sopenharmony_ci 2468c2ecf20Sopenharmony_ci [X1830_CLK_AHB2PMUX] = { 2478c2ecf20Sopenharmony_ci "ahb2_apb_mux", CGU_CLK_MUX, 2488c2ecf20Sopenharmony_ci .parents = { -1, X1830_CLK_SCLKA, X1830_CLK_MPLL, -1 }, 2498c2ecf20Sopenharmony_ci .mux = { CGU_REG_CPCCR, 24, 2 }, 2508c2ecf20Sopenharmony_ci }, 2518c2ecf20Sopenharmony_ci 2528c2ecf20Sopenharmony_ci [X1830_CLK_AHB2] = { 2538c2ecf20Sopenharmony_ci "ahb2", CGU_CLK_DIV, 2548c2ecf20Sopenharmony_ci .parents = { X1830_CLK_AHB2PMUX, -1, -1, -1 }, 2558c2ecf20Sopenharmony_ci .div = { CGU_REG_CPCCR, 12, 1, 4, 20, -1, -1 }, 2568c2ecf20Sopenharmony_ci }, 2578c2ecf20Sopenharmony_ci 2588c2ecf20Sopenharmony_ci [X1830_CLK_PCLK] = { 2598c2ecf20Sopenharmony_ci "pclk", CGU_CLK_DIV | CGU_CLK_GATE, 2608c2ecf20Sopenharmony_ci .parents = { X1830_CLK_AHB2PMUX, -1, -1, -1 }, 2618c2ecf20Sopenharmony_ci .div = { CGU_REG_CPCCR, 16, 1, 4, 20, -1, -1 }, 2628c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR1, 14 }, 2638c2ecf20Sopenharmony_ci }, 2648c2ecf20Sopenharmony_ci 2658c2ecf20Sopenharmony_ci [X1830_CLK_DDR] = { 2668c2ecf20Sopenharmony_ci "ddr", CGU_CLK_MUX | CGU_CLK_DIV | CGU_CLK_GATE, 2678c2ecf20Sopenharmony_ci .parents = { -1, X1830_CLK_SCLKA, X1830_CLK_MPLL, -1 }, 2688c2ecf20Sopenharmony_ci .mux = { CGU_REG_DDRCDR, 30, 2 }, 2698c2ecf20Sopenharmony_ci .div = { CGU_REG_DDRCDR, 0, 1, 4, 29, 28, 27 }, 2708c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 31 }, 2718c2ecf20Sopenharmony_ci }, 2728c2ecf20Sopenharmony_ci 2738c2ecf20Sopenharmony_ci [X1830_CLK_MAC] = { 2748c2ecf20Sopenharmony_ci "mac", CGU_CLK_MUX | CGU_CLK_DIV | CGU_CLK_GATE, 2758c2ecf20Sopenharmony_ci .parents = { X1830_CLK_SCLKA, X1830_CLK_MPLL, 2768c2ecf20Sopenharmony_ci X1830_CLK_VPLL, X1830_CLK_EPLL }, 2778c2ecf20Sopenharmony_ci .mux = { CGU_REG_MACCDR, 30, 2 }, 2788c2ecf20Sopenharmony_ci .div = { CGU_REG_MACCDR, 0, 1, 8, 29, 28, 27 }, 2798c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR1, 4 }, 2808c2ecf20Sopenharmony_ci }, 2818c2ecf20Sopenharmony_ci 2828c2ecf20Sopenharmony_ci [X1830_CLK_LCD] = { 2838c2ecf20Sopenharmony_ci "lcd", CGU_CLK_MUX | CGU_CLK_DIV | CGU_CLK_GATE, 2848c2ecf20Sopenharmony_ci .parents = { X1830_CLK_SCLKA, X1830_CLK_MPLL, 2858c2ecf20Sopenharmony_ci X1830_CLK_VPLL, X1830_CLK_EPLL }, 2868c2ecf20Sopenharmony_ci .mux = { CGU_REG_LPCDR, 30, 2 }, 2878c2ecf20Sopenharmony_ci .div = { CGU_REG_LPCDR, 0, 1, 8, 28, 27, 26 }, 2888c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR1, 9 }, 2898c2ecf20Sopenharmony_ci }, 2908c2ecf20Sopenharmony_ci 2918c2ecf20Sopenharmony_ci [X1830_CLK_MSCMUX] = { 2928c2ecf20Sopenharmony_ci "msc_mux", CGU_CLK_MUX, 2938c2ecf20Sopenharmony_ci .parents = { X1830_CLK_SCLKA, X1830_CLK_MPLL, 2948c2ecf20Sopenharmony_ci X1830_CLK_VPLL, X1830_CLK_EPLL }, 2958c2ecf20Sopenharmony_ci .mux = { CGU_REG_MSC0CDR, 30, 2 }, 2968c2ecf20Sopenharmony_ci }, 2978c2ecf20Sopenharmony_ci 2988c2ecf20Sopenharmony_ci [X1830_CLK_MSC0] = { 2998c2ecf20Sopenharmony_ci "msc0", CGU_CLK_DIV | CGU_CLK_GATE, 3008c2ecf20Sopenharmony_ci .parents = { X1830_CLK_MSCMUX, -1, -1, -1 }, 3018c2ecf20Sopenharmony_ci .div = { CGU_REG_MSC0CDR, 0, 2, 8, 29, 28, 27 }, 3028c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 4 }, 3038c2ecf20Sopenharmony_ci }, 3048c2ecf20Sopenharmony_ci 3058c2ecf20Sopenharmony_ci [X1830_CLK_MSC1] = { 3068c2ecf20Sopenharmony_ci "msc1", CGU_CLK_DIV | CGU_CLK_GATE, 3078c2ecf20Sopenharmony_ci .parents = { X1830_CLK_MSCMUX, -1, -1, -1 }, 3088c2ecf20Sopenharmony_ci .div = { CGU_REG_MSC1CDR, 0, 2, 8, 29, 28, 27 }, 3098c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 5 }, 3108c2ecf20Sopenharmony_ci }, 3118c2ecf20Sopenharmony_ci 3128c2ecf20Sopenharmony_ci [X1830_CLK_SSIPLL] = { 3138c2ecf20Sopenharmony_ci "ssi_pll", CGU_CLK_MUX | CGU_CLK_DIV, 3148c2ecf20Sopenharmony_ci .parents = { X1830_CLK_SCLKA, X1830_CLK_MPLL, 3158c2ecf20Sopenharmony_ci X1830_CLK_VPLL, X1830_CLK_EPLL }, 3168c2ecf20Sopenharmony_ci .mux = { CGU_REG_SSICDR, 30, 2 }, 3178c2ecf20Sopenharmony_ci .div = { CGU_REG_SSICDR, 0, 1, 8, 28, 27, 26 }, 3188c2ecf20Sopenharmony_ci }, 3198c2ecf20Sopenharmony_ci 3208c2ecf20Sopenharmony_ci [X1830_CLK_SSIPLL_DIV2] = { 3218c2ecf20Sopenharmony_ci "ssi_pll_div2", CGU_CLK_FIXDIV, 3228c2ecf20Sopenharmony_ci .parents = { X1830_CLK_SSIPLL }, 3238c2ecf20Sopenharmony_ci .fixdiv = { 2 }, 3248c2ecf20Sopenharmony_ci }, 3258c2ecf20Sopenharmony_ci 3268c2ecf20Sopenharmony_ci [X1830_CLK_SSIMUX] = { 3278c2ecf20Sopenharmony_ci "ssi_mux", CGU_CLK_MUX, 3288c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, X1830_CLK_SSIPLL_DIV2, -1, -1 }, 3298c2ecf20Sopenharmony_ci .mux = { CGU_REG_SSICDR, 29, 1 }, 3308c2ecf20Sopenharmony_ci }, 3318c2ecf20Sopenharmony_ci 3328c2ecf20Sopenharmony_ci [X1830_CLK_EXCLK_DIV512] = { 3338c2ecf20Sopenharmony_ci "exclk_div512", CGU_CLK_FIXDIV, 3348c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK }, 3358c2ecf20Sopenharmony_ci .fixdiv = { 512 }, 3368c2ecf20Sopenharmony_ci }, 3378c2ecf20Sopenharmony_ci 3388c2ecf20Sopenharmony_ci [X1830_CLK_RTC] = { 3398c2ecf20Sopenharmony_ci "rtc_ercs", CGU_CLK_MUX | CGU_CLK_GATE, 3408c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK_DIV512, X1830_CLK_RTCLK }, 3418c2ecf20Sopenharmony_ci .mux = { CGU_REG_OPCR, 2, 1}, 3428c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 29 }, 3438c2ecf20Sopenharmony_ci }, 3448c2ecf20Sopenharmony_ci 3458c2ecf20Sopenharmony_ci /* Gate-only clocks */ 3468c2ecf20Sopenharmony_ci 3478c2ecf20Sopenharmony_ci [X1830_CLK_EMC] = { 3488c2ecf20Sopenharmony_ci "emc", CGU_CLK_GATE, 3498c2ecf20Sopenharmony_ci .parents = { X1830_CLK_AHB2, -1, -1, -1 }, 3508c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 0 }, 3518c2ecf20Sopenharmony_ci }, 3528c2ecf20Sopenharmony_ci 3538c2ecf20Sopenharmony_ci [X1830_CLK_EFUSE] = { 3548c2ecf20Sopenharmony_ci "efuse", CGU_CLK_GATE, 3558c2ecf20Sopenharmony_ci .parents = { X1830_CLK_AHB2, -1, -1, -1 }, 3568c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 1 }, 3578c2ecf20Sopenharmony_ci }, 3588c2ecf20Sopenharmony_ci 3598c2ecf20Sopenharmony_ci [X1830_CLK_OTG] = { 3608c2ecf20Sopenharmony_ci "otg", CGU_CLK_GATE, 3618c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 3628c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 3 }, 3638c2ecf20Sopenharmony_ci }, 3648c2ecf20Sopenharmony_ci 3658c2ecf20Sopenharmony_ci [X1830_CLK_SSI0] = { 3668c2ecf20Sopenharmony_ci "ssi0", CGU_CLK_GATE, 3678c2ecf20Sopenharmony_ci .parents = { X1830_CLK_SSIMUX, -1, -1, -1 }, 3688c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 6 }, 3698c2ecf20Sopenharmony_ci }, 3708c2ecf20Sopenharmony_ci 3718c2ecf20Sopenharmony_ci [X1830_CLK_SMB0] = { 3728c2ecf20Sopenharmony_ci "smb0", CGU_CLK_GATE, 3738c2ecf20Sopenharmony_ci .parents = { X1830_CLK_PCLK, -1, -1, -1 }, 3748c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 7 }, 3758c2ecf20Sopenharmony_ci }, 3768c2ecf20Sopenharmony_ci 3778c2ecf20Sopenharmony_ci [X1830_CLK_SMB1] = { 3788c2ecf20Sopenharmony_ci "smb1", CGU_CLK_GATE, 3798c2ecf20Sopenharmony_ci .parents = { X1830_CLK_PCLK, -1, -1, -1 }, 3808c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 8 }, 3818c2ecf20Sopenharmony_ci }, 3828c2ecf20Sopenharmony_ci 3838c2ecf20Sopenharmony_ci [X1830_CLK_SMB2] = { 3848c2ecf20Sopenharmony_ci "smb2", CGU_CLK_GATE, 3858c2ecf20Sopenharmony_ci .parents = { X1830_CLK_PCLK, -1, -1, -1 }, 3868c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 9 }, 3878c2ecf20Sopenharmony_ci }, 3888c2ecf20Sopenharmony_ci 3898c2ecf20Sopenharmony_ci [X1830_CLK_UART0] = { 3908c2ecf20Sopenharmony_ci "uart0", CGU_CLK_GATE, 3918c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 3928c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 14 }, 3938c2ecf20Sopenharmony_ci }, 3948c2ecf20Sopenharmony_ci 3958c2ecf20Sopenharmony_ci [X1830_CLK_UART1] = { 3968c2ecf20Sopenharmony_ci "uart1", CGU_CLK_GATE, 3978c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 3988c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 15 }, 3998c2ecf20Sopenharmony_ci }, 4008c2ecf20Sopenharmony_ci 4018c2ecf20Sopenharmony_ci [X1830_CLK_SSI1] = { 4028c2ecf20Sopenharmony_ci "ssi1", CGU_CLK_GATE, 4038c2ecf20Sopenharmony_ci .parents = { X1830_CLK_SSIMUX, -1, -1, -1 }, 4048c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 19 }, 4058c2ecf20Sopenharmony_ci }, 4068c2ecf20Sopenharmony_ci 4078c2ecf20Sopenharmony_ci [X1830_CLK_SFC] = { 4088c2ecf20Sopenharmony_ci "sfc", CGU_CLK_GATE, 4098c2ecf20Sopenharmony_ci .parents = { X1830_CLK_SSIPLL, -1, -1, -1 }, 4108c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 20 }, 4118c2ecf20Sopenharmony_ci }, 4128c2ecf20Sopenharmony_ci 4138c2ecf20Sopenharmony_ci [X1830_CLK_PDMA] = { 4148c2ecf20Sopenharmony_ci "pdma", CGU_CLK_GATE, 4158c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 4168c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 21 }, 4178c2ecf20Sopenharmony_ci }, 4188c2ecf20Sopenharmony_ci 4198c2ecf20Sopenharmony_ci [X1830_CLK_TCU] = { 4208c2ecf20Sopenharmony_ci "tcu", CGU_CLK_GATE, 4218c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 4228c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR0, 30 }, 4238c2ecf20Sopenharmony_ci }, 4248c2ecf20Sopenharmony_ci 4258c2ecf20Sopenharmony_ci [X1830_CLK_DTRNG] = { 4268c2ecf20Sopenharmony_ci "dtrng", CGU_CLK_GATE, 4278c2ecf20Sopenharmony_ci .parents = { X1830_CLK_PCLK, -1, -1, -1 }, 4288c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR1, 1 }, 4298c2ecf20Sopenharmony_ci }, 4308c2ecf20Sopenharmony_ci 4318c2ecf20Sopenharmony_ci [X1830_CLK_OST] = { 4328c2ecf20Sopenharmony_ci "ost", CGU_CLK_GATE, 4338c2ecf20Sopenharmony_ci .parents = { X1830_CLK_EXCLK, -1, -1, -1 }, 4348c2ecf20Sopenharmony_ci .gate = { CGU_REG_CLKGR1, 11 }, 4358c2ecf20Sopenharmony_ci }, 4368c2ecf20Sopenharmony_ci}; 4378c2ecf20Sopenharmony_ci 4388c2ecf20Sopenharmony_cistatic void __init x1830_cgu_init(struct device_node *np) 4398c2ecf20Sopenharmony_ci{ 4408c2ecf20Sopenharmony_ci int retval; 4418c2ecf20Sopenharmony_ci 4428c2ecf20Sopenharmony_ci cgu = ingenic_cgu_new(x1830_cgu_clocks, 4438c2ecf20Sopenharmony_ci ARRAY_SIZE(x1830_cgu_clocks), np); 4448c2ecf20Sopenharmony_ci if (!cgu) { 4458c2ecf20Sopenharmony_ci pr_err("%s: failed to initialise CGU\n", __func__); 4468c2ecf20Sopenharmony_ci return; 4478c2ecf20Sopenharmony_ci } 4488c2ecf20Sopenharmony_ci 4498c2ecf20Sopenharmony_ci retval = ingenic_cgu_register_clocks(cgu); 4508c2ecf20Sopenharmony_ci if (retval) { 4518c2ecf20Sopenharmony_ci pr_err("%s: failed to register CGU Clocks\n", __func__); 4528c2ecf20Sopenharmony_ci return; 4538c2ecf20Sopenharmony_ci } 4548c2ecf20Sopenharmony_ci 4558c2ecf20Sopenharmony_ci ingenic_cgu_register_syscore_ops(cgu); 4568c2ecf20Sopenharmony_ci} 4578c2ecf20Sopenharmony_ci/* 4588c2ecf20Sopenharmony_ci * CGU has some children devices, this is useful for probing children devices 4598c2ecf20Sopenharmony_ci * in the case where the device node is compatible with "simple-mfd". 4608c2ecf20Sopenharmony_ci */ 4618c2ecf20Sopenharmony_ciCLK_OF_DECLARE_DRIVER(x1830_cgu, "ingenic,x1830-cgu", x1830_cgu_init); 462