Linux Audio

Check our new training course

Loading...
Note: File does not exist in v5.14.15.
  1/*
  2 *  linux/arch/arm/mach-mmp/clock.c
  3 *
  4 *  This program is free software; you can redistribute it and/or modify
  5 *  it under the terms of the GNU General Public License version 2 as
  6 *  published by the Free Software Foundation.
  7 */
  8
  9#include <linux/module.h>
 10#include <linux/kernel.h>
 11#include <linux/list.h>
 12#include <linux/spinlock.h>
 13#include <linux/clk.h>
 14#include <linux/io.h>
 15
 16#include <mach/regs-apbc.h>
 17#include "clock.h"
 18
 19static void apbc_clk_enable(struct clk *clk)
 20{
 21	uint32_t clk_rst;
 22
 23	clk_rst = APBC_APBCLK | APBC_FNCLK | APBC_FNCLKSEL(clk->fnclksel);
 24	__raw_writel(clk_rst, clk->clk_rst);
 25}
 26
 27static void apbc_clk_disable(struct clk *clk)
 28{
 29	__raw_writel(0, clk->clk_rst);
 30}
 31
 32struct clkops apbc_clk_ops = {
 33	.enable		= apbc_clk_enable,
 34	.disable	= apbc_clk_disable,
 35};
 36
 37static void apmu_clk_enable(struct clk *clk)
 38{
 39	__raw_writel(clk->enable_val, clk->clk_rst);
 40}
 41
 42static void apmu_clk_disable(struct clk *clk)
 43{
 44	__raw_writel(0, clk->clk_rst);
 45}
 46
 47struct clkops apmu_clk_ops = {
 48	.enable		= apmu_clk_enable,
 49	.disable	= apmu_clk_disable,
 50};
 51
 52static DEFINE_SPINLOCK(clocks_lock);
 53
 54int clk_enable(struct clk *clk)
 55{
 56	unsigned long flags;
 57
 58	spin_lock_irqsave(&clocks_lock, flags);
 59	if (clk->enabled++ == 0)
 60		clk->ops->enable(clk);
 61	spin_unlock_irqrestore(&clocks_lock, flags);
 62	return 0;
 63}
 64EXPORT_SYMBOL(clk_enable);
 65
 66void clk_disable(struct clk *clk)
 67{
 68	unsigned long flags;
 69
 70	WARN_ON(clk->enabled == 0);
 71
 72	spin_lock_irqsave(&clocks_lock, flags);
 73	if (--clk->enabled == 0)
 74		clk->ops->disable(clk);
 75	spin_unlock_irqrestore(&clocks_lock, flags);
 76}
 77EXPORT_SYMBOL(clk_disable);
 78
 79unsigned long clk_get_rate(struct clk *clk)
 80{
 81	unsigned long rate;
 82
 83	if (clk->ops->getrate)
 84		rate = clk->ops->getrate(clk);
 85	else
 86		rate = clk->rate;
 87
 88	return rate;
 89}
 90EXPORT_SYMBOL(clk_get_rate);
 91
 92int clk_set_rate(struct clk *clk, unsigned long rate)
 93{
 94	unsigned long flags;
 95	int ret = -EINVAL;
 96
 97	if (clk->ops->setrate) {
 98		spin_lock_irqsave(&clocks_lock, flags);
 99		ret = clk->ops->setrate(clk, rate);
100		spin_unlock_irqrestore(&clocks_lock, flags);
101	}
102
103	return ret;
104}
105EXPORT_SYMBOL(clk_set_rate);