Linux Audio

Check our new training course

Loading...
Note: File does not exist in v4.17.
  1/*
  2 * arch/metag/kernel/clock.c
  3 *
  4 * Copyright (C) 2012 Imagination Technologies Ltd.
  5 *
  6 * This program is free software; you can redistribute it and/or modify
  7 * it under the terms of the GNU General Public License version 2 as
  8 * published by the Free Software Foundation.
  9 */
 10
 11#include <linux/clk.h>
 12#include <linux/delay.h>
 13#include <linux/io.h>
 14#include <linux/of.h>
 15
 16#include <asm/param.h>
 17#include <asm/clock.h>
 18
 19struct meta_clock_desc _meta_clock;
 20
 21/* Default machine get_core_freq callback. */
 22static unsigned long get_core_freq_default(void)
 23{
 24#ifdef CONFIG_METAG_META21
 25	/*
 26	 * Meta 2 cores divide down the core clock for the Meta timers, so we
 27	 * can estimate the core clock from the divider.
 28	 */
 29	return (metag_in32(EXPAND_TIMER_DIV) + 1) * 1000000;
 30#else
 31	/*
 32	 * On Meta 1 we don't know the core clock, but assuming the Meta timer
 33	 * is correct it can be estimated based on loops_per_jiffy.
 34	 */
 35	return (loops_per_jiffy * HZ * 5) >> 1;
 36#endif
 37}
 38
 39static struct clk *clk_core;
 40
 41/* Clk based get_core_freq callback. */
 42static unsigned long get_core_freq_clk(void)
 43{
 44	return clk_get_rate(clk_core);
 45}
 46
 47/**
 48 * init_metag_core_clock() - Set up core clock from devicetree.
 49 *
 50 * Checks to see if a "core" clock is provided in the device tree, and overrides
 51 * the get_core_freq callback to use it.
 52 */
 53static void __init init_metag_core_clock(void)
 54{
 55	/*
 56	 * See if a core clock is provided by the devicetree (and
 57	 * registered by the init callback above).
 58	 */
 59	struct device_node *node;
 60	node = of_find_compatible_node(NULL, NULL, "img,meta");
 61	if (!node) {
 62		pr_warn("%s: no compatible img,meta DT node found\n",
 63			__func__);
 64		return;
 65	}
 66
 67	clk_core = of_clk_get_by_name(node, "core");
 68	if (IS_ERR(clk_core)) {
 69		pr_warn("%s: no core clock found in DT\n",
 70			__func__);
 71		return;
 72	}
 73
 74	/*
 75	 * Override the core frequency callback to use
 76	 * this clk.
 77	 */
 78	_meta_clock.get_core_freq = get_core_freq_clk;
 79}
 80
 81/**
 82 * init_metag_clocks() - Set up clocks from devicetree.
 83 *
 84 * Set up important clocks from device tree. In particular any needed for clock
 85 * sources.
 86 */
 87void __init init_metag_clocks(void)
 88{
 89	init_metag_core_clock();
 90
 91	pr_info("Core clock frequency: %lu Hz\n", get_coreclock());
 92}
 93
 94/**
 95 * setup_meta_clocks() - Early set up of the Meta clock.
 96 * @desc:	Clock descriptor usually provided by machine description
 97 *
 98 * Ensures all callbacks are valid.
 99 */
100void __init setup_meta_clocks(struct meta_clock_desc *desc)
101{
102	/* copy callbacks */
103	if (desc)
104		_meta_clock = *desc;
105
106	/* set fallback functions */
107	if (!_meta_clock.get_core_freq)
108		_meta_clock.get_core_freq = get_core_freq_default;
109}
110