1/* 2 * linux/arch/arm/mach-sa1100/clock.c 3 */ 4#include <linux/module.h> 5#include <linux/kernel.h> 6#include <linux/list.h> 7#include <linux/errno.h> 8#include <linux/err.h> 9#include <linux/string.h> 10#include <linux/clk.h> 11#include <linux/spinlock.h> 12#include <linux/platform_device.h> 13#include <linux/delay.h> 14 15#include <asm/clkdev.h> 16#include <mach/pxa2xx-regs.h> 17#include <mach/hardware.h> 18 19#include "devices.h" 20#include "generic.h" 21#include "clock.h" 22 23static DEFINE_SPINLOCK(clocks_lock); 24 25int clk_enable(struct clk *clk) 26{ 27 unsigned long flags; 28 29 spin_lock_irqsave(&clocks_lock, flags); 30 if (clk->enabled++ == 0) 31 clk->ops->enable(clk); 32 spin_unlock_irqrestore(&clocks_lock, flags); 33 34 if (clk->delay) 35 udelay(clk->delay); 36 37 return 0; 38} 39EXPORT_SYMBOL(clk_enable); 40 41void clk_disable(struct clk *clk) 42{ 43 unsigned long flags; 44 45 WARN_ON(clk->enabled == 0); 46 47 spin_lock_irqsave(&clocks_lock, flags); 48 if (--clk->enabled == 0) 49 clk->ops->disable(clk); 50 spin_unlock_irqrestore(&clocks_lock, flags); 51} 52EXPORT_SYMBOL(clk_disable); 53 54unsigned long clk_get_rate(struct clk *clk) 55{ 56 unsigned long rate; 57 58 rate = clk->rate; 59 if (clk->ops->getrate) 60 rate = clk->ops->getrate(clk); 61 62 return rate; 63} 64EXPORT_SYMBOL(clk_get_rate); 65 66 67void clk_cken_enable(struct clk *clk) 68{ 69 CKEN |= 1 << clk->cken; 70} 71 72void clk_cken_disable(struct clk *clk) 73{ 74 CKEN &= ~(1 << clk->cken); 75} 76 77const struct clkops clk_cken_ops = { 78 .enable = clk_cken_enable, 79 .disable = clk_cken_disable, 80}; 81 82void clks_register(struct clk_lookup *clks, size_t num) 83{ 84 int i; 85 86 for (i = 0; i < num; i++) 87 clkdev_add(&clks[i]); 88} 89