Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 146730
b: refs/heads/master
c: 4f5ecaa
h: refs/heads/master
v: v3
  • Loading branch information
Magnus Damm authored and Paul Mundt committed May 8, 2009
1 parent dca3f09 commit 16a314d
Show file tree
Hide file tree
Showing 3 changed files with 40 additions and 35 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 7d170b1bc540a1d83098a9f27cf4939e026fda81
refs/heads/master: 4f5ecaa05493dfddf155b40224b951592bfce325
4 changes: 2 additions & 2 deletions trunk/arch/sh/include/asm/clock.h
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
#ifndef __ASM_SH_CLOCK_H
#define __ASM_SH_CLOCK_H

#include <linux/kref.h>
#include <linux/list.h>
#include <linux/seq_file.h>
#include <linux/clk.h>
Expand All @@ -28,7 +27,7 @@ struct clk {
struct clk *parent;
struct clk_ops *ops;

struct kref kref;
int usecount;

unsigned long rate;
unsigned long flags;
Expand All @@ -37,6 +36,7 @@ struct clk {

#define CLK_ALWAYS_ENABLED (1 << 0)
#define CLK_RATE_PROPAGATES (1 << 1)
#define CLK_NEEDS_INIT (1 << 2)

/* Should be defined by processor-specific code */
void arch_init_clk_ops(struct clk_ops **, int type);
Expand Down
69 changes: 37 additions & 32 deletions trunk/arch/sh/kernel/cpu/clock.c
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,6 @@
#include <linux/module.h>
#include <linux/mutex.h>
#include <linux/list.h>
#include <linux/kref.h>
#include <linux/kobject.h>
#include <linux/sysdev.h>
#include <linux/seq_file.h>
Expand Down Expand Up @@ -90,7 +89,7 @@ static void propagate_rate(struct clk *clk)
}
}

static int __clk_enable(struct clk *clk)
static void __clk_init(struct clk *clk)
{
/*
* See if this is the first time we're enabling the clock, some
Expand All @@ -100,19 +99,33 @@ static int __clk_enable(struct clk *clk)
* divisors to use before it can effectively recalc.
*/

if (clk->flags & CLK_ALWAYS_ENABLED) {
kref_get(&clk->kref);
return 0;
}

if (unlikely(atomic_read(&clk->kref.refcount) == 1))
if (clk->flags & CLK_NEEDS_INIT) {
if (clk->ops && clk->ops->init)
clk->ops->init(clk);

kref_get(&clk->kref);
clk->flags &= ~CLK_NEEDS_INIT;
}
}

static int __clk_enable(struct clk *clk)
{
if (!clk)
return -EINVAL;

clk->usecount++;

/* nothing to do if always enabled */
if (clk->flags & CLK_ALWAYS_ENABLED)
return 0;

if (clk->usecount == 1) {
__clk_init(clk);

if (likely(clk->ops && clk->ops->enable))
clk->ops->enable(clk);
__clk_enable(clk->parent);

if (clk->ops && clk->ops->enable)
clk->ops->enable(clk);
}

return 0;
}
Expand All @@ -122,11 +135,6 @@ int clk_enable(struct clk *clk)
unsigned long flags;
int ret;

if (!clk)
return -EINVAL;

clk_enable(clk->parent);

spin_lock_irqsave(&clock_lock, flags);
ret = __clk_enable(clk);
spin_unlock_irqrestore(&clock_lock, flags);
Expand All @@ -135,36 +143,33 @@ int clk_enable(struct clk *clk)
}
EXPORT_SYMBOL_GPL(clk_enable);

static void clk_kref_release(struct kref *kref)
{
/* Nothing to do */
}

static void __clk_disable(struct clk *clk)
{
int count = kref_put(&clk->kref, clk_kref_release);
if (!clk)
return;

clk->usecount--;

WARN_ON(clk->usecount < 0);

if (clk->flags & CLK_ALWAYS_ENABLED)
return;

if (!count) { /* count reaches zero, disable the clock */
if (clk->usecount == 0) {
if (likely(clk->ops && clk->ops->disable))
clk->ops->disable(clk);

__clk_disable(clk->parent);
}
}

void clk_disable(struct clk *clk)
{
unsigned long flags;

if (!clk)
return;

spin_lock_irqsave(&clock_lock, flags);
__clk_disable(clk);
spin_unlock_irqrestore(&clock_lock, flags);

clk_disable(clk->parent);
}
EXPORT_SYMBOL_GPL(clk_disable);

Expand All @@ -173,14 +178,14 @@ int clk_register(struct clk *clk)
mutex_lock(&clock_list_sem);

list_add(&clk->node, &clock_list);
kref_init(&clk->kref);
clk->usecount = 0;
clk->flags |= CLK_NEEDS_INIT;

mutex_unlock(&clock_list_sem);

if (clk->flags & CLK_ALWAYS_ENABLED) {
__clk_init(clk);
pr_debug( "Clock '%s' is ALWAYS_ENABLED\n", clk->name);
if (clk->ops && clk->ops->init)
clk->ops->init(clk);
if (clk->ops && clk->ops->enable)
clk->ops->enable(clk);
pr_debug( "Enabled.");
Expand Down Expand Up @@ -356,7 +361,7 @@ static int show_clocks(char *buf, char **start, off_t off,
p += sprintf(p, "%-12s\t: %ld.%02ldMHz\t%s\n", clk->name,
rate / 1000000, (rate % 1000000) / 10000,
((clk->flags & CLK_ALWAYS_ENABLED) ||
(atomic_read(&clk->kref.refcount) != 1)) ?
clk->usecount > 0) ?
"enabled" : "disabled");
}

Expand Down

0 comments on commit 16a314d

Please sign in to comment.