1 /* SPDX-License-Identifier: GPL-2.0 */ 2 #ifndef __MACH_IMX_CLK_H 3 #define __MACH_IMX_CLK_H 4 5 #include <linux/spinlock.h> 6 #include <linux/clk-provider.h> 7 8 extern spinlock_t imx_ccm_lock; 9 10 void imx_check_clocks(struct clk *clks[], unsigned int count); 11 void imx_check_clk_hws(struct clk_hw *clks[], unsigned int count); 12 void imx_register_uart_clocks(struct clk ** const clks[]); 13 14 extern void imx_cscmr1_fixup(u32 *val); 15 16 enum imx_pllv1_type { 17 IMX_PLLV1_IMX1, 18 IMX_PLLV1_IMX21, 19 IMX_PLLV1_IMX25, 20 IMX_PLLV1_IMX27, 21 IMX_PLLV1_IMX31, 22 IMX_PLLV1_IMX35, 23 }; 24 25 enum imx_sccg_pll_type { 26 SCCG_PLL1, 27 SCCG_PLL2, 28 }; 29 30 enum imx_pll14xx_type { 31 PLL_1416X, 32 PLL_1443X, 33 }; 34 35 /* NOTE: Rate table should be kept sorted in descending order. */ 36 struct imx_pll14xx_rate_table { 37 unsigned int rate; 38 unsigned int pdiv; 39 unsigned int mdiv; 40 unsigned int sdiv; 41 unsigned int kdiv; 42 }; 43 44 struct imx_pll14xx_clk { 45 enum imx_pll14xx_type type; 46 const struct imx_pll14xx_rate_table *rate_table; 47 int rate_count; 48 int flags; 49 }; 50 51 struct clk *imx_clk_pll14xx(const char *name, const char *parent_name, 52 void __iomem *base, const struct imx_pll14xx_clk *pll_clk); 53 54 struct clk *imx_clk_pllv1(enum imx_pllv1_type type, const char *name, 55 const char *parent, void __iomem *base); 56 57 struct clk *imx_clk_pllv2(const char *name, const char *parent, 58 void __iomem *base); 59 60 struct clk *imx_clk_frac_pll(const char *name, const char *parent_name, 61 void __iomem *base); 62 63 struct clk *imx_clk_sccg_pll(const char *name, 64 const char * const *parent_names, 65 u8 num_parents, 66 u8 parent, u8 bypass1, u8 bypass2, 67 void __iomem *base, 68 unsigned long flags); 69 70 enum imx_pllv3_type { 71 IMX_PLLV3_GENERIC, 72 IMX_PLLV3_SYS, 73 IMX_PLLV3_USB, 74 IMX_PLLV3_USB_VF610, 75 IMX_PLLV3_AV, 76 IMX_PLLV3_ENET, 77 IMX_PLLV3_ENET_IMX7, 78 IMX_PLLV3_SYS_VF610, 79 IMX_PLLV3_DDR_IMX7, 80 IMX_PLLV3_AV_IMX7, 81 }; 82 83 struct clk *imx_clk_pllv3(enum imx_pllv3_type type, const char *name, 84 const char *parent_name, void __iomem *base, u32 div_mask); 85 86 struct clk_hw *imx_clk_pllv4(const char *name, const char *parent_name, 87 void __iomem *base); 88 89 struct clk *clk_register_gate2(struct device *dev, const char *name, 90 const char *parent_name, unsigned long flags, 91 void __iomem *reg, u8 bit_idx, u8 cgr_val, 92 u8 clk_gate_flags, spinlock_t *lock, 93 unsigned int *share_count); 94 95 struct clk * imx_obtain_fixed_clock( 96 const char *name, unsigned long rate); 97 98 struct clk_hw *imx_obtain_fixed_clk_hw(struct device_node *np, 99 const char *name); 100 101 struct clk *imx_clk_gate_exclusive(const char *name, const char *parent, 102 void __iomem *reg, u8 shift, u32 exclusive_mask); 103 104 struct clk *imx_clk_pfd(const char *name, const char *parent_name, 105 void __iomem *reg, u8 idx); 106 107 struct clk_hw *imx_clk_pfdv2(const char *name, const char *parent_name, 108 void __iomem *reg, u8 idx); 109 110 struct clk *imx_clk_busy_divider(const char *name, const char *parent_name, 111 void __iomem *reg, u8 shift, u8 width, 112 void __iomem *busy_reg, u8 busy_shift); 113 114 struct clk *imx_clk_busy_mux(const char *name, void __iomem *reg, u8 shift, 115 u8 width, void __iomem *busy_reg, u8 busy_shift, 116 const char * const *parent_names, int num_parents); 117 118 struct clk_hw *imx7ulp_clk_composite(const char *name, 119 const char * const *parent_names, 120 int num_parents, bool mux_present, 121 bool rate_present, bool gate_present, 122 void __iomem *reg); 123 124 struct clk *imx_clk_fixup_divider(const char *name, const char *parent, 125 void __iomem *reg, u8 shift, u8 width, 126 void (*fixup)(u32 *val)); 127 128 struct clk *imx_clk_fixup_mux(const char *name, void __iomem *reg, 129 u8 shift, u8 width, const char * const *parents, 130 int num_parents, void (*fixup)(u32 *val)); 131 132 static inline struct clk *imx_clk_fixed(const char *name, int rate) 133 { 134 return clk_register_fixed_rate(NULL, name, NULL, 0, rate); 135 } 136 137 static inline struct clk_hw *imx_clk_hw_fixed(const char *name, int rate) 138 { 139 return clk_hw_register_fixed_rate(NULL, name, NULL, 0, rate); 140 } 141 142 static inline struct clk *imx_clk_mux_ldb(const char *name, void __iomem *reg, 143 u8 shift, u8 width, const char * const *parents, 144 int num_parents) 145 { 146 return clk_register_mux(NULL, name, parents, num_parents, 147 CLK_SET_RATE_NO_REPARENT | CLK_SET_RATE_PARENT, reg, 148 shift, width, CLK_MUX_READ_ONLY, &imx_ccm_lock); 149 } 150 151 static inline struct clk *imx_clk_fixed_factor(const char *name, 152 const char *parent, unsigned int mult, unsigned int div) 153 { 154 return clk_register_fixed_factor(NULL, name, parent, 155 CLK_SET_RATE_PARENT, mult, div); 156 } 157 158 static inline struct clk *imx_clk_divider(const char *name, const char *parent, 159 void __iomem *reg, u8 shift, u8 width) 160 { 161 return clk_register_divider(NULL, name, parent, CLK_SET_RATE_PARENT, 162 reg, shift, width, 0, &imx_ccm_lock); 163 } 164 165 static inline struct clk_hw *imx_clk_hw_divider(const char *name, 166 const char *parent, 167 void __iomem *reg, u8 shift, 168 u8 width) 169 { 170 return clk_hw_register_divider(NULL, name, parent, CLK_SET_RATE_PARENT, 171 reg, shift, width, 0, &imx_ccm_lock); 172 } 173 174 static inline struct clk *imx_clk_divider_flags(const char *name, 175 const char *parent, void __iomem *reg, u8 shift, u8 width, 176 unsigned long flags) 177 { 178 return clk_register_divider(NULL, name, parent, flags, 179 reg, shift, width, 0, &imx_ccm_lock); 180 } 181 182 static inline struct clk_hw *imx_clk_hw_divider_flags(const char *name, 183 const char *parent, 184 void __iomem *reg, u8 shift, 185 u8 width, unsigned long flags) 186 { 187 return clk_hw_register_divider(NULL, name, parent, flags, 188 reg, shift, width, 0, &imx_ccm_lock); 189 } 190 191 static inline struct clk *imx_clk_divider2(const char *name, const char *parent, 192 void __iomem *reg, u8 shift, u8 width) 193 { 194 return clk_register_divider(NULL, name, parent, 195 CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE, 196 reg, shift, width, 0, &imx_ccm_lock); 197 } 198 199 static inline struct clk *imx_clk_divider2_flags(const char *name, 200 const char *parent, void __iomem *reg, u8 shift, u8 width, 201 unsigned long flags) 202 { 203 return clk_register_divider(NULL, name, parent, 204 flags | CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE, 205 reg, shift, width, 0, &imx_ccm_lock); 206 } 207 208 static inline struct clk *imx_clk_gate(const char *name, const char *parent, 209 void __iomem *reg, u8 shift) 210 { 211 return clk_register_gate(NULL, name, parent, CLK_SET_RATE_PARENT, reg, 212 shift, 0, &imx_ccm_lock); 213 } 214 215 static inline struct clk *imx_clk_gate_flags(const char *name, const char *parent, 216 void __iomem *reg, u8 shift, unsigned long flags) 217 { 218 return clk_register_gate(NULL, name, parent, flags | CLK_SET_RATE_PARENT, reg, 219 shift, 0, &imx_ccm_lock); 220 } 221 222 static inline struct clk_hw *imx_clk_hw_gate(const char *name, const char *parent, 223 void __iomem *reg, u8 shift) 224 { 225 return clk_hw_register_gate(NULL, name, parent, CLK_SET_RATE_PARENT, reg, 226 shift, 0, &imx_ccm_lock); 227 } 228 229 static inline struct clk *imx_clk_gate_dis(const char *name, const char *parent, 230 void __iomem *reg, u8 shift) 231 { 232 return clk_register_gate(NULL, name, parent, CLK_SET_RATE_PARENT, reg, 233 shift, CLK_GATE_SET_TO_DISABLE, &imx_ccm_lock); 234 } 235 236 static inline struct clk *imx_clk_gate_dis_flags(const char *name, const char *parent, 237 void __iomem *reg, u8 shift, unsigned long flags) 238 { 239 return clk_register_gate(NULL, name, parent, flags | CLK_SET_RATE_PARENT, reg, 240 shift, CLK_GATE_SET_TO_DISABLE, &imx_ccm_lock); 241 } 242 243 static inline struct clk *imx_clk_gate2(const char *name, const char *parent, 244 void __iomem *reg, u8 shift) 245 { 246 return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT, reg, 247 shift, 0x3, 0, &imx_ccm_lock, NULL); 248 } 249 250 static inline struct clk *imx_clk_gate2_flags(const char *name, const char *parent, 251 void __iomem *reg, u8 shift, unsigned long flags) 252 { 253 return clk_register_gate2(NULL, name, parent, flags | CLK_SET_RATE_PARENT, reg, 254 shift, 0x3, 0, &imx_ccm_lock, NULL); 255 } 256 257 static inline struct clk *imx_clk_gate2_shared(const char *name, 258 const char *parent, void __iomem *reg, u8 shift, 259 unsigned int *share_count) 260 { 261 return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT, reg, 262 shift, 0x3, 0, &imx_ccm_lock, share_count); 263 } 264 265 static inline struct clk *imx_clk_gate2_shared2(const char *name, 266 const char *parent, void __iomem *reg, u8 shift, 267 unsigned int *share_count) 268 { 269 return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT | 270 CLK_OPS_PARENT_ENABLE, reg, shift, 0x3, 0, 271 &imx_ccm_lock, share_count); 272 } 273 274 static inline struct clk *imx_clk_gate2_cgr(const char *name, 275 const char *parent, void __iomem *reg, u8 shift, u8 cgr_val) 276 { 277 return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT, reg, 278 shift, cgr_val, 0, &imx_ccm_lock, NULL); 279 } 280 281 static inline struct clk *imx_clk_gate3(const char *name, const char *parent, 282 void __iomem *reg, u8 shift) 283 { 284 return clk_register_gate(NULL, name, parent, 285 CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE, 286 reg, shift, 0, &imx_ccm_lock); 287 } 288 289 static inline struct clk *imx_clk_gate3_flags(const char *name, 290 const char *parent, void __iomem *reg, u8 shift, 291 unsigned long flags) 292 { 293 return clk_register_gate(NULL, name, parent, 294 flags | CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE, 295 reg, shift, 0, &imx_ccm_lock); 296 } 297 298 static inline struct clk *imx_clk_gate4(const char *name, const char *parent, 299 void __iomem *reg, u8 shift) 300 { 301 return clk_register_gate2(NULL, name, parent, 302 CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE, 303 reg, shift, 0x3, 0, &imx_ccm_lock, NULL); 304 } 305 306 static inline struct clk *imx_clk_gate4_flags(const char *name, 307 const char *parent, void __iomem *reg, u8 shift, 308 unsigned long flags) 309 { 310 return clk_register_gate2(NULL, name, parent, 311 flags | CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE, 312 reg, shift, 0x3, 0, &imx_ccm_lock, NULL); 313 } 314 315 static inline struct clk *imx_clk_mux(const char *name, void __iomem *reg, 316 u8 shift, u8 width, const char * const *parents, 317 int num_parents) 318 { 319 return clk_register_mux(NULL, name, parents, num_parents, 320 CLK_SET_RATE_NO_REPARENT, reg, shift, 321 width, 0, &imx_ccm_lock); 322 } 323 324 static inline struct clk *imx_clk_mux2(const char *name, void __iomem *reg, 325 u8 shift, u8 width, const char * const *parents, 326 int num_parents) 327 { 328 return clk_register_mux(NULL, name, parents, num_parents, 329 CLK_SET_RATE_NO_REPARENT | CLK_OPS_PARENT_ENABLE, 330 reg, shift, width, 0, &imx_ccm_lock); 331 } 332 333 static inline struct clk_hw *imx_clk_hw_mux2(const char *name, void __iomem *reg, 334 u8 shift, u8 width, 335 const char * const *parents, 336 int num_parents) 337 { 338 return clk_hw_register_mux(NULL, name, parents, num_parents, 339 CLK_SET_RATE_NO_REPARENT | 340 CLK_OPS_PARENT_ENABLE, 341 reg, shift, width, 0, &imx_ccm_lock); 342 } 343 344 static inline struct clk *imx_clk_mux_flags(const char *name, 345 void __iomem *reg, u8 shift, u8 width, 346 const char * const *parents, int num_parents, 347 unsigned long flags) 348 { 349 return clk_register_mux(NULL, name, parents, num_parents, 350 flags | CLK_SET_RATE_NO_REPARENT, reg, shift, width, 0, 351 &imx_ccm_lock); 352 } 353 354 static inline struct clk *imx_clk_mux2_flags(const char *name, 355 void __iomem *reg, u8 shift, u8 width, 356 const char * const *parents, 357 int num_parents, unsigned long flags) 358 { 359 return clk_register_mux(NULL, name, parents, num_parents, 360 flags | CLK_SET_RATE_NO_REPARENT | CLK_OPS_PARENT_ENABLE, 361 reg, shift, width, 0, &imx_ccm_lock); 362 } 363 364 static inline struct clk_hw *imx_clk_hw_mux_flags(const char *name, 365 void __iomem *reg, u8 shift, 366 u8 width, 367 const char * const *parents, 368 int num_parents, 369 unsigned long flags) 370 { 371 return clk_hw_register_mux(NULL, name, parents, num_parents, 372 flags | CLK_SET_RATE_NO_REPARENT, 373 reg, shift, width, 0, &imx_ccm_lock); 374 } 375 376 struct clk *imx_clk_cpu(const char *name, const char *parent_name, 377 struct clk *div, struct clk *mux, struct clk *pll, 378 struct clk *step); 379 380 struct clk *imx8m_clk_composite_flags(const char *name, 381 const char * const *parent_names, 382 int num_parents, void __iomem *reg, 383 unsigned long flags); 384 385 #define __imx8m_clk_composite(name, parent_names, reg, flags) \ 386 imx8m_clk_composite_flags(name, parent_names, \ 387 ARRAY_SIZE(parent_names), reg, \ 388 flags | CLK_SET_RATE_NO_REPARENT | CLK_OPS_PARENT_ENABLE) 389 390 #define imx8m_clk_composite(name, parent_names, reg) \ 391 __imx8m_clk_composite(name, parent_names, reg, 0) 392 393 #define imx8m_clk_composite_critical(name, parent_names, reg) \ 394 __imx8m_clk_composite(name, parent_names, reg, CLK_IS_CRITICAL) 395 396 struct clk_hw *imx_clk_divider_gate(const char *name, const char *parent_name, 397 unsigned long flags, void __iomem *reg, u8 shift, u8 width, 398 u8 clk_divider_flags, const struct clk_div_table *table, 399 spinlock_t *lock); 400 #endif 401