1#include <linux/clk.h> 2#include <linux/err.h> 3#include <linux/of.h> 4#include <linux/slab.h> 5#include <linux/spinlock.h> 6#include "clk.h" 7 8DEFINE_SPINLOCK(imx_ccm_lock); 9 10void __init imx_check_clocks(struct clk *clks[], unsigned int count) 11{ 12 unsigned i; 13 14 for (i = 0; i < count; i++) 15 if (IS_ERR(clks[i])) 16 pr_err("i.MX clk %u: register failed with %ld\n", 17 i, PTR_ERR(clks[i])); 18} 19 20static struct clk * __init imx_obtain_fixed_clock_from_dt(const char *name) 21{ 22 struct of_phandle_args phandle; 23 struct clk *clk = ERR_PTR(-ENODEV); 24 char *path; 25 26 path = kasprintf(GFP_KERNEL, "/clocks/%s", name); 27 if (!path) 28 return ERR_PTR(-ENOMEM); 29 30 phandle.np = of_find_node_by_path(path); 31 kfree(path); 32 33 if (phandle.np) { 34 clk = of_clk_get_from_provider(&phandle); 35 of_node_put(phandle.np); 36 } 37 return clk; 38} 39 40struct clk * __init imx_obtain_fixed_clock( 41 const char *name, unsigned long rate) 42{ 43 struct clk *clk; 44 45 clk = imx_obtain_fixed_clock_from_dt(name); 46 if (IS_ERR(clk)) 47 clk = imx_clk_fixed(name, rate); 48 return clk; 49} 50 51/* 52 * This fixups the register CCM_CSCMR1 write value. 53 * The write/read/divider values of the aclk_podf field 54 * of that register have the relationship described by 55 * the following table: 56 * 57 * write value read value divider 58 * 3b'000 3b'110 7 59 * 3b'001 3b'111 8 60 * 3b'010 3b'100 5 61 * 3b'011 3b'101 6 62 * 3b'100 3b'010 3 63 * 3b'101 3b'011 4 64 * 3b'110 3b'000 1 65 * 3b'111 3b'001 2(default) 66 * 67 * That's why we do the xor operation below. 68 */ 69#define CSCMR1_FIXUP 0x00600000 70 71void imx_cscmr1_fixup(u32 *val) 72{ 73 *val ^= CSCMR1_FIXUP; 74 return; 75} 76