1d861196163e30c07add471562b45dce38517c9b2Colin Cross/*
2d861196163e30c07add471562b45dce38517c9b2Colin Cross * arch/arm/mach-tegra/tegra2_clocks.c
3d861196163e30c07add471562b45dce38517c9b2Colin Cross *
4d861196163e30c07add471562b45dce38517c9b2Colin Cross * Copyright (C) 2010 Google, Inc.
5d861196163e30c07add471562b45dce38517c9b2Colin Cross *
6d861196163e30c07add471562b45dce38517c9b2Colin Cross * Author:
7d861196163e30c07add471562b45dce38517c9b2Colin Cross *	Colin Cross <ccross@google.com>
8d861196163e30c07add471562b45dce38517c9b2Colin Cross *
9d861196163e30c07add471562b45dce38517c9b2Colin Cross * This software is licensed under the terms of the GNU General Public
10d861196163e30c07add471562b45dce38517c9b2Colin Cross * License version 2, as published by the Free Software Foundation, and
11d861196163e30c07add471562b45dce38517c9b2Colin Cross * may be copied, distributed, and modified under those terms.
12d861196163e30c07add471562b45dce38517c9b2Colin Cross *
13d861196163e30c07add471562b45dce38517c9b2Colin Cross * This program is distributed in the hope that it will be useful,
14d861196163e30c07add471562b45dce38517c9b2Colin Cross * but WITHOUT ANY WARRANTY; without even the implied warranty of
15d861196163e30c07add471562b45dce38517c9b2Colin Cross * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16d861196163e30c07add471562b45dce38517c9b2Colin Cross * GNU General Public License for more details.
17d861196163e30c07add471562b45dce38517c9b2Colin Cross *
18d861196163e30c07add471562b45dce38517c9b2Colin Cross */
19d861196163e30c07add471562b45dce38517c9b2Colin Cross
20d861196163e30c07add471562b45dce38517c9b2Colin Cross#include <linux/kernel.h>
21d861196163e30c07add471562b45dce38517c9b2Colin Cross#include <linux/module.h>
22d861196163e30c07add471562b45dce38517c9b2Colin Cross#include <linux/list.h>
23d861196163e30c07add471562b45dce38517c9b2Colin Cross#include <linux/spinlock.h>
24d861196163e30c07add471562b45dce38517c9b2Colin Cross#include <linux/delay.h>
25d861196163e30c07add471562b45dce38517c9b2Colin Cross#include <linux/io.h>
266d803ba736abb5e122dede70a4720e4843dd6df4Jean-Christop PLAGNIOL-VILLARD#include <linux/clkdev.h>
274729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross#include <linux/clk.h>
28d861196163e30c07add471562b45dce38517c9b2Colin Cross
29d861196163e30c07add471562b45dce38517c9b2Colin Cross#include <mach/iomap.h>
302ea67fd145397c1409ffc85b2210ccf7ef69a183Colin Cross#include <mach/suspend.h>
31d861196163e30c07add471562b45dce38517c9b2Colin Cross
32d861196163e30c07add471562b45dce38517c9b2Colin Cross#include "clock.h"
3371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#include "fuse.h"
346d2968284f63efa1d1849165f9e3a80402509212Colin Cross#include "tegra2_emc.h"
35d861196163e30c07add471562b45dce38517c9b2Colin Cross
36d861196163e30c07add471562b45dce38517c9b2Colin Cross#define RST_DEVICES			0x004
37d861196163e30c07add471562b45dce38517c9b2Colin Cross#define RST_DEVICES_SET			0x300
38d861196163e30c07add471562b45dce38517c9b2Colin Cross#define RST_DEVICES_CLR			0x304
3971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define RST_DEVICES_NUM			3
40d861196163e30c07add471562b45dce38517c9b2Colin Cross
41d861196163e30c07add471562b45dce38517c9b2Colin Cross#define CLK_OUT_ENB			0x010
42d861196163e30c07add471562b45dce38517c9b2Colin Cross#define CLK_OUT_ENB_SET			0x320
43d861196163e30c07add471562b45dce38517c9b2Colin Cross#define CLK_OUT_ENB_CLR			0x324
4471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define CLK_OUT_ENB_NUM			3
4571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
4671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define CLK_MASK_ARM			0x44
4771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define MISC_CLK_ENB			0x48
48d861196163e30c07add471562b45dce38517c9b2Colin Cross
49d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_CTRL			0x50
50d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_CTRL_OSC_FREQ_MASK		(3<<30)
51d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_CTRL_OSC_FREQ_13MHZ		(0<<30)
52d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_CTRL_OSC_FREQ_19_2MHZ	(1<<30)
53d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_CTRL_OSC_FREQ_12MHZ		(2<<30)
54d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_CTRL_OSC_FREQ_26MHZ		(3<<30)
55cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define OSC_CTRL_MASK			(0x3f2 | OSC_CTRL_OSC_FREQ_MASK)
56d861196163e30c07add471562b45dce38517c9b2Colin Cross
57d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_FREQ_DET			0x58
58d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_FREQ_DET_TRIG		(1<<31)
59d861196163e30c07add471562b45dce38517c9b2Colin Cross
60d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_FREQ_DET_STATUS		0x5C
61d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_FREQ_DET_BUSY		(1<<31)
62d861196163e30c07add471562b45dce38517c9b2Colin Cross#define OSC_FREQ_DET_CNT_MASK		0xFFFF
63d861196163e30c07add471562b45dce38517c9b2Colin Cross
6471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define PERIPH_CLK_SOURCE_I2S1		0x100
6571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define PERIPH_CLK_SOURCE_EMC		0x19c
6671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define PERIPH_CLK_SOURCE_OSC		0x1fc
6771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define PERIPH_CLK_SOURCE_NUM \
6871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	((PERIPH_CLK_SOURCE_OSC - PERIPH_CLK_SOURCE_I2S1) / 4)
6971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
70d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PERIPH_CLK_SOURCE_MASK		(3<<30)
71d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PERIPH_CLK_SOURCE_SHIFT		30
72d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PERIPH_CLK_SOURCE_ENABLE	(1<<28)
7371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define PERIPH_CLK_SOURCE_DIVU71_MASK	0xFF
7471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define PERIPH_CLK_SOURCE_DIVU16_MASK	0xFFFF
75d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PERIPH_CLK_SOURCE_DIV_SHIFT	0
76d861196163e30c07add471562b45dce38517c9b2Colin Cross
779743b38969790d33b077ab80b175ea63a0398703Colin Cross#define SDMMC_CLK_INT_FB_SEL		(1 << 23)
789743b38969790d33b077ab80b175ea63a0398703Colin Cross#define SDMMC_CLK_INT_FB_DLY_SHIFT	16
799743b38969790d33b077ab80b175ea63a0398703Colin Cross#define SDMMC_CLK_INT_FB_DLY_MASK	(0xF << SDMMC_CLK_INT_FB_DLY_SHIFT)
809743b38969790d33b077ab80b175ea63a0398703Colin Cross
81d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE			0x0
82d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_BYPASS			(1<<31)
83d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_ENABLE			(1<<30)
84d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_REF_ENABLE		(1<<29)
85d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_OVERRIDE		(1<<28)
86d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_DIVP_MASK		(0x7<<20)
87d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_DIVP_SHIFT		20
88d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_DIVN_MASK		(0x3FF<<8)
89d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_DIVN_SHIFT		8
90d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_DIVM_MASK		(0x1F)
91d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_BASE_DIVM_SHIFT		0
92d861196163e30c07add471562b45dce38517c9b2Colin Cross
93d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_OUT_RATIO_MASK		(0xFF<<8)
94d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_OUT_RATIO_SHIFT		8
95d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_OUT_OVERRIDE		(1<<2)
96d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_OUT_CLKEN			(1<<1)
97d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_OUT_RESET_DISABLE		(1<<0)
98d861196163e30c07add471562b45dce38517c9b2Colin Cross
99d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_MISC(c)			(((c)->flags & PLL_ALT_MISC_REG) ? 0x4 : 0xc)
10071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
101d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_MISC_DCCON_SHIFT		20
102d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_MISC_CPCON_SHIFT		8
103d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_MISC_CPCON_MASK		(0xF<<PLL_MISC_CPCON_SHIFT)
104d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_MISC_LFCON_SHIFT		4
105d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_MISC_LFCON_MASK		(0xF<<PLL_MISC_LFCON_SHIFT)
106d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_MISC_VCOCON_SHIFT		0
107d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLL_MISC_VCOCON_MASK		(0xF<<PLL_MISC_VCOCON_SHIFT)
108d861196163e30c07add471562b45dce38517c9b2Colin Cross
10971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define PLLU_BASE_POST_DIV		(1<<20)
11071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
111d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLLD_MISC_CLKENABLE		(1<<30)
112d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLLD_MISC_DIV_RST		(1<<23)
113d861196163e30c07add471562b45dce38517c9b2Colin Cross#define PLLD_MISC_DCCON_SHIFT		12
114d861196163e30c07add471562b45dce38517c9b2Colin Cross
1158d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport#define PLLE_MISC_READY			(1 << 15)
1168d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
117f151961173bf28047d01b410969f05e485f56d7eColin Cross#define PERIPH_CLK_TO_ENB_REG(c)	((c->u.periph.clk_num / 32) * 4)
118f151961173bf28047d01b410969f05e485f56d7eColin Cross#define PERIPH_CLK_TO_ENB_SET_REG(c)	((c->u.periph.clk_num / 32) * 8)
119f151961173bf28047d01b410969f05e485f56d7eColin Cross#define PERIPH_CLK_TO_ENB_BIT(c)	(1 << (c->u.periph.clk_num % 32))
120d861196163e30c07add471562b45dce38517c9b2Colin Cross
121d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_CLK_MUX			0x00
122d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_STATE_SHIFT		28
123d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_STATE_MASK		(0xF << SUPER_STATE_SHIFT)
124d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_STATE_STANDBY		(0x0 << SUPER_STATE_SHIFT)
125d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_STATE_IDLE		(0x1 << SUPER_STATE_SHIFT)
126d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_STATE_RUN			(0x2 << SUPER_STATE_SHIFT)
127d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_STATE_IRQ			(0x3 << SUPER_STATE_SHIFT)
128d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_STATE_FIQ			(0x4 << SUPER_STATE_SHIFT)
129d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_SOURCE_MASK		0xF
130d861196163e30c07add471562b45dce38517c9b2Colin Cross#define	SUPER_FIQ_SOURCE_SHIFT		12
131d861196163e30c07add471562b45dce38517c9b2Colin Cross#define	SUPER_IRQ_SOURCE_SHIFT		8
132d861196163e30c07add471562b45dce38517c9b2Colin Cross#define	SUPER_RUN_SOURCE_SHIFT		4
133d861196163e30c07add471562b45dce38517c9b2Colin Cross#define	SUPER_IDLE_SOURCE_SHIFT		0
134d861196163e30c07add471562b45dce38517c9b2Colin Cross
135d861196163e30c07add471562b45dce38517c9b2Colin Cross#define SUPER_CLK_DIVIDER		0x04
136d861196163e30c07add471562b45dce38517c9b2Colin Cross
137d861196163e30c07add471562b45dce38517c9b2Colin Cross#define BUS_CLK_DISABLE			(1<<3)
138d861196163e30c07add471562b45dce38517c9b2Colin Cross#define BUS_CLK_DIV_MASK		0x3
139d861196163e30c07add471562b45dce38517c9b2Colin Cross
140cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define PMC_CTRL			0x0
141cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross #define PMC_CTRL_BLINK_ENB		(1 << 7)
142cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
143cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define PMC_DPD_PADS_ORIDE		0x1c
144cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross #define PMC_DPD_PADS_ORIDE_BLINK_ENB	(1 << 20)
145cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
146cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define PMC_BLINK_TIMER_DATA_ON_SHIFT	0
147cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define PMC_BLINK_TIMER_DATA_ON_MASK	0x7fff
148cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define PMC_BLINK_TIMER_ENB		(1 << 15)
149cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define PMC_BLINK_TIMER_DATA_OFF_SHIFT	16
150cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define PMC_BLINK_TIMER_DATA_OFF_MASK	0xffff
151cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
152d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void __iomem *reg_clk_base = IO_ADDRESS(TEGRA_CLK_RESET_BASE);
153cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic void __iomem *reg_pmc_base = IO_ADDRESS(TEGRA_PMC_BASE);
154d861196163e30c07add471562b45dce38517c9b2Colin Cross
1554729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross/*
1564729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross * Some clocks share a register with other clocks.  Any clock op that
1574729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross * non-atomically modifies a register used by another clock must lock
1584729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross * clock_register_lock first.
1594729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross */
1604729fd7a7dfe7847b4870801ad12222adaeb016cColin Crossstatic DEFINE_SPINLOCK(clock_register_lock);
1614729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
16278f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross/*
16378f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross * Some peripheral clocks share an enable bit, so refcount the enable bits
16478f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross * in registers CLK_ENABLE_L, CLK_ENABLE_H, and CLK_ENABLE_U
16578f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross */
16678f379b574dcbe656fa21ea72e95f8dff232e233Colin Crossstatic int tegra_periph_clk_enable_refcount[3 * 32];
16778f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
168d861196163e30c07add471562b45dce38517c9b2Colin Cross#define clk_writel(value, reg) \
169d395935f55a7ceebf22c752bbfbfe1272648a08bOlof Johansson	__raw_writel(value, reg_clk_base + (reg))
170d861196163e30c07add471562b45dce38517c9b2Colin Cross#define clk_readl(reg) \
171d395935f55a7ceebf22c752bbfbfe1272648a08bOlof Johansson	__raw_readl(reg_clk_base + (reg))
172cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define pmc_writel(value, reg) \
173d395935f55a7ceebf22c752bbfbfe1272648a08bOlof Johansson	__raw_writel(value, reg_pmc_base + (reg))
174cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross#define pmc_readl(reg) \
175d395935f55a7ceebf22c752bbfbfe1272648a08bOlof Johansson	__raw_readl(reg_pmc_base + (reg))
176d861196163e30c07add471562b45dce38517c9b2Colin Cross
1778e4fab2c39b2db774e41553646788599cfdac9dfPeter De Schrijverstatic unsigned long clk_measure_input_freq(void)
178d861196163e30c07add471562b45dce38517c9b2Colin Cross{
179d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 clock_autodetect;
180d861196163e30c07add471562b45dce38517c9b2Colin Cross	clk_writel(OSC_FREQ_DET_TRIG | 1, OSC_FREQ_DET);
181d861196163e30c07add471562b45dce38517c9b2Colin Cross	do {} while (clk_readl(OSC_FREQ_DET_STATUS) & OSC_FREQ_DET_BUSY);
182d861196163e30c07add471562b45dce38517c9b2Colin Cross	clock_autodetect = clk_readl(OSC_FREQ_DET_STATUS);
183d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (clock_autodetect >= 732 - 3 && clock_autodetect <= 732 + 3) {
184d861196163e30c07add471562b45dce38517c9b2Colin Cross		return 12000000;
185d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else if (clock_autodetect >= 794 - 3 && clock_autodetect <= 794 + 3) {
186d861196163e30c07add471562b45dce38517c9b2Colin Cross		return 13000000;
187d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else if (clock_autodetect >= 1172 - 3 && clock_autodetect <= 1172 + 3) {
188d861196163e30c07add471562b45dce38517c9b2Colin Cross		return 19200000;
189d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else if (clock_autodetect >= 1587 - 3 && clock_autodetect <= 1587 + 3) {
190d861196163e30c07add471562b45dce38517c9b2Colin Cross		return 26000000;
191d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else {
192d861196163e30c07add471562b45dce38517c9b2Colin Cross		pr_err("%s: Unexpected clock autodetect value %d", __func__, clock_autodetect);
193d861196163e30c07add471562b45dce38517c9b2Colin Cross		BUG();
194d861196163e30c07add471562b45dce38517c9b2Colin Cross		return 0;
195d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
196d861196163e30c07add471562b45dce38517c9b2Colin Cross}
197d861196163e30c07add471562b45dce38517c9b2Colin Cross
19871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic int clk_div71_get_divider(unsigned long parent_rate, unsigned long rate)
199d861196163e30c07add471562b45dce38517c9b2Colin Cross{
20071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	s64 divider_u71 = parent_rate * 2;
20171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	divider_u71 += rate - 1;
20271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	do_div(divider_u71, rate);
203d861196163e30c07add471562b45dce38517c9b2Colin Cross
20471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (divider_u71 - 2 < 0)
20571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		return 0;
206d861196163e30c07add471562b45dce38517c9b2Colin Cross
20771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (divider_u71 - 2 > 255)
208d861196163e30c07add471562b45dce38517c9b2Colin Cross		return -EINVAL;
209d861196163e30c07add471562b45dce38517c9b2Colin Cross
210d861196163e30c07add471562b45dce38517c9b2Colin Cross	return divider_u71 - 2;
211d861196163e30c07add471562b45dce38517c9b2Colin Cross}
212d861196163e30c07add471562b45dce38517c9b2Colin Cross
21371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic int clk_div16_get_divider(unsigned long parent_rate, unsigned long rate)
214d861196163e30c07add471562b45dce38517c9b2Colin Cross{
21571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	s64 divider_u16;
216d861196163e30c07add471562b45dce38517c9b2Colin Cross
21771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	divider_u16 = parent_rate;
21871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	divider_u16 += rate - 1;
21971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	do_div(divider_u16, rate);
220d861196163e30c07add471562b45dce38517c9b2Colin Cross
22171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (divider_u16 - 1 < 0)
22271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		return 0;
22371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
22471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (divider_u16 - 1 > 255)
22571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		return -EINVAL;
22671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
22771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	return divider_u16 - 1;
22871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
229d861196163e30c07add471562b45dce38517c9b2Colin Cross
230d861196163e30c07add471562b45dce38517c9b2Colin Cross/* clk_m functions */
231d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic unsigned long tegra2_clk_m_autodetect_rate(struct clk *c)
232d861196163e30c07add471562b45dce38517c9b2Colin Cross{
233d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 auto_clock_control = clk_readl(OSC_CTRL) & ~OSC_CTRL_OSC_FREQ_MASK;
234d861196163e30c07add471562b45dce38517c9b2Colin Cross
235d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->rate = clk_measure_input_freq();
236d861196163e30c07add471562b45dce38517c9b2Colin Cross	switch (c->rate) {
237d861196163e30c07add471562b45dce38517c9b2Colin Cross	case 12000000:
238d861196163e30c07add471562b45dce38517c9b2Colin Cross		auto_clock_control |= OSC_CTRL_OSC_FREQ_12MHZ;
239d861196163e30c07add471562b45dce38517c9b2Colin Cross		break;
240d861196163e30c07add471562b45dce38517c9b2Colin Cross	case 13000000:
241d861196163e30c07add471562b45dce38517c9b2Colin Cross		auto_clock_control |= OSC_CTRL_OSC_FREQ_13MHZ;
242d861196163e30c07add471562b45dce38517c9b2Colin Cross		break;
243d861196163e30c07add471562b45dce38517c9b2Colin Cross	case 19200000:
244d861196163e30c07add471562b45dce38517c9b2Colin Cross		auto_clock_control |= OSC_CTRL_OSC_FREQ_19_2MHZ;
245d861196163e30c07add471562b45dce38517c9b2Colin Cross		break;
246d861196163e30c07add471562b45dce38517c9b2Colin Cross	case 26000000:
247d861196163e30c07add471562b45dce38517c9b2Colin Cross		auto_clock_control |= OSC_CTRL_OSC_FREQ_26MHZ;
248d861196163e30c07add471562b45dce38517c9b2Colin Cross		break;
249d861196163e30c07add471562b45dce38517c9b2Colin Cross	default:
250d861196163e30c07add471562b45dce38517c9b2Colin Cross		pr_err("%s: Unexpected clock rate %ld", __func__, c->rate);
251d861196163e30c07add471562b45dce38517c9b2Colin Cross		BUG();
252d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
253d861196163e30c07add471562b45dce38517c9b2Colin Cross	clk_writel(auto_clock_control, OSC_CTRL);
254d861196163e30c07add471562b45dce38517c9b2Colin Cross	return c->rate;
255d861196163e30c07add471562b45dce38517c9b2Colin Cross}
256d861196163e30c07add471562b45dce38517c9b2Colin Cross
257d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_clk_m_init(struct clk *c)
258d861196163e30c07add471562b45dce38517c9b2Colin Cross{
259d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
260d861196163e30c07add471562b45dce38517c9b2Colin Cross	tegra2_clk_m_autodetect_rate(c);
261d861196163e30c07add471562b45dce38517c9b2Colin Cross}
262d861196163e30c07add471562b45dce38517c9b2Colin Cross
263d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_clk_m_enable(struct clk *c)
264d861196163e30c07add471562b45dce38517c9b2Colin Cross{
265d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
266d861196163e30c07add471562b45dce38517c9b2Colin Cross	return 0;
267d861196163e30c07add471562b45dce38517c9b2Colin Cross}
268d861196163e30c07add471562b45dce38517c9b2Colin Cross
269d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_clk_m_disable(struct clk *c)
270d861196163e30c07add471562b45dce38517c9b2Colin Cross{
271d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
272d861196163e30c07add471562b45dce38517c9b2Colin Cross	BUG();
273d861196163e30c07add471562b45dce38517c9b2Colin Cross}
274d861196163e30c07add471562b45dce38517c9b2Colin Cross
275d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_ops tegra_clk_m_ops = {
276d861196163e30c07add471562b45dce38517c9b2Colin Cross	.init		= tegra2_clk_m_init,
277d861196163e30c07add471562b45dce38517c9b2Colin Cross	.enable		= tegra2_clk_m_enable,
278d861196163e30c07add471562b45dce38517c9b2Colin Cross	.disable	= tegra2_clk_m_disable,
279d861196163e30c07add471562b45dce38517c9b2Colin Cross};
280d861196163e30c07add471562b45dce38517c9b2Colin Cross
281d861196163e30c07add471562b45dce38517c9b2Colin Cross/* super clock functions */
282d861196163e30c07add471562b45dce38517c9b2Colin Cross/* "super clocks" on tegra have two-stage muxes and a clock skipping
283d861196163e30c07add471562b45dce38517c9b2Colin Cross * super divider.  We will ignore the clock skipping divider, since we
284d861196163e30c07add471562b45dce38517c9b2Colin Cross * can't lower the voltage when using the clock skip, but we can if we
285d861196163e30c07add471562b45dce38517c9b2Colin Cross * lower the PLL frequency.
286d861196163e30c07add471562b45dce38517c9b2Colin Cross */
287d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_super_clk_init(struct clk *c)
288d861196163e30c07add471562b45dce38517c9b2Colin Cross{
289d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
290d861196163e30c07add471562b45dce38517c9b2Colin Cross	int source;
291d861196163e30c07add471562b45dce38517c9b2Colin Cross	int shift;
292d861196163e30c07add471562b45dce38517c9b2Colin Cross	const struct clk_mux_sel *sel;
293d861196163e30c07add471562b45dce38517c9b2Colin Cross	val = clk_readl(c->reg + SUPER_CLK_MUX);
294d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->state = ON;
295d861196163e30c07add471562b45dce38517c9b2Colin Cross	BUG_ON(((val & SUPER_STATE_MASK) != SUPER_STATE_RUN) &&
296d861196163e30c07add471562b45dce38517c9b2Colin Cross		((val & SUPER_STATE_MASK) != SUPER_STATE_IDLE));
297d861196163e30c07add471562b45dce38517c9b2Colin Cross	shift = ((val & SUPER_STATE_MASK) == SUPER_STATE_IDLE) ?
298d861196163e30c07add471562b45dce38517c9b2Colin Cross		SUPER_IDLE_SOURCE_SHIFT : SUPER_RUN_SOURCE_SHIFT;
299d861196163e30c07add471562b45dce38517c9b2Colin Cross	source = (val >> shift) & SUPER_SOURCE_MASK;
300d861196163e30c07add471562b45dce38517c9b2Colin Cross	for (sel = c->inputs; sel->input != NULL; sel++) {
301d861196163e30c07add471562b45dce38517c9b2Colin Cross		if (sel->value == source)
302d861196163e30c07add471562b45dce38517c9b2Colin Cross			break;
303d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
304d861196163e30c07add471562b45dce38517c9b2Colin Cross	BUG_ON(sel->input == NULL);
305d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->parent = sel->input;
306d861196163e30c07add471562b45dce38517c9b2Colin Cross}
307d861196163e30c07add471562b45dce38517c9b2Colin Cross
308d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_super_clk_enable(struct clk *c)
309d861196163e30c07add471562b45dce38517c9b2Colin Cross{
310d861196163e30c07add471562b45dce38517c9b2Colin Cross	clk_writel(0, c->reg + SUPER_CLK_DIVIDER);
311d861196163e30c07add471562b45dce38517c9b2Colin Cross	return 0;
312d861196163e30c07add471562b45dce38517c9b2Colin Cross}
313d861196163e30c07add471562b45dce38517c9b2Colin Cross
314d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_super_clk_disable(struct clk *c)
315d861196163e30c07add471562b45dce38517c9b2Colin Cross{
316d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
317d861196163e30c07add471562b45dce38517c9b2Colin Cross
318d861196163e30c07add471562b45dce38517c9b2Colin Cross	/* oops - don't disable the CPU clock! */
319d861196163e30c07add471562b45dce38517c9b2Colin Cross	BUG();
320d861196163e30c07add471562b45dce38517c9b2Colin Cross}
321d861196163e30c07add471562b45dce38517c9b2Colin Cross
322d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_super_clk_set_parent(struct clk *c, struct clk *p)
323d861196163e30c07add471562b45dce38517c9b2Colin Cross{
324d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
325d861196163e30c07add471562b45dce38517c9b2Colin Cross	const struct clk_mux_sel *sel;
326d861196163e30c07add471562b45dce38517c9b2Colin Cross	int shift;
32771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
3286eab04a87677a37cf15b52e2b4b4fd57917102adJustin P. Mattock	val = clk_readl(c->reg + SUPER_CLK_MUX);
329d861196163e30c07add471562b45dce38517c9b2Colin Cross	BUG_ON(((val & SUPER_STATE_MASK) != SUPER_STATE_RUN) &&
330d861196163e30c07add471562b45dce38517c9b2Colin Cross		((val & SUPER_STATE_MASK) != SUPER_STATE_IDLE));
331d861196163e30c07add471562b45dce38517c9b2Colin Cross	shift = ((val & SUPER_STATE_MASK) == SUPER_STATE_IDLE) ?
332d861196163e30c07add471562b45dce38517c9b2Colin Cross		SUPER_IDLE_SOURCE_SHIFT : SUPER_RUN_SOURCE_SHIFT;
333d861196163e30c07add471562b45dce38517c9b2Colin Cross	for (sel = c->inputs; sel->input != NULL; sel++) {
334d861196163e30c07add471562b45dce38517c9b2Colin Cross		if (sel->input == p) {
335d861196163e30c07add471562b45dce38517c9b2Colin Cross			val &= ~(SUPER_SOURCE_MASK << shift);
336d861196163e30c07add471562b45dce38517c9b2Colin Cross			val |= sel->value << shift;
33771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
33871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			if (c->refcnt)
3394729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross				clk_enable(p);
34071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
341d861196163e30c07add471562b45dce38517c9b2Colin Cross			clk_writel(val, c->reg);
34271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
34371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			if (c->refcnt && c->parent)
3444729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross				clk_disable(c->parent);
34571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
34671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			clk_reparent(c, p);
347d861196163e30c07add471562b45dce38517c9b2Colin Cross			return 0;
348d861196163e30c07add471562b45dce38517c9b2Colin Cross		}
349d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
350d861196163e30c07add471562b45dce38517c9b2Colin Cross	return -EINVAL;
351d861196163e30c07add471562b45dce38517c9b2Colin Cross}
352d861196163e30c07add471562b45dce38517c9b2Colin Cross
3539c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross/*
3549c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross * Super clocks have "clock skippers" instead of dividers.  Dividing using
3559c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross * a clock skipper does not allow the voltage to be scaled down, so instead
3569c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross * adjust the rate of the parent clock.  This requires that the parent of a
3579c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross * super clock have no other children, otherwise the rate will change
3589c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross * underneath the other children.
3599c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross */
3609c7dc562cd78784f54261b9bedb44e8b0056f729Colin Crossstatic int tegra2_super_clk_set_rate(struct clk *c, unsigned long rate)
3619c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross{
3629c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	return clk_set_rate(c->parent, rate);
3639c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross}
3649c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross
365d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_ops tegra_super_ops = {
366d861196163e30c07add471562b45dce38517c9b2Colin Cross	.init			= tegra2_super_clk_init,
367d861196163e30c07add471562b45dce38517c9b2Colin Cross	.enable			= tegra2_super_clk_enable,
368d861196163e30c07add471562b45dce38517c9b2Colin Cross	.disable		= tegra2_super_clk_disable,
369d861196163e30c07add471562b45dce38517c9b2Colin Cross	.set_parent		= tegra2_super_clk_set_parent,
3709c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.set_rate		= tegra2_super_clk_set_rate,
37171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross};
37271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
37371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross/* virtual cpu clock functions */
37471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross/* some clocks can not be stopped (cpu, memory bus) while the SoC is running.
37571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross   To change the frequency of these clocks, the parent pll may need to be
37671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross   reprogrammed, so the clock must be moved off the pll, the pll reprogrammed,
37771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross   and then the clock moved back to the pll.  To hide this sequence, a virtual
37871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross   clock handles it.
37971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross */
38071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic void tegra2_cpu_clk_init(struct clk *c)
38171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
38271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
38371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
38471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic int tegra2_cpu_clk_enable(struct clk *c)
38571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
38671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	return 0;
38771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
38871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
38971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic void tegra2_cpu_clk_disable(struct clk *c)
39071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
39171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
39271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
39371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* oops - don't disable the CPU clock! */
39471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	BUG();
39571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
39671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
39771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic int tegra2_cpu_clk_set_rate(struct clk *c, unsigned long rate)
39871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
39971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	int ret;
40089a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross	/*
40189a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross	 * Take an extra reference to the main pll so it doesn't turn
40289a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross	 * off when we move the cpu off of it
40389a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross	 */
40489a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross	clk_enable(c->u.cpu.main);
40589a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross
4064729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	ret = clk_set_parent(c->parent, c->u.cpu.backup);
40771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (ret) {
408f151961173bf28047d01b410969f05e485f56d7eColin Cross		pr_err("Failed to switch cpu to clock %s\n", c->u.cpu.backup->name);
40989a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross		goto out;
41071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
41171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
4124729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	if (rate == clk_get_rate(c->u.cpu.backup))
413cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		goto out;
414cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
4154729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	ret = clk_set_rate(c->u.cpu.main, rate);
41671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (ret) {
41771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		pr_err("Failed to change cpu pll to %lu\n", rate);
41889a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross		goto out;
41971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
42071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
4214729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	ret = clk_set_parent(c->parent, c->u.cpu.main);
42271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (ret) {
423f151961173bf28047d01b410969f05e485f56d7eColin Cross		pr_err("Failed to switch cpu to clock %s\n", c->u.cpu.main->name);
42489a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross		goto out;
42571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
42671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
427cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossout:
42889a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross	clk_disable(c->u.cpu.main);
42989a5fb84dabdf6daeae7d5301a6b1ae4754425ddColin Cross	return ret;
43071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
43171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
43271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk_ops tegra_cpu_ops = {
43371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.init     = tegra2_cpu_clk_init,
43471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.enable   = tegra2_cpu_clk_enable,
43571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.disable  = tegra2_cpu_clk_disable,
43671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.set_rate = tegra2_cpu_clk_set_rate,
437d861196163e30c07add471562b45dce38517c9b2Colin Cross};
438d861196163e30c07add471562b45dce38517c9b2Colin Cross
4399c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross/* virtual cop clock functions. Used to acquire the fake 'cop' clock to
4409c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross * reset the COP block (i.e. AVP) */
4419c7dc562cd78784f54261b9bedb44e8b0056f729Colin Crossstatic void tegra2_cop_clk_reset(struct clk *c, bool assert)
4429c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross{
4439c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	unsigned long reg = assert ? RST_DEVICES_SET : RST_DEVICES_CLR;
4449c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross
4459c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	pr_debug("%s %s\n", __func__, assert ? "assert" : "deassert");
4469c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	clk_writel(1 << 1, reg);
4479c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross}
4489c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross
4499c7dc562cd78784f54261b9bedb44e8b0056f729Colin Crossstatic struct clk_ops tegra_cop_ops = {
4509c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.reset    = tegra2_cop_clk_reset,
4519c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross};
4529c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross
453d861196163e30c07add471562b45dce38517c9b2Colin Cross/* bus clock functions */
454d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_bus_clk_init(struct clk *c)
455d861196163e30c07add471562b45dce38517c9b2Colin Cross{
456d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val = clk_readl(c->reg);
457d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->state = ((val >> c->reg_shift) & BUS_CLK_DISABLE) ? OFF : ON;
458d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->div = ((val >> c->reg_shift) & BUS_CLK_DIV_MASK) + 1;
459d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->mul = 1;
460d861196163e30c07add471562b45dce38517c9b2Colin Cross}
461d861196163e30c07add471562b45dce38517c9b2Colin Cross
462d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_bus_clk_enable(struct clk *c)
463d861196163e30c07add471562b45dce38517c9b2Colin Cross{
4644729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	u32 val;
4654729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long flags;
4664729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
4674729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	spin_lock_irqsave(&clock_register_lock, flags);
4684729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
4694729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	val = clk_readl(c->reg);
470d861196163e30c07add471562b45dce38517c9b2Colin Cross	val &= ~(BUS_CLK_DISABLE << c->reg_shift);
471d861196163e30c07add471562b45dce38517c9b2Colin Cross	clk_writel(val, c->reg);
4724729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
4734729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	spin_unlock_irqrestore(&clock_register_lock, flags);
4744729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
475d861196163e30c07add471562b45dce38517c9b2Colin Cross	return 0;
476d861196163e30c07add471562b45dce38517c9b2Colin Cross}
477d861196163e30c07add471562b45dce38517c9b2Colin Cross
478d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_bus_clk_disable(struct clk *c)
479d861196163e30c07add471562b45dce38517c9b2Colin Cross{
4804729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	u32 val;
4814729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long flags;
4824729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
4834729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	spin_lock_irqsave(&clock_register_lock, flags);
4844729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
4854729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	val = clk_readl(c->reg);
486d861196163e30c07add471562b45dce38517c9b2Colin Cross	val |= BUS_CLK_DISABLE << c->reg_shift;
487d861196163e30c07add471562b45dce38517c9b2Colin Cross	clk_writel(val, c->reg);
4884729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
4894729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	spin_unlock_irqrestore(&clock_register_lock, flags);
490d861196163e30c07add471562b45dce38517c9b2Colin Cross}
491d861196163e30c07add471562b45dce38517c9b2Colin Cross
492d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_bus_clk_set_rate(struct clk *c, unsigned long rate)
493d861196163e30c07add471562b45dce38517c9b2Colin Cross{
4944729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	u32 val;
4954729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long parent_rate = clk_get_rate(c->parent);
4964729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long flags;
4974729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	int ret = -EINVAL;
498d861196163e30c07add471562b45dce38517c9b2Colin Cross	int i;
4994729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
5004729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	spin_lock_irqsave(&clock_register_lock, flags);
5014729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
5024729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	val = clk_readl(c->reg);
503d861196163e30c07add471562b45dce38517c9b2Colin Cross	for (i = 1; i <= 4; i++) {
504d861196163e30c07add471562b45dce38517c9b2Colin Cross		if (rate == parent_rate / i) {
505d861196163e30c07add471562b45dce38517c9b2Colin Cross			val &= ~(BUS_CLK_DIV_MASK << c->reg_shift);
506d861196163e30c07add471562b45dce38517c9b2Colin Cross			val |= (i - 1) << c->reg_shift;
507d861196163e30c07add471562b45dce38517c9b2Colin Cross			clk_writel(val, c->reg);
508d861196163e30c07add471562b45dce38517c9b2Colin Cross			c->div = i;
509d861196163e30c07add471562b45dce38517c9b2Colin Cross			c->mul = 1;
5104729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross			ret = 0;
5114729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross			break;
512d861196163e30c07add471562b45dce38517c9b2Colin Cross		}
513d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
5144729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
5154729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	spin_unlock_irqrestore(&clock_register_lock, flags);
5164729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
5174729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	return ret;
518d861196163e30c07add471562b45dce38517c9b2Colin Cross}
519d861196163e30c07add471562b45dce38517c9b2Colin Cross
520d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_ops tegra_bus_ops = {
521d861196163e30c07add471562b45dce38517c9b2Colin Cross	.init			= tegra2_bus_clk_init,
522d861196163e30c07add471562b45dce38517c9b2Colin Cross	.enable			= tegra2_bus_clk_enable,
523d861196163e30c07add471562b45dce38517c9b2Colin Cross	.disable		= tegra2_bus_clk_disable,
524d861196163e30c07add471562b45dce38517c9b2Colin Cross	.set_rate		= tegra2_bus_clk_set_rate,
525d861196163e30c07add471562b45dce38517c9b2Colin Cross};
526d861196163e30c07add471562b45dce38517c9b2Colin Cross
527cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross/* Blink output functions */
528cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
529cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic void tegra2_blink_clk_init(struct clk *c)
530cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross{
531cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	u32 val;
532cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
533cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	val = pmc_readl(PMC_CTRL);
534cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	c->state = (val & PMC_CTRL_BLINK_ENB) ? ON : OFF;
535cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	c->mul = 1;
536cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	val = pmc_readl(c->reg);
537cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
538cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	if (val & PMC_BLINK_TIMER_ENB) {
539cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		unsigned int on_off;
540cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
541cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		on_off = (val >> PMC_BLINK_TIMER_DATA_ON_SHIFT) &
542cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross			PMC_BLINK_TIMER_DATA_ON_MASK;
543cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		val >>= PMC_BLINK_TIMER_DATA_OFF_SHIFT;
544cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		val &= PMC_BLINK_TIMER_DATA_OFF_MASK;
545cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		on_off += val;
546cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		/* each tick in the blink timer is 4 32KHz clocks */
547cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		c->div = on_off * 4;
548cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	} else {
549cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		c->div = 1;
550cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	}
551cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross}
552cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
553cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic int tegra2_blink_clk_enable(struct clk *c)
554cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross{
555cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	u32 val;
556cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
557cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	val = pmc_readl(PMC_DPD_PADS_ORIDE);
558cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	pmc_writel(val | PMC_DPD_PADS_ORIDE_BLINK_ENB, PMC_DPD_PADS_ORIDE);
559cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
560cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	val = pmc_readl(PMC_CTRL);
561cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	pmc_writel(val | PMC_CTRL_BLINK_ENB, PMC_CTRL);
562cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
563cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	return 0;
564cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross}
565cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
566cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic void tegra2_blink_clk_disable(struct clk *c)
567cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross{
568cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	u32 val;
569cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
570cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	val = pmc_readl(PMC_CTRL);
571cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	pmc_writel(val & ~PMC_CTRL_BLINK_ENB, PMC_CTRL);
572cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
573cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	val = pmc_readl(PMC_DPD_PADS_ORIDE);
574cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	pmc_writel(val & ~PMC_DPD_PADS_ORIDE_BLINK_ENB, PMC_DPD_PADS_ORIDE);
575cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross}
576cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
577cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic int tegra2_blink_clk_set_rate(struct clk *c, unsigned long rate)
578cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross{
5794729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long parent_rate = clk_get_rate(c->parent);
5804729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	if (rate >= parent_rate) {
581cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		c->div = 1;
582cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		pmc_writel(0, c->reg);
583cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	} else {
584cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		unsigned int on_off;
585cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		u32 val;
586cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
5874729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		on_off = DIV_ROUND_UP(parent_rate / 8, rate);
588cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		c->div = on_off * 8;
589cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
590cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		val = (on_off & PMC_BLINK_TIMER_DATA_ON_MASK) <<
591cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross			PMC_BLINK_TIMER_DATA_ON_SHIFT;
592cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		on_off &= PMC_BLINK_TIMER_DATA_OFF_MASK;
593cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		on_off <<= PMC_BLINK_TIMER_DATA_OFF_SHIFT;
594cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		val |= on_off;
595cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		val |= PMC_BLINK_TIMER_ENB;
596cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		pmc_writel(val, c->reg);
597cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	}
598cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
599cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	return 0;
600cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross}
601cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
602cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic struct clk_ops tegra_blink_clk_ops = {
603cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.init			= &tegra2_blink_clk_init,
604cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.enable			= &tegra2_blink_clk_enable,
605cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.disable		= &tegra2_blink_clk_disable,
606cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.set_rate		= &tegra2_blink_clk_set_rate,
607cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross};
608cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
609d861196163e30c07add471562b45dce38517c9b2Colin Cross/* PLL Functions */
610d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_pll_clk_wait_for_lock(struct clk *c)
611d861196163e30c07add471562b45dce38517c9b2Colin Cross{
612f151961173bf28047d01b410969f05e485f56d7eColin Cross	udelay(c->u.pll.lock_delay);
613d861196163e30c07add471562b45dce38517c9b2Colin Cross
614d861196163e30c07add471562b45dce38517c9b2Colin Cross	return 0;
615d861196163e30c07add471562b45dce38517c9b2Colin Cross}
616d861196163e30c07add471562b45dce38517c9b2Colin Cross
617d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_pll_clk_init(struct clk *c)
618d861196163e30c07add471562b45dce38517c9b2Colin Cross{
619d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val = clk_readl(c->reg + PLL_BASE);
620d861196163e30c07add471562b45dce38517c9b2Colin Cross
621d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->state = (val & PLL_BASE_ENABLE) ? ON : OFF;
622d861196163e30c07add471562b45dce38517c9b2Colin Cross
623d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & PLL_FIXED && !(val & PLL_BASE_OVERRIDE)) {
624d861196163e30c07add471562b45dce38517c9b2Colin Cross		pr_warning("Clock %s has unknown fixed frequency\n", c->name);
62571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->mul = 1;
62671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->div = 1;
627d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else if (val & PLL_BASE_BYPASS) {
62871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->mul = 1;
62971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->div = 1;
630d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else {
63171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->mul = (val & PLL_BASE_DIVN_MASK) >> PLL_BASE_DIVN_SHIFT;
63271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->div = (val & PLL_BASE_DIVM_MASK) >> PLL_BASE_DIVM_SHIFT;
63371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (c->flags & PLLU)
63471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			c->div *= (val & PLLU_BASE_POST_DIV) ? 1 : 2;
63571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		else
63671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			c->div *= (val & PLL_BASE_DIVP_MASK) ? 2 : 1;
637d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
638d861196163e30c07add471562b45dce38517c9b2Colin Cross}
639d861196163e30c07add471562b45dce38517c9b2Colin Cross
640d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_pll_clk_enable(struct clk *c)
641d861196163e30c07add471562b45dce38517c9b2Colin Cross{
642d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
643d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
644d861196163e30c07add471562b45dce38517c9b2Colin Cross
645d861196163e30c07add471562b45dce38517c9b2Colin Cross	val = clk_readl(c->reg + PLL_BASE);
646d861196163e30c07add471562b45dce38517c9b2Colin Cross	val &= ~PLL_BASE_BYPASS;
647d861196163e30c07add471562b45dce38517c9b2Colin Cross	val |= PLL_BASE_ENABLE;
648d861196163e30c07add471562b45dce38517c9b2Colin Cross	clk_writel(val, c->reg + PLL_BASE);
649d861196163e30c07add471562b45dce38517c9b2Colin Cross
650d861196163e30c07add471562b45dce38517c9b2Colin Cross	tegra2_pll_clk_wait_for_lock(c);
651d861196163e30c07add471562b45dce38517c9b2Colin Cross
652d861196163e30c07add471562b45dce38517c9b2Colin Cross	return 0;
653d861196163e30c07add471562b45dce38517c9b2Colin Cross}
654d861196163e30c07add471562b45dce38517c9b2Colin Cross
655d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_pll_clk_disable(struct clk *c)
656d861196163e30c07add471562b45dce38517c9b2Colin Cross{
657d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
658d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
659d861196163e30c07add471562b45dce38517c9b2Colin Cross
660d861196163e30c07add471562b45dce38517c9b2Colin Cross	val = clk_readl(c->reg);
661d861196163e30c07add471562b45dce38517c9b2Colin Cross	val &= ~(PLL_BASE_BYPASS | PLL_BASE_ENABLE);
662d861196163e30c07add471562b45dce38517c9b2Colin Cross	clk_writel(val, c->reg);
663d861196163e30c07add471562b45dce38517c9b2Colin Cross}
664d861196163e30c07add471562b45dce38517c9b2Colin Cross
665d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_pll_clk_set_rate(struct clk *c, unsigned long rate)
666d861196163e30c07add471562b45dce38517c9b2Colin Cross{
667d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
668d861196163e30c07add471562b45dce38517c9b2Colin Cross	unsigned long input_rate;
669f151961173bf28047d01b410969f05e485f56d7eColin Cross	const struct clk_pll_freq_table *sel;
670d861196163e30c07add471562b45dce38517c9b2Colin Cross
671d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s: %s %lu\n", __func__, c->name, rate);
672d861196163e30c07add471562b45dce38517c9b2Colin Cross
6734729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	input_rate = clk_get_rate(c->parent);
674f151961173bf28047d01b410969f05e485f56d7eColin Cross	for (sel = c->u.pll.freq_table; sel->input_rate != 0; sel++) {
675d861196163e30c07add471562b45dce38517c9b2Colin Cross		if (sel->input_rate == input_rate && sel->output_rate == rate) {
67671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			c->mul = sel->n;
67771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			c->div = sel->m * sel->p;
678d861196163e30c07add471562b45dce38517c9b2Colin Cross
679d861196163e30c07add471562b45dce38517c9b2Colin Cross			val = clk_readl(c->reg + PLL_BASE);
680d861196163e30c07add471562b45dce38517c9b2Colin Cross			if (c->flags & PLL_FIXED)
681d861196163e30c07add471562b45dce38517c9b2Colin Cross				val |= PLL_BASE_OVERRIDE;
682d861196163e30c07add471562b45dce38517c9b2Colin Cross			val &= ~(PLL_BASE_DIVP_MASK | PLL_BASE_DIVN_MASK |
683d861196163e30c07add471562b45dce38517c9b2Colin Cross				 PLL_BASE_DIVM_MASK);
68471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val |= (sel->m << PLL_BASE_DIVM_SHIFT) |
68571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross				(sel->n << PLL_BASE_DIVN_SHIFT);
68671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			BUG_ON(sel->p < 1 || sel->p > 2);
68771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			if (c->flags & PLLU) {
68871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross				if (sel->p == 1)
68971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross					val |= PLLU_BASE_POST_DIV;
69071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			} else {
69171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross				if (sel->p == 2)
69271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross					val |= 1 << PLL_BASE_DIVP_SHIFT;
69371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			}
694d861196163e30c07add471562b45dce38517c9b2Colin Cross			clk_writel(val, c->reg + PLL_BASE);
695d861196163e30c07add471562b45dce38517c9b2Colin Cross
696d861196163e30c07add471562b45dce38517c9b2Colin Cross			if (c->flags & PLL_HAS_CPCON) {
69771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross				val = clk_readl(c->reg + PLL_MISC(c));
69871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross				val &= ~PLL_MISC_CPCON_MASK;
69971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross				val |= sel->cpcon << PLL_MISC_CPCON_SHIFT;
700d861196163e30c07add471562b45dce38517c9b2Colin Cross				clk_writel(val, c->reg + PLL_MISC(c));
701d861196163e30c07add471562b45dce38517c9b2Colin Cross			}
702d861196163e30c07add471562b45dce38517c9b2Colin Cross
703d861196163e30c07add471562b45dce38517c9b2Colin Cross			if (c->state == ON)
704d861196163e30c07add471562b45dce38517c9b2Colin Cross				tegra2_pll_clk_enable(c);
705d861196163e30c07add471562b45dce38517c9b2Colin Cross
706d861196163e30c07add471562b45dce38517c9b2Colin Cross			return 0;
707d861196163e30c07add471562b45dce38517c9b2Colin Cross		}
708d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
709d861196163e30c07add471562b45dce38517c9b2Colin Cross	return -EINVAL;
710d861196163e30c07add471562b45dce38517c9b2Colin Cross}
711d861196163e30c07add471562b45dce38517c9b2Colin Cross
712d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_ops tegra_pll_ops = {
713d861196163e30c07add471562b45dce38517c9b2Colin Cross	.init			= tegra2_pll_clk_init,
714d861196163e30c07add471562b45dce38517c9b2Colin Cross	.enable			= tegra2_pll_clk_enable,
715d861196163e30c07add471562b45dce38517c9b2Colin Cross	.disable		= tegra2_pll_clk_disable,
716d861196163e30c07add471562b45dce38517c9b2Colin Cross	.set_rate		= tegra2_pll_clk_set_rate,
71771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross};
71871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
71971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic void tegra2_pllx_clk_init(struct clk *c)
72071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
72171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	tegra2_pll_clk_init(c);
72271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
7239a1086da345cea8b2d1f01b47e5bbd81d640d642Olof Johansson	if (tegra_sku_id == 7)
72471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->max_rate = 750000000;
72571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
72671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
72771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk_ops tegra_pllx_ops = {
72871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.init     = tegra2_pllx_clk_init,
72971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.enable   = tegra2_pll_clk_enable,
73071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.disable  = tegra2_pll_clk_disable,
73171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.set_rate = tegra2_pll_clk_set_rate,
732d861196163e30c07add471562b45dce38517c9b2Colin Cross};
733d861196163e30c07add471562b45dce38517c9b2Colin Cross
7348d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoportstatic int tegra2_plle_clk_enable(struct clk *c)
7358d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport{
7368d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	u32 val;
7378d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
7388d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	pr_debug("%s on clock %s\n", __func__, c->name);
7398d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
7408d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	mdelay(1);
7418d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
7428d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	val = clk_readl(c->reg + PLL_BASE);
7438d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	if (!(val & PLLE_MISC_READY))
7448d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport		return -EBUSY;
7458d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
7468d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	val = clk_readl(c->reg + PLL_BASE);
7478d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	val |= PLL_BASE_ENABLE | PLL_BASE_BYPASS;
7488d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	clk_writel(val, c->reg + PLL_BASE);
7498d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
7508d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	return 0;
7518d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport}
7528d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
7538d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoportstatic struct clk_ops tegra_plle_ops = {
7548d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	.init       = tegra2_pll_clk_init,
7558d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	.enable     = tegra2_plle_clk_enable,
7568d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	.set_rate   = tegra2_pll_clk_set_rate,
7578d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport};
7588d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
759d861196163e30c07add471562b45dce38517c9b2Colin Cross/* Clock divider ops */
760d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_pll_div_clk_init(struct clk *c)
761d861196163e30c07add471562b45dce38517c9b2Colin Cross{
762d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val = clk_readl(c->reg);
763d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 divu71;
764d861196163e30c07add471562b45dce38517c9b2Colin Cross	val >>= c->reg_shift;
765d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->state = (val & PLL_OUT_CLKEN) ? ON : OFF;
766d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (!(val & PLL_OUT_RESET_DISABLE))
767d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->state = OFF;
768d861196163e30c07add471562b45dce38517c9b2Colin Cross
769d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & DIV_U71) {
770d861196163e30c07add471562b45dce38517c9b2Colin Cross		divu71 = (val & PLL_OUT_RATIO_MASK) >> PLL_OUT_RATIO_SHIFT;
771d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->div = (divu71 + 2);
772d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->mul = 2;
773d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else if (c->flags & DIV_2) {
774d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->div = 2;
775d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->mul = 1;
776d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else {
777d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->div = 1;
778d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->mul = 1;
779d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
780d861196163e30c07add471562b45dce38517c9b2Colin Cross}
781d861196163e30c07add471562b45dce38517c9b2Colin Cross
782d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_pll_div_clk_enable(struct clk *c)
783d861196163e30c07add471562b45dce38517c9b2Colin Cross{
784d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
785d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 new_val;
7864729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long flags;
787d861196163e30c07add471562b45dce38517c9b2Colin Cross
788d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s: %s\n", __func__, c->name);
789d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & DIV_U71) {
7904729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		spin_lock_irqsave(&clock_register_lock, flags);
791d861196163e30c07add471562b45dce38517c9b2Colin Cross		val = clk_readl(c->reg);
792d861196163e30c07add471562b45dce38517c9b2Colin Cross		new_val = val >> c->reg_shift;
793d861196163e30c07add471562b45dce38517c9b2Colin Cross		new_val &= 0xFFFF;
794d861196163e30c07add471562b45dce38517c9b2Colin Cross
795d861196163e30c07add471562b45dce38517c9b2Colin Cross		new_val |= PLL_OUT_CLKEN | PLL_OUT_RESET_DISABLE;
796d861196163e30c07add471562b45dce38517c9b2Colin Cross
797d861196163e30c07add471562b45dce38517c9b2Colin Cross		val &= ~(0xFFFF << c->reg_shift);
798d861196163e30c07add471562b45dce38517c9b2Colin Cross		val |= new_val << c->reg_shift;
799d861196163e30c07add471562b45dce38517c9b2Colin Cross		clk_writel(val, c->reg);
8004729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		spin_unlock_irqrestore(&clock_register_lock, flags);
801d861196163e30c07add471562b45dce38517c9b2Colin Cross		return 0;
802d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else if (c->flags & DIV_2) {
803d861196163e30c07add471562b45dce38517c9b2Colin Cross		BUG_ON(!(c->flags & PLLD));
8044729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		spin_lock_irqsave(&clock_register_lock, flags);
805d861196163e30c07add471562b45dce38517c9b2Colin Cross		val = clk_readl(c->reg);
806d861196163e30c07add471562b45dce38517c9b2Colin Cross		val &= ~PLLD_MISC_DIV_RST;
807d861196163e30c07add471562b45dce38517c9b2Colin Cross		clk_writel(val, c->reg);
8084729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		spin_unlock_irqrestore(&clock_register_lock, flags);
809d861196163e30c07add471562b45dce38517c9b2Colin Cross		return 0;
810d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
811d861196163e30c07add471562b45dce38517c9b2Colin Cross	return -EINVAL;
812d861196163e30c07add471562b45dce38517c9b2Colin Cross}
813d861196163e30c07add471562b45dce38517c9b2Colin Cross
814d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_pll_div_clk_disable(struct clk *c)
815d861196163e30c07add471562b45dce38517c9b2Colin Cross{
816d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
817d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 new_val;
8184729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long flags;
819d861196163e30c07add471562b45dce38517c9b2Colin Cross
820d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s: %s\n", __func__, c->name);
821d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & DIV_U71) {
8224729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		spin_lock_irqsave(&clock_register_lock, flags);
823d861196163e30c07add471562b45dce38517c9b2Colin Cross		val = clk_readl(c->reg);
824d861196163e30c07add471562b45dce38517c9b2Colin Cross		new_val = val >> c->reg_shift;
825d861196163e30c07add471562b45dce38517c9b2Colin Cross		new_val &= 0xFFFF;
826d861196163e30c07add471562b45dce38517c9b2Colin Cross
827d861196163e30c07add471562b45dce38517c9b2Colin Cross		new_val &= ~(PLL_OUT_CLKEN | PLL_OUT_RESET_DISABLE);
828d861196163e30c07add471562b45dce38517c9b2Colin Cross
829d861196163e30c07add471562b45dce38517c9b2Colin Cross		val &= ~(0xFFFF << c->reg_shift);
830d861196163e30c07add471562b45dce38517c9b2Colin Cross		val |= new_val << c->reg_shift;
831d861196163e30c07add471562b45dce38517c9b2Colin Cross		clk_writel(val, c->reg);
8324729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		spin_unlock_irqrestore(&clock_register_lock, flags);
833d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else if (c->flags & DIV_2) {
834d861196163e30c07add471562b45dce38517c9b2Colin Cross		BUG_ON(!(c->flags & PLLD));
8354729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		spin_lock_irqsave(&clock_register_lock, flags);
836d861196163e30c07add471562b45dce38517c9b2Colin Cross		val = clk_readl(c->reg);
837d861196163e30c07add471562b45dce38517c9b2Colin Cross		val |= PLLD_MISC_DIV_RST;
838d861196163e30c07add471562b45dce38517c9b2Colin Cross		clk_writel(val, c->reg);
8394729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		spin_unlock_irqrestore(&clock_register_lock, flags);
840d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
841d861196163e30c07add471562b45dce38517c9b2Colin Cross}
842d861196163e30c07add471562b45dce38517c9b2Colin Cross
843d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_pll_div_clk_set_rate(struct clk *c, unsigned long rate)
844d861196163e30c07add471562b45dce38517c9b2Colin Cross{
845d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
846d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 new_val;
847d861196163e30c07add471562b45dce38517c9b2Colin Cross	int divider_u71;
8484729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long parent_rate = clk_get_rate(c->parent);
8494729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long flags;
8504729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
851d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s: %s %lu\n", __func__, c->name, rate);
852d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & DIV_U71) {
8534729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		divider_u71 = clk_div71_get_divider(parent_rate, rate);
854d861196163e30c07add471562b45dce38517c9b2Colin Cross		if (divider_u71 >= 0) {
8554729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross			spin_lock_irqsave(&clock_register_lock, flags);
856d861196163e30c07add471562b45dce38517c9b2Colin Cross			val = clk_readl(c->reg);
857d861196163e30c07add471562b45dce38517c9b2Colin Cross			new_val = val >> c->reg_shift;
858d861196163e30c07add471562b45dce38517c9b2Colin Cross			new_val &= 0xFFFF;
859d861196163e30c07add471562b45dce38517c9b2Colin Cross			if (c->flags & DIV_U71_FIXED)
860d861196163e30c07add471562b45dce38517c9b2Colin Cross				new_val |= PLL_OUT_OVERRIDE;
861d861196163e30c07add471562b45dce38517c9b2Colin Cross			new_val &= ~PLL_OUT_RATIO_MASK;
862d861196163e30c07add471562b45dce38517c9b2Colin Cross			new_val |= divider_u71 << PLL_OUT_RATIO_SHIFT;
863d861196163e30c07add471562b45dce38517c9b2Colin Cross
864d861196163e30c07add471562b45dce38517c9b2Colin Cross			val &= ~(0xFFFF << c->reg_shift);
865d861196163e30c07add471562b45dce38517c9b2Colin Cross			val |= new_val << c->reg_shift;
866d861196163e30c07add471562b45dce38517c9b2Colin Cross			clk_writel(val, c->reg);
867d861196163e30c07add471562b45dce38517c9b2Colin Cross			c->div = divider_u71 + 2;
868d861196163e30c07add471562b45dce38517c9b2Colin Cross			c->mul = 2;
8694729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross			spin_unlock_irqrestore(&clock_register_lock, flags);
870d861196163e30c07add471562b45dce38517c9b2Colin Cross			return 0;
871d861196163e30c07add471562b45dce38517c9b2Colin Cross		}
872d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else if (c->flags & DIV_2) {
8734729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		if (parent_rate == rate * 2)
874d861196163e30c07add471562b45dce38517c9b2Colin Cross			return 0;
875d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
876d861196163e30c07add471562b45dce38517c9b2Colin Cross	return -EINVAL;
877d861196163e30c07add471562b45dce38517c9b2Colin Cross}
878d861196163e30c07add471562b45dce38517c9b2Colin Cross
87971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic long tegra2_pll_div_clk_round_rate(struct clk *c, unsigned long rate)
88071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
88171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	int divider;
8824729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long parent_rate = clk_get_rate(c->parent);
88371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	pr_debug("%s: %s %lu\n", __func__, c->name, rate);
88471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
88571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (c->flags & DIV_U71) {
8864729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		divider = clk_div71_get_divider(parent_rate, rate);
88771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (divider < 0)
88871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			return divider;
889421186e71000c067c2687baeffde62954a80cdccColin Cross		return DIV_ROUND_UP(parent_rate * 2, divider + 2);
89071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	} else if (c->flags & DIV_2) {
891421186e71000c067c2687baeffde62954a80cdccColin Cross		return DIV_ROUND_UP(parent_rate, 2);
89271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
89371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	return -EINVAL;
89471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
895d861196163e30c07add471562b45dce38517c9b2Colin Cross
896d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_ops tegra_pll_div_ops = {
897d861196163e30c07add471562b45dce38517c9b2Colin Cross	.init			= tegra2_pll_div_clk_init,
898d861196163e30c07add471562b45dce38517c9b2Colin Cross	.enable			= tegra2_pll_div_clk_enable,
899d861196163e30c07add471562b45dce38517c9b2Colin Cross	.disable		= tegra2_pll_div_clk_disable,
900d861196163e30c07add471562b45dce38517c9b2Colin Cross	.set_rate		= tegra2_pll_div_clk_set_rate,
90171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.round_rate		= tegra2_pll_div_clk_round_rate,
902d861196163e30c07add471562b45dce38517c9b2Colin Cross};
903d861196163e30c07add471562b45dce38517c9b2Colin Cross
904d861196163e30c07add471562b45dce38517c9b2Colin Cross/* Periph clk ops */
905d861196163e30c07add471562b45dce38517c9b2Colin Cross
906d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_periph_clk_init(struct clk *c)
907d861196163e30c07add471562b45dce38517c9b2Colin Cross{
908d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val = clk_readl(c->reg);
90945fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	const struct clk_mux_sel *mux = NULL;
910d861196163e30c07add471562b45dce38517c9b2Colin Cross	const struct clk_mux_sel *sel;
911d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & MUX) {
912d861196163e30c07add471562b45dce38517c9b2Colin Cross		for (sel = c->inputs; sel->input != NULL; sel++) {
913d861196163e30c07add471562b45dce38517c9b2Colin Cross			if (val >> PERIPH_CLK_SOURCE_SHIFT == sel->value)
914d861196163e30c07add471562b45dce38517c9b2Colin Cross				mux = sel;
915d861196163e30c07add471562b45dce38517c9b2Colin Cross		}
916d861196163e30c07add471562b45dce38517c9b2Colin Cross		BUG_ON(!mux);
917d861196163e30c07add471562b45dce38517c9b2Colin Cross
918d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->parent = mux->input;
919d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else {
920d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->parent = c->inputs[0].input;
921d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
922d861196163e30c07add471562b45dce38517c9b2Colin Cross
923d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & DIV_U71) {
92471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		u32 divu71 = val & PERIPH_CLK_SOURCE_DIVU71_MASK;
925d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->div = divu71 + 2;
926d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->mul = 2;
92771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	} else if (c->flags & DIV_U16) {
92871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		u32 divu16 = val & PERIPH_CLK_SOURCE_DIVU16_MASK;
92971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->div = divu16 + 1;
93071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->mul = 1;
931d861196163e30c07add471562b45dce38517c9b2Colin Cross	} else {
932d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->div = 1;
933d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->mul = 1;
934d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
935d861196163e30c07add471562b45dce38517c9b2Colin Cross
936d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->state = ON;
9371be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
9381be3d0537516fa42825406b4bc1291b77ed62614Colin Cross	if (!c->u.periph.clk_num)
9391be3d0537516fa42825406b4bc1291b77ed62614Colin Cross		return;
9401be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
941d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (!(clk_readl(CLK_OUT_ENB + PERIPH_CLK_TO_ENB_REG(c)) &
942d861196163e30c07add471562b45dce38517c9b2Colin Cross			PERIPH_CLK_TO_ENB_BIT(c)))
943d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->state = OFF;
9441be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
945d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (!(c->flags & PERIPH_NO_RESET))
946d861196163e30c07add471562b45dce38517c9b2Colin Cross		if (clk_readl(RST_DEVICES + PERIPH_CLK_TO_ENB_REG(c)) &
947d861196163e30c07add471562b45dce38517c9b2Colin Cross				PERIPH_CLK_TO_ENB_BIT(c))
948d861196163e30c07add471562b45dce38517c9b2Colin Cross			c->state = OFF;
949d861196163e30c07add471562b45dce38517c9b2Colin Cross}
950d861196163e30c07add471562b45dce38517c9b2Colin Cross
951d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_periph_clk_enable(struct clk *c)
952d861196163e30c07add471562b45dce38517c9b2Colin Cross{
953d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
95478f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	unsigned long flags;
95578f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	int refcount;
956d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
957d861196163e30c07add471562b45dce38517c9b2Colin Cross
9581be3d0537516fa42825406b4bc1291b77ed62614Colin Cross	if (!c->u.periph.clk_num)
9591be3d0537516fa42825406b4bc1291b77ed62614Colin Cross		return 0;
9601be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
96178f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	spin_lock_irqsave(&clock_register_lock, flags);
96278f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
96378f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	refcount = tegra_periph_clk_enable_refcount[c->u.periph.clk_num]++;
96478f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
96578f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	if (refcount > 1)
96678f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross		goto out;
96778f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
968d861196163e30c07add471562b45dce38517c9b2Colin Cross	clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
969d861196163e30c07add471562b45dce38517c9b2Colin Cross		CLK_OUT_ENB_SET + PERIPH_CLK_TO_ENB_SET_REG(c));
970d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (!(c->flags & PERIPH_NO_RESET) && !(c->flags & PERIPH_MANUAL_RESET))
971d861196163e30c07add471562b45dce38517c9b2Colin Cross		clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
972d861196163e30c07add471562b45dce38517c9b2Colin Cross			RST_DEVICES_CLR + PERIPH_CLK_TO_ENB_SET_REG(c));
973d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & PERIPH_EMC_ENB) {
974d861196163e30c07add471562b45dce38517c9b2Colin Cross		/* The EMC peripheral clock has 2 extra enable bits */
975d861196163e30c07add471562b45dce38517c9b2Colin Cross		/* FIXME: Do they need to be disabled? */
976d861196163e30c07add471562b45dce38517c9b2Colin Cross		val = clk_readl(c->reg);
977d861196163e30c07add471562b45dce38517c9b2Colin Cross		val |= 0x3 << 24;
978d861196163e30c07add471562b45dce38517c9b2Colin Cross		clk_writel(val, c->reg);
979d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
98078f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
98178f379b574dcbe656fa21ea72e95f8dff232e233Colin Crossout:
98278f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	spin_unlock_irqrestore(&clock_register_lock, flags);
98378f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
984d861196163e30c07add471562b45dce38517c9b2Colin Cross	return 0;
985d861196163e30c07add471562b45dce38517c9b2Colin Cross}
986d861196163e30c07add471562b45dce38517c9b2Colin Cross
987d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_periph_clk_disable(struct clk *c)
988d861196163e30c07add471562b45dce38517c9b2Colin Cross{
98978f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	unsigned long flags;
99078f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
991d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s on clock %s\n", __func__, c->name);
992d861196163e30c07add471562b45dce38517c9b2Colin Cross
9931be3d0537516fa42825406b4bc1291b77ed62614Colin Cross	if (!c->u.periph.clk_num)
9941be3d0537516fa42825406b4bc1291b77ed62614Colin Cross		return;
9951be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
99678f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	spin_lock_irqsave(&clock_register_lock, flags);
99778f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
99878f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	if (c->refcnt)
99978f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross		tegra_periph_clk_enable_refcount[c->u.periph.clk_num]--;
100078f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
100178f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	if (tegra_periph_clk_enable_refcount[c->u.periph.clk_num] == 0)
100278f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross		clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
100378f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross			CLK_OUT_ENB_CLR + PERIPH_CLK_TO_ENB_SET_REG(c));
100478f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross
100578f379b574dcbe656fa21ea72e95f8dff232e233Colin Cross	spin_unlock_irqrestore(&clock_register_lock, flags);
1006d861196163e30c07add471562b45dce38517c9b2Colin Cross}
1007d861196163e30c07add471562b45dce38517c9b2Colin Cross
10082b84cb4faab698b1708ce841c554546b1c9b2261Dima Zavinstatic void tegra2_periph_clk_reset(struct clk *c, bool assert)
1009d861196163e30c07add471562b45dce38517c9b2Colin Cross{
10102b84cb4faab698b1708ce841c554546b1c9b2261Dima Zavin	unsigned long base = assert ? RST_DEVICES_SET : RST_DEVICES_CLR;
1011d861196163e30c07add471562b45dce38517c9b2Colin Cross
10122b84cb4faab698b1708ce841c554546b1c9b2261Dima Zavin	pr_debug("%s %s on clock %s\n", __func__,
10132b84cb4faab698b1708ce841c554546b1c9b2261Dima Zavin		 assert ? "assert" : "deassert", c->name);
10141be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
10151be3d0537516fa42825406b4bc1291b77ed62614Colin Cross	BUG_ON(!c->u.periph.clk_num);
10161be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
1017d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (!(c->flags & PERIPH_NO_RESET))
1018d861196163e30c07add471562b45dce38517c9b2Colin Cross		clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
10192b84cb4faab698b1708ce841c554546b1c9b2261Dima Zavin			   base + PERIPH_CLK_TO_ENB_SET_REG(c));
1020d861196163e30c07add471562b45dce38517c9b2Colin Cross}
1021d861196163e30c07add471562b45dce38517c9b2Colin Cross
1022d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_periph_clk_set_parent(struct clk *c, struct clk *p)
1023d861196163e30c07add471562b45dce38517c9b2Colin Cross{
1024d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
1025d861196163e30c07add471562b45dce38517c9b2Colin Cross	const struct clk_mux_sel *sel;
1026d861196163e30c07add471562b45dce38517c9b2Colin Cross	pr_debug("%s: %s %s\n", __func__, c->name, p->name);
1027d861196163e30c07add471562b45dce38517c9b2Colin Cross	for (sel = c->inputs; sel->input != NULL; sel++) {
1028d861196163e30c07add471562b45dce38517c9b2Colin Cross		if (sel->input == p) {
1029d861196163e30c07add471562b45dce38517c9b2Colin Cross			val = clk_readl(c->reg);
1030d861196163e30c07add471562b45dce38517c9b2Colin Cross			val &= ~PERIPH_CLK_SOURCE_MASK;
1031d861196163e30c07add471562b45dce38517c9b2Colin Cross			val |= (sel->value) << PERIPH_CLK_SOURCE_SHIFT;
103271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
103371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			if (c->refcnt)
10344729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross				clk_enable(p);
103571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
1036d861196163e30c07add471562b45dce38517c9b2Colin Cross			clk_writel(val, c->reg);
103771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
103871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			if (c->refcnt && c->parent)
10394729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross				clk_disable(c->parent);
104071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
104171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			clk_reparent(c, p);
1042d861196163e30c07add471562b45dce38517c9b2Colin Cross			return 0;
1043d861196163e30c07add471562b45dce38517c9b2Colin Cross		}
1044d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
1045d861196163e30c07add471562b45dce38517c9b2Colin Cross
1046d861196163e30c07add471562b45dce38517c9b2Colin Cross	return -EINVAL;
1047d861196163e30c07add471562b45dce38517c9b2Colin Cross}
1048d861196163e30c07add471562b45dce38517c9b2Colin Cross
1049d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic int tegra2_periph_clk_set_rate(struct clk *c, unsigned long rate)
1050d861196163e30c07add471562b45dce38517c9b2Colin Cross{
1051d861196163e30c07add471562b45dce38517c9b2Colin Cross	u32 val;
105271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	int divider;
10534729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long parent_rate = clk_get_rate(c->parent);
10544729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross
1055d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (c->flags & DIV_U71) {
10564729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		divider = clk_div71_get_divider(parent_rate, rate);
105771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (divider >= 0) {
1058d861196163e30c07add471562b45dce38517c9b2Colin Cross			val = clk_readl(c->reg);
105971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val &= ~PERIPH_CLK_SOURCE_DIVU71_MASK;
106071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val |= divider;
1061d861196163e30c07add471562b45dce38517c9b2Colin Cross			clk_writel(val, c->reg);
106271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			c->div = divider + 2;
1063d861196163e30c07add471562b45dce38517c9b2Colin Cross			c->mul = 2;
1064d861196163e30c07add471562b45dce38517c9b2Colin Cross			return 0;
1065d861196163e30c07add471562b45dce38517c9b2Colin Cross		}
106671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	} else if (c->flags & DIV_U16) {
10674729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		divider = clk_div16_get_divider(parent_rate, rate);
106871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (divider >= 0) {
106971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val = clk_readl(c->reg);
107071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val &= ~PERIPH_CLK_SOURCE_DIVU16_MASK;
107171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val |= divider;
107271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			clk_writel(val, c->reg);
107371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			c->div = divider + 1;
107471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			c->mul = 1;
107571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			return 0;
107671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		}
10774729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	} else if (parent_rate <= rate) {
107871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->div = 1;
107971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		c->mul = 1;
108071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		return 0;
108171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
108271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	return -EINVAL;
108371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
108471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
108571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic long tegra2_periph_clk_round_rate(struct clk *c,
108671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	unsigned long rate)
108771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
108871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	int divider;
10894729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	unsigned long parent_rate = clk_get_rate(c->parent);
109071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	pr_debug("%s: %s %lu\n", __func__, c->name, rate);
109171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
109271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	if (c->flags & DIV_U71) {
10934729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		divider = clk_div71_get_divider(parent_rate, rate);
109471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (divider < 0)
109571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			return divider;
109671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
1097421186e71000c067c2687baeffde62954a80cdccColin Cross		return DIV_ROUND_UP(parent_rate * 2, divider + 2);
109871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	} else if (c->flags & DIV_U16) {
10994729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross		divider = clk_div16_get_divider(parent_rate, rate);
110071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (divider < 0)
110171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			return divider;
1102421186e71000c067c2687baeffde62954a80cdccColin Cross		return DIV_ROUND_UP(parent_rate, divider + 1);
1103d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
1104d861196163e30c07add471562b45dce38517c9b2Colin Cross	return -EINVAL;
1105d861196163e30c07add471562b45dce38517c9b2Colin Cross}
1106d861196163e30c07add471562b45dce38517c9b2Colin Cross
1107d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_ops tegra_periph_clk_ops = {
1108d861196163e30c07add471562b45dce38517c9b2Colin Cross	.init			= &tegra2_periph_clk_init,
1109d861196163e30c07add471562b45dce38517c9b2Colin Cross	.enable			= &tegra2_periph_clk_enable,
1110d861196163e30c07add471562b45dce38517c9b2Colin Cross	.disable		= &tegra2_periph_clk_disable,
1111d861196163e30c07add471562b45dce38517c9b2Colin Cross	.set_parent		= &tegra2_periph_clk_set_parent,
1112d861196163e30c07add471562b45dce38517c9b2Colin Cross	.set_rate		= &tegra2_periph_clk_set_rate,
111371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.round_rate		= &tegra2_periph_clk_round_rate,
11142b84cb4faab698b1708ce841c554546b1c9b2261Dima Zavin	.reset			= &tegra2_periph_clk_reset,
1115d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1116d861196163e30c07add471562b45dce38517c9b2Colin Cross
11179743b38969790d33b077ab80b175ea63a0398703Colin Cross/* The SDMMC controllers have extra bits in the clock source register that
11189743b38969790d33b077ab80b175ea63a0398703Colin Cross * adjust the delay between the clock and data to compenstate for delays
11199743b38969790d33b077ab80b175ea63a0398703Colin Cross * on the PCB. */
11209743b38969790d33b077ab80b175ea63a0398703Colin Crossvoid tegra2_sdmmc_tap_delay(struct clk *c, int delay)
11219743b38969790d33b077ab80b175ea63a0398703Colin Cross{
11229743b38969790d33b077ab80b175ea63a0398703Colin Cross	u32 reg;
1123742face03f57727b5a86d0df631e47a1ef0498d2Peter De Schrijver	unsigned long flags;
1124742face03f57727b5a86d0df631e47a1ef0498d2Peter De Schrijver
1125742face03f57727b5a86d0df631e47a1ef0498d2Peter De Schrijver	spin_lock_irqsave(&c->spinlock, flags);
11269743b38969790d33b077ab80b175ea63a0398703Colin Cross
11279743b38969790d33b077ab80b175ea63a0398703Colin Cross	delay = clamp(delay, 0, 15);
11289743b38969790d33b077ab80b175ea63a0398703Colin Cross	reg = clk_readl(c->reg);
11299743b38969790d33b077ab80b175ea63a0398703Colin Cross	reg &= ~SDMMC_CLK_INT_FB_DLY_MASK;
11309743b38969790d33b077ab80b175ea63a0398703Colin Cross	reg |= SDMMC_CLK_INT_FB_SEL;
11319743b38969790d33b077ab80b175ea63a0398703Colin Cross	reg |= delay << SDMMC_CLK_INT_FB_DLY_SHIFT;
11329743b38969790d33b077ab80b175ea63a0398703Colin Cross	clk_writel(reg, c->reg);
1133742face03f57727b5a86d0df631e47a1ef0498d2Peter De Schrijver
1134742face03f57727b5a86d0df631e47a1ef0498d2Peter De Schrijver	spin_unlock_irqrestore(&c->spinlock, flags);
11359743b38969790d33b077ab80b175ea63a0398703Colin Cross}
11369743b38969790d33b077ab80b175ea63a0398703Colin Cross
11376d2968284f63efa1d1849165f9e3a80402509212Colin Cross/* External memory controller clock ops */
11386d2968284f63efa1d1849165f9e3a80402509212Colin Crossstatic void tegra2_emc_clk_init(struct clk *c)
11396d2968284f63efa1d1849165f9e3a80402509212Colin Cross{
11406d2968284f63efa1d1849165f9e3a80402509212Colin Cross	tegra2_periph_clk_init(c);
11416d2968284f63efa1d1849165f9e3a80402509212Colin Cross	c->max_rate = clk_get_rate_locked(c);
11426d2968284f63efa1d1849165f9e3a80402509212Colin Cross}
11436d2968284f63efa1d1849165f9e3a80402509212Colin Cross
11446d2968284f63efa1d1849165f9e3a80402509212Colin Crossstatic long tegra2_emc_clk_round_rate(struct clk *c, unsigned long rate)
11456d2968284f63efa1d1849165f9e3a80402509212Colin Cross{
1146e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	long emc_rate;
1147e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	long clk_rate;
11486d2968284f63efa1d1849165f9e3a80402509212Colin Cross
1149e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	/*
1150e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * The slowest entry in the EMC clock table that is at least as
1151e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * fast as rate.
1152e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 */
1153e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	emc_rate = tegra_emc_round_rate(rate);
1154e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	if (emc_rate < 0)
11556d2968284f63efa1d1849165f9e3a80402509212Colin Cross		return c->max_rate;
11566d2968284f63efa1d1849165f9e3a80402509212Colin Cross
1157e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	/*
1158e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * The fastest rate the PLL will generate that is at most the
1159e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * requested rate.
1160e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 */
1161e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	clk_rate = tegra2_periph_clk_round_rate(c, emc_rate);
1162e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren
1163e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	/*
1164e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * If this fails, and emc_rate > clk_rate, it's because the maximum
1165e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * rate in the EMC tables is larger than the maximum rate of the EMC
1166e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * clock. The EMC clock's max rate is the rate it was running when the
1167e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * kernel booted. Such a mismatch is probably due to using the wrong
1168e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 * BCT, i.e. using a Tegra20 BCT with an EMC table written for Tegra25.
1169e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	 */
1170e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	WARN_ONCE(emc_rate != clk_rate,
1171e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren		"emc_rate %ld != clk_rate %ld",
1172e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren		emc_rate, clk_rate);
11736d2968284f63efa1d1849165f9e3a80402509212Colin Cross
1174e186ad74c0941f5caeda28bde76dab903b342c1cStephen Warren	return emc_rate;
11756d2968284f63efa1d1849165f9e3a80402509212Colin Cross}
11766d2968284f63efa1d1849165f9e3a80402509212Colin Cross
11776d2968284f63efa1d1849165f9e3a80402509212Colin Crossstatic int tegra2_emc_clk_set_rate(struct clk *c, unsigned long rate)
11786d2968284f63efa1d1849165f9e3a80402509212Colin Cross{
11796d2968284f63efa1d1849165f9e3a80402509212Colin Cross	int ret;
11806d2968284f63efa1d1849165f9e3a80402509212Colin Cross	/*
11816d2968284f63efa1d1849165f9e3a80402509212Colin Cross	 * The Tegra2 memory controller has an interlock with the clock
11826d2968284f63efa1d1849165f9e3a80402509212Colin Cross	 * block that allows memory shadowed registers to be updated,
11836d2968284f63efa1d1849165f9e3a80402509212Colin Cross	 * and then transfer them to the main registers at the same
11846d2968284f63efa1d1849165f9e3a80402509212Colin Cross	 * time as the clock update without glitches.
11856d2968284f63efa1d1849165f9e3a80402509212Colin Cross	 */
11866d2968284f63efa1d1849165f9e3a80402509212Colin Cross	ret = tegra_emc_set_rate(rate);
11876d2968284f63efa1d1849165f9e3a80402509212Colin Cross	if (ret < 0)
11886d2968284f63efa1d1849165f9e3a80402509212Colin Cross		return ret;
11896d2968284f63efa1d1849165f9e3a80402509212Colin Cross
11906d2968284f63efa1d1849165f9e3a80402509212Colin Cross	ret = tegra2_periph_clk_set_rate(c, rate);
11916d2968284f63efa1d1849165f9e3a80402509212Colin Cross	udelay(1);
11926d2968284f63efa1d1849165f9e3a80402509212Colin Cross
11936d2968284f63efa1d1849165f9e3a80402509212Colin Cross	return ret;
11946d2968284f63efa1d1849165f9e3a80402509212Colin Cross}
11956d2968284f63efa1d1849165f9e3a80402509212Colin Cross
11966d2968284f63efa1d1849165f9e3a80402509212Colin Crossstatic struct clk_ops tegra_emc_clk_ops = {
11976d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.init			= &tegra2_emc_clk_init,
11986d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.enable			= &tegra2_periph_clk_enable,
11996d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.disable		= &tegra2_periph_clk_disable,
12006d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.set_parent		= &tegra2_periph_clk_set_parent,
12016d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.set_rate		= &tegra2_emc_clk_set_rate,
12026d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.round_rate		= &tegra2_emc_clk_round_rate,
12036d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.reset			= &tegra2_periph_clk_reset,
12046d2968284f63efa1d1849165f9e3a80402509212Colin Cross};
12056d2968284f63efa1d1849165f9e3a80402509212Colin Cross
1206d861196163e30c07add471562b45dce38517c9b2Colin Cross/* Clock doubler ops */
1207d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic void tegra2_clk_double_init(struct clk *c)
1208d861196163e30c07add471562b45dce38517c9b2Colin Cross{
1209d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->mul = 2;
1210d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->div = 1;
1211d861196163e30c07add471562b45dce38517c9b2Colin Cross	c->state = ON;
12121be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
12131be3d0537516fa42825406b4bc1291b77ed62614Colin Cross	if (!c->u.periph.clk_num)
12141be3d0537516fa42825406b4bc1291b77ed62614Colin Cross		return;
12151be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
1216d861196163e30c07add471562b45dce38517c9b2Colin Cross	if (!(clk_readl(CLK_OUT_ENB + PERIPH_CLK_TO_ENB_REG(c)) &
1217d861196163e30c07add471562b45dce38517c9b2Colin Cross			PERIPH_CLK_TO_ENB_BIT(c)))
1218d861196163e30c07add471562b45dce38517c9b2Colin Cross		c->state = OFF;
1219d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1220d861196163e30c07add471562b45dce38517c9b2Colin Cross
122171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic int tegra2_clk_double_set_rate(struct clk *c, unsigned long rate)
122271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
12234729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross	if (rate != 2 * clk_get_rate(c->parent))
122471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		return -EINVAL;
122571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	c->mul = 2;
122671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	c->div = 1;
122771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	return 0;
122871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
122971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
1230d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_ops tegra_clk_double_ops = {
1231d861196163e30c07add471562b45dce38517c9b2Colin Cross	.init			= &tegra2_clk_double_init,
1232d861196163e30c07add471562b45dce38517c9b2Colin Cross	.enable			= &tegra2_periph_clk_enable,
1233d861196163e30c07add471562b45dce38517c9b2Colin Cross	.disable		= &tegra2_periph_clk_disable,
123471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.set_rate		= &tegra2_clk_double_set_rate,
123571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross};
123671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
1237cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross/* Audio sync clock ops */
123871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic void tegra2_audio_sync_clk_init(struct clk *c)
123971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
124071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	int source;
124171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	const struct clk_mux_sel *sel;
124271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	u32 val = clk_readl(c->reg);
124371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	c->state = (val & (1<<4)) ? OFF : ON;
124471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	source = val & 0xf;
124571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (sel = c->inputs; sel->input != NULL; sel++)
124671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (sel->value == source)
124771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			break;
124871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	BUG_ON(sel->input == NULL);
124971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	c->parent = sel->input;
125071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
125171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
125271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic int tegra2_audio_sync_clk_enable(struct clk *c)
125371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
125471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	clk_writel(0, c->reg);
125571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	return 0;
125671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
125771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
125871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic void tegra2_audio_sync_clk_disable(struct clk *c)
125971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
126071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	clk_writel(1, c->reg);
126171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
126271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
126371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic int tegra2_audio_sync_clk_set_parent(struct clk *c, struct clk *p)
126471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
126571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	u32 val;
126671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	const struct clk_mux_sel *sel;
126771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (sel = c->inputs; sel->input != NULL; sel++) {
126871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (sel->input == p) {
126971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val = clk_readl(c->reg);
127071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val &= ~0xf;
127171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			val |= sel->value;
127271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
127371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			if (c->refcnt)
12744729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross				clk_enable(p);
127571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
127671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			clk_writel(val, c->reg);
127771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
127871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			if (c->refcnt && c->parent)
12794729fd7a7dfe7847b4870801ad12222adaeb016cColin Cross				clk_disable(c->parent);
128071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
128171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			clk_reparent(c, p);
128271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			return 0;
128371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		}
128471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
128571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
128671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	return -EINVAL;
128771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
128871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
128971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk_ops tegra_audio_sync_clk_ops = {
129071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.init       = tegra2_audio_sync_clk_init,
129171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.enable     = tegra2_audio_sync_clk_enable,
129271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.disable    = tegra2_audio_sync_clk_disable,
129371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.set_parent = tegra2_audio_sync_clk_set_parent,
1294d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1295d861196163e30c07add471562b45dce38517c9b2Colin Cross
1296cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross/* cdev1 and cdev2 (dap_mclk1 and dap_mclk2) ops */
1297cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1298cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic void tegra2_cdev_clk_init(struct clk *c)
1299cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross{
1300cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	/* We could un-tristate the cdev1 or cdev2 pingroup here; this is
1301cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	 * currently done in the pinmux code. */
1302cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	c->state = ON;
13031be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
13041be3d0537516fa42825406b4bc1291b77ed62614Colin Cross	BUG_ON(!c->u.periph.clk_num);
13051be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
1306cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	if (!(clk_readl(CLK_OUT_ENB + PERIPH_CLK_TO_ENB_REG(c)) &
1307cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross			PERIPH_CLK_TO_ENB_BIT(c)))
1308cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		c->state = OFF;
1309cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross}
1310cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1311cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic int tegra2_cdev_clk_enable(struct clk *c)
1312cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross{
13131be3d0537516fa42825406b4bc1291b77ed62614Colin Cross	BUG_ON(!c->u.periph.clk_num);
13141be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
1315cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
1316cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		CLK_OUT_ENB_SET + PERIPH_CLK_TO_ENB_SET_REG(c));
1317cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	return 0;
1318cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross}
1319cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1320cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic void tegra2_cdev_clk_disable(struct clk *c)
1321cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross{
13221be3d0537516fa42825406b4bc1291b77ed62614Colin Cross	BUG_ON(!c->u.periph.clk_num);
13231be3d0537516fa42825406b4bc1291b77ed62614Colin Cross
1324cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(PERIPH_CLK_TO_ENB_BIT(c),
1325cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross		CLK_OUT_ENB_CLR + PERIPH_CLK_TO_ENB_SET_REG(c));
1326cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross}
1327cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1328cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic struct clk_ops tegra_cdev_clk_ops = {
1329cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.init			= &tegra2_cdev_clk_init,
1330cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.enable			= &tegra2_cdev_clk_enable,
1331cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.disable		= &tegra2_cdev_clk_disable,
1332cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross};
1333cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1334310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross/* shared bus ops */
1335310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross/*
1336310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross * Some clocks may have multiple downstream users that need to request a
1337310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross * higher clock rate.  Shared bus clocks provide a unique shared_bus_user
1338310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross * clock to each user.  The frequency of the bus is set to the highest
1339310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross * enabled shared_bus_user clock, with a minimum value set by the
1340310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross * shared bus.
1341310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross */
1342310992ca4b994db8c869e1c0f32c004b7a196147Colin Crossstatic int tegra_clk_shared_bus_update(struct clk *bus)
1343310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross{
1344310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	struct clk *c;
1345310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	unsigned long rate = bus->min_rate;
1346310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1347310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	list_for_each_entry(c, &bus->shared_bus_list, u.shared_bus_user.node)
1348310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross		if (c->u.shared_bus_user.enabled)
1349310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross			rate = max(c->u.shared_bus_user.rate, rate);
1350310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1351310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	if (rate == clk_get_rate_locked(bus))
1352310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross		return 0;
1353310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1354310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	return clk_set_rate_locked(bus, rate);
1355310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross};
1356310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1357310992ca4b994db8c869e1c0f32c004b7a196147Colin Crossstatic void tegra_clk_shared_bus_init(struct clk *c)
1358310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross{
1359310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	unsigned long flags;
1360310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1361310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	c->max_rate = c->parent->max_rate;
1362310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	c->u.shared_bus_user.rate = c->parent->max_rate;
1363310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	c->state = OFF;
1364310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	c->set = true;
1365310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1366310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	spin_lock_irqsave(&c->parent->spinlock, flags);
1367310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1368310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	list_add_tail(&c->u.shared_bus_user.node,
1369310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross		&c->parent->shared_bus_list);
1370310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1371310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	spin_unlock_irqrestore(&c->parent->spinlock, flags);
1372310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross}
1373310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1374310992ca4b994db8c869e1c0f32c004b7a196147Colin Crossstatic int tegra_clk_shared_bus_set_rate(struct clk *c, unsigned long rate)
1375310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross{
1376310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	unsigned long flags;
1377310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	int ret;
1378906c3b616dcf8e64b11d7d665d62f5e9940f4d46Nicolas Kaiser	long new_rate = rate;
1379310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1380906c3b616dcf8e64b11d7d665d62f5e9940f4d46Nicolas Kaiser	new_rate = clk_round_rate(c->parent, new_rate);
1381906c3b616dcf8e64b11d7d665d62f5e9940f4d46Nicolas Kaiser	if (new_rate < 0)
1382906c3b616dcf8e64b11d7d665d62f5e9940f4d46Nicolas Kaiser		return new_rate;
1383310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1384310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	spin_lock_irqsave(&c->parent->spinlock, flags);
1385310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1386906c3b616dcf8e64b11d7d665d62f5e9940f4d46Nicolas Kaiser	c->u.shared_bus_user.rate = new_rate;
1387310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	ret = tegra_clk_shared_bus_update(c->parent);
1388310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1389310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	spin_unlock_irqrestore(&c->parent->spinlock, flags);
1390310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1391310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	return ret;
1392310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross}
1393310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1394310992ca4b994db8c869e1c0f32c004b7a196147Colin Crossstatic long tegra_clk_shared_bus_round_rate(struct clk *c, unsigned long rate)
1395310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross{
1396310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	return clk_round_rate(c->parent, rate);
1397310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross}
1398310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1399310992ca4b994db8c869e1c0f32c004b7a196147Colin Crossstatic int tegra_clk_shared_bus_enable(struct clk *c)
1400310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross{
1401310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	unsigned long flags;
1402310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	int ret;
1403310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1404310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	spin_lock_irqsave(&c->parent->spinlock, flags);
1405310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1406310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	c->u.shared_bus_user.enabled = true;
1407310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	ret = tegra_clk_shared_bus_update(c->parent);
1408310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1409310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	spin_unlock_irqrestore(&c->parent->spinlock, flags);
1410310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1411310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	return ret;
1412310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross}
1413310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1414310992ca4b994db8c869e1c0f32c004b7a196147Colin Crossstatic void tegra_clk_shared_bus_disable(struct clk *c)
1415310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross{
1416310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	unsigned long flags;
1417310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	int ret;
1418310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1419310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	spin_lock_irqsave(&c->parent->spinlock, flags);
1420310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1421310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	c->u.shared_bus_user.enabled = false;
1422310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	ret = tegra_clk_shared_bus_update(c->parent);
1423310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	WARN_ON_ONCE(ret);
1424310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1425310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	spin_unlock_irqrestore(&c->parent->spinlock, flags);
1426310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross}
1427310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1428310992ca4b994db8c869e1c0f32c004b7a196147Colin Crossstatic struct clk_ops tegra_clk_shared_bus_ops = {
1429310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	.init = tegra_clk_shared_bus_init,
1430310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	.enable = tegra_clk_shared_bus_enable,
1431310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	.disable = tegra_clk_shared_bus_disable,
1432310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	.set_rate = tegra_clk_shared_bus_set_rate,
1433310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	.round_rate = tegra_clk_shared_bus_round_rate,
1434310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross};
1435310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1436310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
1437d861196163e30c07add471562b45dce38517c9b2Colin Cross/* Clock definitions */
1438d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_clk_32k = {
1439d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name = "clk_32k",
144071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.rate = 32768,
1441d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops  = NULL,
144271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate = 32768,
1443d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1444d861196163e30c07add471562b45dce38517c9b2Colin Cross
1445f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_s_freq_table[] = {
1446d861196163e30c07add471562b45dce38517c9b2Colin Cross	{32768, 12000000, 366, 1, 1, 0},
1447d861196163e30c07add471562b45dce38517c9b2Colin Cross	{32768, 13000000, 397, 1, 1, 0},
1448d861196163e30c07add471562b45dce38517c9b2Colin Cross	{32768, 19200000, 586, 1, 1, 0},
1449d861196163e30c07add471562b45dce38517c9b2Colin Cross	{32768, 26000000, 793, 1, 1, 0},
1450d861196163e30c07add471562b45dce38517c9b2Colin Cross	{0, 0, 0, 0, 0, 0},
1451d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1452d861196163e30c07add471562b45dce38517c9b2Colin Cross
1453d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_s = {
1454d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_s",
1455d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = PLL_ALT_MISC_REG,
1456d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_ops,
1457d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_clk_32k,
145871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 26000000,
1459f151961173bf28047d01b410969f05e485f56d7eColin Cross	.reg       = 0xf0,
1460f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1461f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 32768,
1462f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 32768,
1463f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_min    = 0, /* FIXME */
1464f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_max    = 0, /* FIXME */
1465f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_min   = 12000000,
1466f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_max   = 26000000,
1467f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_s_freq_table,
1468f151961173bf28047d01b410969f05e485f56d7eColin Cross		.lock_delay = 300,
1469f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1470d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1471d861196163e30c07add471562b45dce38517c9b2Colin Cross
1472d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel tegra_clk_m_sel[] = {
1473d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_32k, .value = 0},
1474d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_s,  .value = 1},
147545fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL , 0},
1476d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1477f151961173bf28047d01b410969f05e485f56d7eColin Cross
1478d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_clk_m = {
1479d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "clk_m",
1480d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = ENABLE_ON_INIT,
1481d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_clk_m_ops,
1482d861196163e30c07add471562b45dce38517c9b2Colin Cross	.inputs    = tegra_clk_m_sel,
1483d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0x1fc,
1484d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 28,
148571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 26000000,
1486d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1487d861196163e30c07add471562b45dce38517c9b2Colin Cross
1488f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_c_freq_table[] = {
1489d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 0, 0, 0, 0, 0, 0 },
1490d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1491d861196163e30c07add471562b45dce38517c9b2Colin Cross
1492d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_c = {
1493d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_c",
1494d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags	   = PLL_HAS_CPCON,
1495d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_ops,
1496d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0x80,
1497d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_clk_m,
149871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 600000000,
1499f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1500f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 2000000,
1501f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 31000000,
1502f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_min    = 1000000,
1503f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_max    = 6000000,
1504f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_min   = 20000000,
1505f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_max   = 1400000000,
1506f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_c_freq_table,
1507f151961173bf28047d01b410969f05e485f56d7eColin Cross		.lock_delay = 300,
1508f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1509d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1510d861196163e30c07add471562b45dce38517c9b2Colin Cross
1511d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_c_out1 = {
1512d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_c_out1",
1513d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_div_ops,
1514d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = DIV_U71,
1515d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_c,
1516d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0x84,
1517d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 0,
151871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 600000000,
1519d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1520d861196163e30c07add471562b45dce38517c9b2Colin Cross
1521f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_m_freq_table[] = {
152271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 12000000, 666000000, 666, 12, 1, 8},
152371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 13000000, 666000000, 666, 13, 1, 8},
152471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 666000000, 555, 16, 1, 8},
152571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 26000000, 666000000, 666, 26, 1, 8},
152671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 12000000, 600000000, 600, 12, 1, 8},
152771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 13000000, 600000000, 600, 13, 1, 8},
152871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 600000000, 375, 12, 1, 6},
152971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 26000000, 600000000, 600, 26, 1, 8},
1530d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 0, 0, 0, 0, 0, 0 },
1531d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1532d861196163e30c07add471562b45dce38517c9b2Colin Cross
1533d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_m = {
1534d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_m",
1535d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = PLL_HAS_CPCON,
1536d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_ops,
1537d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0x90,
1538d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_clk_m,
153971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 800000000,
1540f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1541f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 2000000,
1542f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 31000000,
1543f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_min    = 1000000,
1544f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_max    = 6000000,
1545f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_min   = 20000000,
1546f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_max   = 1200000000,
1547f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_m_freq_table,
1548f151961173bf28047d01b410969f05e485f56d7eColin Cross		.lock_delay = 300,
1549f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1550d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1551d861196163e30c07add471562b45dce38517c9b2Colin Cross
1552d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_m_out1 = {
1553d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_m_out1",
1554d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_div_ops,
1555d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = DIV_U71,
1556d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_m,
1557d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0x94,
1558d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 0,
155971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 600000000,
1560d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1561d861196163e30c07add471562b45dce38517c9b2Colin Cross
1562f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_p_freq_table[] = {
1563d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 12000000, 216000000, 432, 12, 2, 8},
1564d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 13000000, 216000000, 432, 13, 2, 8},
1565d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 19200000, 216000000, 90,   4, 2, 1},
1566d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 26000000, 216000000, 432, 26, 2, 8},
1567d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 12000000, 432000000, 432, 12, 1, 8},
1568d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 13000000, 432000000, 432, 13, 1, 8},
1569d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 19200000, 432000000, 90,   4, 1, 1},
1570d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 26000000, 432000000, 432, 26, 1, 8},
1571d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 0, 0, 0, 0, 0, 0 },
1572d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1573d861196163e30c07add471562b45dce38517c9b2Colin Cross
1574d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_p = {
1575d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_p",
1576d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = ENABLE_ON_INIT | PLL_FIXED | PLL_HAS_CPCON,
1577d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_ops,
1578d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xa0,
1579d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_clk_m,
158071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 432000000,
1581f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1582f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 2000000,
1583f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 31000000,
1584f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_min    = 1000000,
1585f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_max    = 6000000,
1586f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_min   = 20000000,
1587f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_max   = 1400000000,
1588f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_p_freq_table,
1589f151961173bf28047d01b410969f05e485f56d7eColin Cross		.lock_delay = 300,
1590f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1591d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1592d861196163e30c07add471562b45dce38517c9b2Colin Cross
1593d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_p_out1 = {
1594d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_p_out1",
1595d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_div_ops,
1596d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = ENABLE_ON_INIT | DIV_U71 | DIV_U71_FIXED,
1597d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_p,
1598d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xa4,
1599d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 0,
160071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 432000000,
1601d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1602d861196163e30c07add471562b45dce38517c9b2Colin Cross
1603d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_p_out2 = {
1604d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_p_out2",
1605d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_div_ops,
1606d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = ENABLE_ON_INIT | DIV_U71 | DIV_U71_FIXED,
1607d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_p,
1608d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xa4,
1609d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 16,
161071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 432000000,
1611d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1612d861196163e30c07add471562b45dce38517c9b2Colin Cross
1613d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_p_out3 = {
1614d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_p_out3",
1615d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_div_ops,
1616d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = ENABLE_ON_INIT | DIV_U71 | DIV_U71_FIXED,
1617d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_p,
1618d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xa8,
1619d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 0,
162071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 432000000,
1621d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1622d861196163e30c07add471562b45dce38517c9b2Colin Cross
1623d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_p_out4 = {
1624d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_p_out4",
1625d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_div_ops,
1626d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = ENABLE_ON_INIT | DIV_U71 | DIV_U71_FIXED,
1627d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_p,
1628d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xa8,
1629d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 16,
163071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 432000000,
1631d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1632d861196163e30c07add471562b45dce38517c9b2Colin Cross
1633f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_a_freq_table[] = {
1634d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 28800000, 56448000, 49, 25, 1, 1},
1635d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 28800000, 73728000, 64, 25, 1, 1},
163671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 28800000, 24000000,  5,  6, 1, 1},
1637d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 0, 0, 0, 0, 0, 0 },
1638d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1639d861196163e30c07add471562b45dce38517c9b2Colin Cross
1640d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_a = {
1641d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_a",
1642d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = PLL_HAS_CPCON,
1643d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_ops,
1644d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xb0,
1645d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_p_out1,
16469c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.max_rate  = 73728000,
1647f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1648f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 2000000,
1649f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 31000000,
1650f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_min    = 1000000,
1651f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_max    = 6000000,
1652f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_min   = 20000000,
1653f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_max   = 1400000000,
1654f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_a_freq_table,
1655f151961173bf28047d01b410969f05e485f56d7eColin Cross		.lock_delay = 300,
1656f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1657d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1658d861196163e30c07add471562b45dce38517c9b2Colin Cross
1659d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_a_out0 = {
1660d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_a_out0",
1661d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_div_ops,
1662d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = DIV_U71,
1663d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_a,
1664d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xb4,
1665d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 0,
16669c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.max_rate  = 73728000,
1667d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1668d861196163e30c07add471562b45dce38517c9b2Colin Cross
1669f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_d_freq_table[] = {
1670cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	{ 12000000, 216000000, 216, 12, 1, 4},
1671cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	{ 13000000, 216000000, 216, 13, 1, 4},
1672cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	{ 19200000, 216000000, 135, 12, 1, 3},
1673cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	{ 26000000, 216000000, 216, 26, 1, 4},
1674cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1675cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	{ 12000000, 594000000, 594, 12, 1, 8},
1676cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	{ 13000000, 594000000, 594, 13, 1, 8},
1677cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	{ 19200000, 594000000, 495, 16, 1, 8},
1678cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	{ 26000000, 594000000, 594, 26, 1, 8},
1679cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1680d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 12000000, 1000000000, 1000, 12, 1, 12},
1681d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 13000000, 1000000000, 1000, 13, 1, 12},
1682d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 19200000, 1000000000, 625,  12, 1, 8},
1683d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 26000000, 1000000000, 1000, 26, 1, 12},
1684cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1685d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 0, 0, 0, 0, 0, 0 },
1686d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1687d861196163e30c07add471562b45dce38517c9b2Colin Cross
1688d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_d = {
1689d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_d",
1690d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = PLL_HAS_CPCON | PLLD,
1691d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_ops,
1692d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xd0,
1693d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_clk_m,
169471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 1000000000,
1695f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1696f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 2000000,
1697f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 40000000,
1698f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_min    = 1000000,
1699f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_max    = 6000000,
1700f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_min   = 40000000,
1701f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_max   = 1000000000,
1702f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_d_freq_table,
1703f151961173bf28047d01b410969f05e485f56d7eColin Cross		.lock_delay = 1000,
1704f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1705d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1706d861196163e30c07add471562b45dce38517c9b2Colin Cross
1707d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_d_out0 = {
1708d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_d_out0",
1709d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_div_ops,
1710d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = DIV_2 | PLLD,
1711d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_pll_d,
171271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 500000000,
1713d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1714d861196163e30c07add471562b45dce38517c9b2Colin Cross
1715f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_u_freq_table[] = {
171671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 12000000, 480000000, 960, 12, 2, 0},
171771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 13000000, 480000000, 960, 13, 2, 0},
171871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 480000000, 200, 4,  2, 0},
171971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 26000000, 480000000, 960, 26, 2, 0},
1720d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 0, 0, 0, 0, 0, 0 },
1721d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1722d861196163e30c07add471562b45dce38517c9b2Colin Cross
1723d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_u = {
1724d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_u",
172571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.flags     = PLLU,
1726d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_pll_ops,
1727d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xc0,
1728d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_clk_m,
172971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 480000000,
1730f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1731f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 2000000,
1732f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 40000000,
1733f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_min    = 1000000,
1734f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_max    = 6000000,
1735f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_min   = 480000000,
1736f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_max   = 960000000,
1737f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_u_freq_table,
1738f151961173bf28047d01b410969f05e485f56d7eColin Cross		.lock_delay = 1000,
1739f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1740f151961173bf28047d01b410969f05e485f56d7eColin Cross};
1741f151961173bf28047d01b410969f05e485f56d7eColin Cross
1742f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_x_freq_table[] = {
174371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* 1 GHz */
1744d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 12000000, 1000000000, 1000, 12, 1, 12},
1745d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 13000000, 1000000000, 1000, 13, 1, 12},
1746d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 19200000, 1000000000, 625,  12, 1, 8},
1747d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 26000000, 1000000000, 1000, 26, 1, 12},
174871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
174971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* 912 MHz */
175071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 12000000, 912000000,  912,  12, 1, 12},
175171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 13000000, 912000000,  912,  13, 1, 12},
175271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 912000000,  760,  16, 1, 8},
175371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 26000000, 912000000,  912,  26, 1, 12},
175471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
175571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* 816 MHz */
175671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 12000000, 816000000,  816,  12, 1, 12},
175771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 13000000, 816000000,  816,  13, 1, 12},
175871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 816000000,  680,  16, 1, 8},
175971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 26000000, 816000000,  816,  26, 1, 12},
176071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
176171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* 760 MHz */
176271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 12000000, 760000000,  760,  12, 1, 12},
176371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 13000000, 760000000,  760,  13, 1, 12},
176471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 760000000,  950,  24, 1, 8},
176571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 26000000, 760000000,  760,  26, 1, 12},
176671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
176771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* 608 MHz */
17689c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	{ 12000000, 608000000,  608,  12, 1, 12},
17699c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	{ 13000000, 608000000,  608,  13, 1, 12},
177071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 608000000,  380,  12, 1, 8},
17719c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	{ 26000000, 608000000,  608,  26, 1, 12},
177271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
177371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* 456 MHz */
177471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 12000000, 456000000,  456,  12, 1, 12},
177571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 13000000, 456000000,  456,  13, 1, 12},
177671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 456000000,  380,  16, 1, 8},
177771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 26000000, 456000000,  456,  26, 1, 12},
177871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
177971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* 312 MHz */
178071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 12000000, 312000000,  312,  12, 1, 12},
178171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 13000000, 312000000,  312,  13, 1, 12},
178271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 19200000, 312000000,  260,  16, 1, 8},
178371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ 26000000, 312000000,  312,  26, 1, 12},
178471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
1785d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ 0, 0, 0, 0, 0, 0 },
1786d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1787d861196163e30c07add471562b45dce38517c9b2Colin Cross
1788d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_pll_x = {
1789d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "pll_x",
1790d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = PLL_HAS_CPCON | PLL_ALT_MISC_REG,
179171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.ops       = &tegra_pllx_ops,
1792d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0xe0,
1793d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_clk_m,
179471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 1000000000,
1795f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1796f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 2000000,
1797f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 31000000,
1798f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_min    = 1000000,
1799f151961173bf28047d01b410969f05e485f56d7eColin Cross		.cf_max    = 6000000,
1800f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_min   = 20000000,
1801f151961173bf28047d01b410969f05e485f56d7eColin Cross		.vco_max   = 1200000000,
1802f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_x_freq_table,
1803f151961173bf28047d01b410969f05e485f56d7eColin Cross		.lock_delay = 300,
1804f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1805f151961173bf28047d01b410969f05e485f56d7eColin Cross};
1806f151961173bf28047d01b410969f05e485f56d7eColin Cross
1807f151961173bf28047d01b410969f05e485f56d7eColin Crossstatic struct clk_pll_freq_table tegra_pll_e_freq_table[] = {
18088d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	{ 12000000, 100000000,  200,  24, 1, 0 },
18098d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	{ 0, 0, 0, 0, 0, 0 },
18108d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport};
18118d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
18128d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoportstatic struct clk tegra_pll_e = {
18138d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	.name      = "pll_e",
18148d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	.flags	   = PLL_ALT_MISC_REG,
18158d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	.ops       = &tegra_plle_ops,
18168d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	.parent    = &tegra_clk_m,
18178d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	.reg       = 0xe8,
1818f151961173bf28047d01b410969f05e485f56d7eColin Cross	.max_rate  = 100000000,
1819f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.pll = {
1820f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_min = 12000000,
1821f151961173bf28047d01b410969f05e485f56d7eColin Cross		.input_max = 12000000,
1822f151961173bf28047d01b410969f05e485f56d7eColin Cross		.freq_table = tegra_pll_e_freq_table,
1823f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
18248d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport};
18258d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport
1826d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_clk_d = {
1827d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name      = "clk_d",
1828d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = PERIPH_NO_RESET,
1829d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_clk_double_ops,
1830d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0x34,
1831d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 12,
1832d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent    = &tegra_clk_m,
183371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 52000000,
1834f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.periph  = {
1835f151961173bf28047d01b410969f05e485f56d7eColin Cross		.clk_num = 90,
1836f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
183771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross};
183871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
1839cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross/* dap_mclk1, belongs to the cdev1 pingroup. */
1840ddb7d5d80edb58e8235f1bc6c350eac40bfe85d1Stephen Warrenstatic struct clk tegra_clk_cdev1 = {
1841ddb7d5d80edb58e8235f1bc6c350eac40bfe85d1Stephen Warren	.name      = "cdev1",
1842cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.ops       = &tegra_cdev_clk_ops,
1843cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.rate      = 26000000,
1844cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.max_rate  = 26000000,
1845f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.periph  = {
1846f151961173bf28047d01b410969f05e485f56d7eColin Cross		.clk_num = 94,
1847f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1848cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross};
1849cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
1850cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross/* dap_mclk2, belongs to the cdev2 pingroup. */
1851ddb7d5d80edb58e8235f1bc6c350eac40bfe85d1Stephen Warrenstatic struct clk tegra_clk_cdev2 = {
1852ddb7d5d80edb58e8235f1bc6c350eac40bfe85d1Stephen Warren	.name      = "cdev2",
1853cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.ops       = &tegra_cdev_clk_ops,
1854cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.rate      = 26000000,
1855cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.max_rate  = 26000000,
1856f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.periph  = {
1857f151961173bf28047d01b410969f05e485f56d7eColin Cross		.clk_num   = 93,
1858f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1859cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross};
1860cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
186171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross/* initialized before peripheral clocks */
186271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk_mux_sel mux_audio_sync_clk[8+1];
186371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic const struct audio_sources {
186471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	const char *name;
186571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	int value;
186671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross} mux_audio_sync_clk_sources[] = {
186771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .name = "spdif_in", .value = 0 },
186871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .name = "i2s1", .value = 1 },
186971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .name = "i2s2", .value = 2 },
187071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .name = "pll_a_out0", .value = 4 },
187171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#if 0 /* FIXME: not implemented */
187271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .name = "ac97", .value = 3 },
187371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .name = "ext_audio_clk2", .value = 5 },
187471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .name = "ext_audio_clk1", .value = 6 },
187571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .name = "ext_vimclk", .value = 7 },
187671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#endif
187745fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0 }
187871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross};
187971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
188071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk tegra_clk_audio = {
188171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.name      = "audio",
188271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.inputs    = mux_audio_sync_clk,
188371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.reg       = 0x38,
18849c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.max_rate  = 73728000,
188571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.ops       = &tegra_audio_sync_clk_ops
1886d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1887d861196163e30c07add471562b45dce38517c9b2Colin Cross
1888d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_clk_audio_2x = {
188971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.name      = "audio_2x",
1890d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags     = PERIPH_NO_RESET,
189171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 48000000,
1892d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops       = &tegra_clk_double_ops,
1893d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg       = 0x34,
1894d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift = 8,
189571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.parent    = &tegra_clk_audio,
1896f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.periph = {
1897f151961173bf28047d01b410969f05e485f56d7eColin Cross		.clk_num = 89,
1898f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
189971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross};
190071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
190187c6e46a2c96ce2081070701237c58ed7eec94e7Olof Johanssonstatic struct clk_lookup tegra_audio_clk_lookups[] = {
190271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .con_id = "audio", .clk = &tegra_clk_audio },
190371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{ .con_id = "audio_2x", .clk = &tegra_clk_audio_2x }
190471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross};
190571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
190671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross/* This is called after peripheral clocks are initialized, as the
190771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross * audio_sync clock depends on some of the peripheral clocks.
190871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross */
190971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
191071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic void init_audio_sync_clock_mux(void)
191171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
191271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	int i;
191371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	struct clk_mux_sel *sel = mux_audio_sync_clk;
191471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	const struct audio_sources *src = mux_audio_sync_clk_sources;
191571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	struct clk_lookup *lookup;
191671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
191771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (i = 0; src->name; i++, sel++, src++) {
191871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		sel->input = tegra_get_clock_by_name(src->name);
191971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (!sel->input)
192071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			pr_err("%s: could not find clk %s\n", __func__,
192171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross				src->name);
192271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		sel->value = src->value;
192371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
192471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
192571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	lookup = tegra_audio_clk_lookups;
192671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (i = 0; i < ARRAY_SIZE(tegra_audio_clk_lookups); i++, lookup++) {
192771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		clk_init(lookup->clk);
192871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		clkdev_add(lookup);
192971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
1930d861196163e30c07add471562b45dce38517c9b2Colin Cross}
1931d861196163e30c07add471562b45dce38517c9b2Colin Cross
1932d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_cclk[] = {
1933d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_m,	.value = 0},
1934d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_c,	.value = 1},
1935d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_32k,	.value = 2},
1936d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_m,	.value = 3},
1937d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p,	.value = 4},
1938d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p_out4,	.value = 5},
1939d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p_out3,	.value = 6},
1940d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_d,	.value = 7},
1941d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_x,	.value = 8},
194245fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
1943d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1944d861196163e30c07add471562b45dce38517c9b2Colin Cross
1945d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_sclk[] = {
1946d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_m,	.value = 0},
1947d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_c_out1,	.value = 1},
1948d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p_out4,	.value = 2},
1949d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p_out3,	.value = 3},
1950d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p_out2,	.value = 4},
1951d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_d,	.value = 5},
1952d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_32k,	.value = 6},
1953d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_m_out1,	.value = 7},
195445fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
1955d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1956d861196163e30c07add471562b45dce38517c9b2Colin Cross
195771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk tegra_clk_cclk = {
195871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.name	= "cclk",
1959d861196163e30c07add471562b45dce38517c9b2Colin Cross	.inputs	= mux_cclk,
1960d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg	= 0x20,
1961d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops	= &tegra_super_ops,
196271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate = 1000000000,
1963d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1964d861196163e30c07add471562b45dce38517c9b2Colin Cross
196571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk tegra_clk_sclk = {
196671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.name	= "sclk",
1967d861196163e30c07add471562b45dce38517c9b2Colin Cross	.inputs	= mux_sclk,
1968d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg	= 0x28,
1969d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops	= &tegra_super_ops,
19709c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.max_rate = 240000000,
19719c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.min_rate = 120000000,
197271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross};
197371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
197471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk tegra_clk_virtual_cpu = {
197571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.name      = "cpu",
197671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.parent    = &tegra_clk_cclk,
197771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.ops       = &tegra_cpu_ops,
197871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate  = 1000000000,
1979f151961173bf28047d01b410969f05e485f56d7eColin Cross	.u.cpu = {
1980f151961173bf28047d01b410969f05e485f56d7eColin Cross		.main      = &tegra_pll_x,
1981f151961173bf28047d01b410969f05e485f56d7eColin Cross		.backup    = &tegra_pll_p,
1982f151961173bf28047d01b410969f05e485f56d7eColin Cross	},
1983d861196163e30c07add471562b45dce38517c9b2Colin Cross};
1984d861196163e30c07add471562b45dce38517c9b2Colin Cross
19859c7dc562cd78784f54261b9bedb44e8b0056f729Colin Crossstatic struct clk tegra_clk_cop = {
19869c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.name      = "cop",
19879c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.parent    = &tegra_clk_sclk,
19889c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.ops       = &tegra_cop_ops,
19899c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.max_rate  = 240000000,
19909c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross};
19919c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross
1992d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_clk_hclk = {
1993d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name		= "hclk",
1994d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags		= DIV_BUS,
199571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.parent		= &tegra_clk_sclk,
1996d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg		= 0x30,
1997d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift	= 4,
1998d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops		= &tegra_bus_ops,
199971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	.max_rate       = 240000000,
2000d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2001d861196163e30c07add471562b45dce38517c9b2Colin Cross
2002d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk tegra_clk_pclk = {
2003d861196163e30c07add471562b45dce38517c9b2Colin Cross	.name		= "pclk",
2004d861196163e30c07add471562b45dce38517c9b2Colin Cross	.flags		= DIV_BUS,
2005d861196163e30c07add471562b45dce38517c9b2Colin Cross	.parent		= &tegra_clk_hclk,
2006d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg		= 0x30,
2007d861196163e30c07add471562b45dce38517c9b2Colin Cross	.reg_shift	= 0,
2008d861196163e30c07add471562b45dce38517c9b2Colin Cross	.ops		= &tegra_bus_ops,
20099c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	.max_rate       = 120000000,
2010d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2011d861196163e30c07add471562b45dce38517c9b2Colin Cross
2012cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Crossstatic struct clk tegra_clk_blink = {
2013cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.name		= "blink",
2014cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.parent		= &tegra_clk_32k,
2015cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.reg		= 0x40,
2016cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.ops		= &tegra_blink_clk_ops,
2017cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	.max_rate	= 32768,
2018cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross};
2019cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
2020d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_pllm_pllc_pllp_plla[] = {
2021d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_m, .value = 0},
2022d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_c, .value = 1},
2023d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p, .value = 2},
2024d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_a_out0, .value = 3},
202545fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2026d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2027d861196163e30c07add471562b45dce38517c9b2Colin Cross
2028d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_pllm_pllc_pllp_clkm[] = {
2029d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_m, .value = 0},
2030d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_c, .value = 1},
2031d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p, .value = 2},
2032d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_m, .value = 3},
203345fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2034d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2035d861196163e30c07add471562b45dce38517c9b2Colin Cross
2036d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_pllp_pllc_pllm_clkm[] = {
2037d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p, .value = 0},
2038d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_c, .value = 1},
2039d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_m, .value = 2},
2040d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_m, .value = 3},
204145fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2042d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2043d861196163e30c07add471562b45dce38517c9b2Colin Cross
204471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic struct clk_mux_sel mux_pllaout0_audio2x_pllp_clkm[] = {
204571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{.input = &tegra_pll_a_out0, .value = 0},
204671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{.input = &tegra_clk_audio_2x, .value = 1},
2047d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_p, .value = 2},
2048d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_clk_m, .value = 3},
204945fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2050d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2051d861196163e30c07add471562b45dce38517c9b2Colin Cross
2052d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_pllp_plld_pllc_clkm[] = {
2053d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_p, .value = 0},
2054d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_d_out0, .value = 1},
2055d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_c, .value = 2},
2056d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_clk_m, .value = 3},
205745fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2058d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2059d861196163e30c07add471562b45dce38517c9b2Colin Cross
2060d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_pllp_pllc_audio_clkm_clk32[] = {
2061d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_p,     .value = 0},
2062d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_c,     .value = 1},
206371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	{.input = &tegra_clk_audio,     .value = 2},
2064d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_clk_m,     .value = 3},
2065d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_clk_32k,   .value = 4},
206645fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2067d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2068d861196163e30c07add471562b45dce38517c9b2Colin Cross
2069d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_pllp_pllc_pllm[] = {
2070d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_p,     .value = 0},
2071d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_c,     .value = 1},
2072d861196163e30c07add471562b45dce38517c9b2Colin Cross	{.input = &tegra_pll_m,     .value = 2},
207345fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2074d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2075d861196163e30c07add471562b45dce38517c9b2Colin Cross
2076d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_clk_m[] = {
2077d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_m, .value = 0},
207845fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2079d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2080d861196163e30c07add471562b45dce38517c9b2Colin Cross
2081d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_pllp_out3[] = {
2082d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_p_out3, .value = 0},
208345fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2084d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2085d861196163e30c07add471562b45dce38517c9b2Colin Cross
2086d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_plld[] = {
2087d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_pll_d, .value = 0},
208845fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2089d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2090d861196163e30c07add471562b45dce38517c9b2Colin Cross
2091d861196163e30c07add471562b45dce38517c9b2Colin Crossstatic struct clk_mux_sel mux_clk_32k[] = {
2092d861196163e30c07add471562b45dce38517c9b2Colin Cross	{ .input = &tegra_clk_32k, .value = 0},
209345fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
2094d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2095d861196163e30c07add471562b45dce38517c9b2Colin Cross
20961ca00347c579f15b0eea1a6d4bab84e2cf56e745Stephen Warrenstatic struct clk_mux_sel mux_pclk[] = {
20971ca00347c579f15b0eea1a6d4bab84e2cf56e745Stephen Warren	{ .input = &tegra_clk_pclk, .value = 0},
209845fba2186256988a8f0cc2d7f8de6ef53fb1e4baOlof Johansson	{ NULL, 0},
20991ca00347c579f15b0eea1a6d4bab84e2cf56e745Stephen Warren};
21001ca00347c579f15b0eea1a6d4bab84e2cf56e745Stephen Warren
21016d2968284f63efa1d1849165f9e3a80402509212Colin Crossstatic struct clk tegra_clk_emc = {
21026d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.name = "emc",
21036d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.ops = &tegra_emc_clk_ops,
21046d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.reg = 0x19c,
21056d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.max_rate = 800000000,
21066d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.inputs = mux_pllm_pllc_pllp_clkm,
21076d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.flags = MUX | DIV_U71 | PERIPH_EMC_ENB,
21086d2968284f63efa1d1849165f9e3a80402509212Colin Cross	.u.periph = {
21096d2968284f63efa1d1849165f9e3a80402509212Colin Cross		.clk_num = 57,
21106d2968284f63efa1d1849165f9e3a80402509212Colin Cross	},
21116d2968284f63efa1d1849165f9e3a80402509212Colin Cross};
21126d2968284f63efa1d1849165f9e3a80402509212Colin Cross
211371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#define PERIPH_CLK(_name, _dev, _con, _clk_num, _reg, _max, _inputs, _flags) \
2114d861196163e30c07add471562b45dce38517c9b2Colin Cross	{						\
2115d861196163e30c07add471562b45dce38517c9b2Colin Cross		.name      = _name,			\
2116d861196163e30c07add471562b45dce38517c9b2Colin Cross		.lookup    = {				\
2117d861196163e30c07add471562b45dce38517c9b2Colin Cross			.dev_id    = _dev,		\
2118d861196163e30c07add471562b45dce38517c9b2Colin Cross			.con_id	   = _con,		\
2119d861196163e30c07add471562b45dce38517c9b2Colin Cross		},					\
2120d861196163e30c07add471562b45dce38517c9b2Colin Cross		.ops       = &tegra_periph_clk_ops,	\
2121d861196163e30c07add471562b45dce38517c9b2Colin Cross		.reg       = _reg,			\
2122d861196163e30c07add471562b45dce38517c9b2Colin Cross		.inputs    = _inputs,			\
2123d861196163e30c07add471562b45dce38517c9b2Colin Cross		.flags     = _flags,			\
212471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		.max_rate  = _max,			\
2125f151961173bf28047d01b410969f05e485f56d7eColin Cross		.u.periph = {				\
2126f151961173bf28047d01b410969f05e485f56d7eColin Cross			.clk_num   = _clk_num,		\
2127f151961173bf28047d01b410969f05e485f56d7eColin Cross		},					\
2128d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
2129d861196163e30c07add471562b45dce38517c9b2Colin Cross
2130310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross#define SHARED_CLK(_name, _dev, _con, _parent)		\
2131310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	{						\
2132310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross		.name      = _name,			\
2133310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross		.lookup    = {				\
2134310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross			.dev_id    = _dev,		\
2135310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross			.con_id    = _con,		\
2136310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross		},					\
2137310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross		.ops       = &tegra_clk_shared_bus_ops,	\
2138310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross		.parent = _parent,			\
2139310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	}
2140310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross
214187c6e46a2c96ce2081070701237c58ed7eec94e7Olof Johanssonstatic struct clk tegra_list_clks[] = {
21421ca00347c579f15b0eea1a6d4bab84e2cf56e745Stephen Warren	PERIPH_CLK("apbdma",	"tegra-dma",		NULL,	34,	0,	108000000, mux_pclk,			0),
214371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("rtc",	"rtc-tegra",		NULL,	4,	0,	32768,     mux_clk_32k,			PERIPH_NO_RESET),
214471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("timer",	"timer",		NULL,	5,	0,	26000000,  mux_clk_m,			0),
21453c106bf5b3e59e1fc8e0dfcd7a620cfed7a98430Stephen Warren	PERIPH_CLK("i2s1",	"tegra-i2s.0",		NULL,	11,	0x100,	26000000,  mux_pllaout0_audio2x_pllp_clkm,	MUX | DIV_U71),
21463c106bf5b3e59e1fc8e0dfcd7a620cfed7a98430Stephen Warren	PERIPH_CLK("i2s2",	"tegra-i2s.1",		NULL,	18,	0x104,	26000000,  mux_pllaout0_audio2x_pllp_clkm,	MUX | DIV_U71),
214771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("spdif_out",	"spdif_out",		NULL,	10,	0x108,	100000000, mux_pllaout0_audio2x_pllp_clkm,	MUX | DIV_U71),
214871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("spdif_in",	"spdif_in",		NULL,	10,	0x10c,	100000000, mux_pllp_pllc_pllm,		MUX | DIV_U71),
214971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("pwm",	"pwm",			NULL,	17,	0x110,	432000000, mux_pllp_pllc_audio_clkm_clk32,	MUX | DIV_U71),
215071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("spi",	"spi",			NULL,	43,	0x114,	40000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
215171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("xio",	"xio",			NULL,	45,	0x120,	150000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
215271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("twc",	"twc",			NULL,	16,	0x12c,	150000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
215371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("sbc1",	"spi_tegra.0",		NULL,	41,	0x134,	160000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
215471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("sbc2",	"spi_tegra.1",		NULL,	44,	0x118,	160000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
215571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("sbc3",	"spi_tegra.2",		NULL,	46,	0x11c,	160000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
215671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("sbc4",	"spi_tegra.3",		NULL,	68,	0x1b4,	160000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
215771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("ide",	"ide",			NULL,	25,	0x144,	100000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* requires min voltage */
215871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("ndflash",	"tegra_nand",		NULL,	13,	0x160,	164000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* scales with voltage */
215971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("vfir",	"vfir",			NULL,	7,	0x168,	72000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
216071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("sdmmc1",	"sdhci-tegra.0",	NULL,	14,	0x150,	52000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* scales with voltage */
216171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("sdmmc2",	"sdhci-tegra.1",	NULL,	9,	0x154,	52000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* scales with voltage */
216271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("sdmmc3",	"sdhci-tegra.2",	NULL,	69,	0x1bc,	52000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* scales with voltage */
2163cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("sdmmc4",	"sdhci-tegra.3",	NULL,	15,	0x164,	52000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* scales with voltage */
21649c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	PERIPH_CLK("vcp",	"tegra-avp",		"vcp",	29,	0,	250000000, mux_clk_m,			0),
21659c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	PERIPH_CLK("bsea",	"tegra-avp",		"bsea",	62,	0,	250000000, mux_clk_m,			0),
21669c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	PERIPH_CLK("bsev",	"tegra-aes",		"bsev",	63,	0,	250000000, mux_clk_m,			0),
21679c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	PERIPH_CLK("vde",	"tegra-avp",		"vde",	61,	0x1c8,	250000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* scales with voltage and process_id */
216871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("csite",	"csite",		NULL,	73,	0x1d4,	144000000, mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* max rate ??? */
2169d861196163e30c07add471562b45dce38517c9b2Colin Cross	/* FIXME: what is la? */
217071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("la",	"la",			NULL,	76,	0x1f8,	26000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
217171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("owr",	"tegra_w1",		NULL,	71,	0x1cc,	26000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71),
217271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("nor",	"nor",			NULL,	42,	0x1d0,	92000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* requires min voltage */
217371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("mipi",	"mipi",			NULL,	50,	0x174,	60000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U71), /* scales with voltage */
217471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("i2c1",	"tegra-i2c.0",		NULL,	12,	0x124,	26000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U16),
217571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("i2c2",	"tegra-i2c.1",		NULL,	54,	0x198,	26000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U16),
217671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("i2c3",	"tegra-i2c.2",		NULL,	67,	0x1b8,	26000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U16),
217771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("dvc",	"tegra-i2c.3",		NULL,	47,	0x128,	26000000,  mux_pllp_pllc_pllm_clkm,	MUX | DIV_U16),
217871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("i2c1_i2c",	"tegra-i2c.0",		"i2c",	0,	0,	72000000,  mux_pllp_out3,			0),
217971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("i2c2_i2c",	"tegra-i2c.1",		"i2c",	0,	0,	72000000,  mux_pllp_out3,			0),
218071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("i2c3_i2c",	"tegra-i2c.2",		"i2c",	0,	0,	72000000,  mux_pllp_out3,			0),
218171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("dvc_i2c",	"tegra-i2c.3",		"i2c",	0,	0,	72000000,  mux_pllp_out3,			0),
2182cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("uarta",	"uart.0",		NULL,	6,	0x178,	600000000, mux_pllp_pllc_pllm_clkm,	MUX),
2183cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("uartb",	"uart.1",		NULL,	7,	0x17c,	600000000, mux_pllp_pllc_pllm_clkm,	MUX),
2184cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("uartc",	"uart.2",		NULL,	55,	0x1a0,	600000000, mux_pllp_pllc_pllm_clkm,	MUX),
2185cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("uartd",	"uart.3",		NULL,	65,	0x1c0,	600000000, mux_pllp_pllc_pllm_clkm,	MUX),
2186cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("uarte",	"uart.4",		NULL,	66,	0x1c4,	600000000, mux_pllp_pllc_pllm_clkm,	MUX),
218771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("3d",	"3d",			NULL,	24,	0x158,	300000000, mux_pllm_pllc_pllp_plla,	MUX | DIV_U71 | PERIPH_MANUAL_RESET), /* scales with voltage and process_id */
218871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("2d",	"2d",			NULL,	21,	0x15c,	300000000, mux_pllm_pllc_pllp_plla,	MUX | DIV_U71), /* scales with voltage and process_id */
2189cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("vi",	"tegra_camera",		"vi",	20,	0x148,	150000000, mux_pllm_pllc_pllp_plla,	MUX | DIV_U71), /* scales with voltage and process_id */
2190cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("vi_sensor",	"tegra_camera",		"vi_sensor",	20,	0x1a8,	150000000, mux_pllm_pllc_pllp_plla,	MUX | DIV_U71 | PERIPH_NO_RESET), /* scales with voltage and process_id */
219171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("epp",	"epp",			NULL,	19,	0x16c,	300000000, mux_pllm_pllc_pllp_plla,	MUX | DIV_U71), /* scales with voltage and process_id */
219271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("mpe",	"mpe",			NULL,	60,	0x170,	250000000, mux_pllm_pllc_pllp_plla,	MUX | DIV_U71), /* scales with voltage and process_id */
219371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("host1x",	"host1x",		NULL,	28,	0x180,	166000000, mux_pllm_pllc_pllp_plla,	MUX | DIV_U71), /* scales with voltage and process_id */
219471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("cve",	"cve",			NULL,	49,	0x140,	250000000, mux_pllp_plld_pllc_clkm,	MUX | DIV_U71), /* requires min voltage */
219571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("tvo",	"tvo",			NULL,	49,	0x188,	250000000, mux_pllp_plld_pllc_clkm,	MUX | DIV_U71), /* requires min voltage */
2196cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("hdmi",	"hdmi",			NULL,	51,	0x18c,	600000000, mux_pllp_plld_pllc_clkm,	MUX | DIV_U71), /* requires min voltage */
219771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("tvdac",	"tvdac",		NULL,	53,	0x194,	250000000, mux_pllp_plld_pllc_clkm,	MUX | DIV_U71), /* requires min voltage */
2198e051526ba7cce238f232fc4a69a61c5ac0b03828Robert Morell	PERIPH_CLK("disp1",	"tegradc.0",		NULL,	27,	0x138,	600000000, mux_pllp_plld_pllc_clkm,	MUX), /* scales with voltage and process_id */
2199e051526ba7cce238f232fc4a69a61c5ac0b03828Robert Morell	PERIPH_CLK("disp2",	"tegradc.1",		NULL,	26,	0x13c,	600000000, mux_pllp_plld_pllc_clkm,	MUX), /* scales with voltage and process_id */
220071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("usbd",	"fsl-tegra-udc",	NULL,	22,	0,	480000000, mux_clk_m,			0), /* requires min voltage */
220171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("usb2",	"tegra-ehci.1",		NULL,	58,	0,	480000000, mux_clk_m,			0), /* requires min voltage */
220271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("usb3",	"tegra-ehci.2",		NULL,	59,	0,	480000000, mux_clk_m,			0), /* requires min voltage */
220371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	PERIPH_CLK("dsi",	"dsi",			NULL,	48,	0,	500000000, mux_plld,			0), /* scales with voltage */
2204cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("csi",	"tegra_camera",		"csi",	52,	0,	72000000,  mux_pllp_out3,		0),
2205cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("isp",	"tegra_camera",		"isp",	23,	0,	150000000, mux_clk_m,			0), /* same frequency as VI */
2206cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	PERIPH_CLK("csus",	"tegra_camera",		"csus",	92,	0,	150000000, mux_clk_m,			PERIPH_NO_RESET),
22078d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	PERIPH_CLK("pex",       NULL,			"pex",  70,     0,	26000000,  mux_clk_m,			PERIPH_MANUAL_RESET),
22088d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	PERIPH_CLK("afi",       NULL,			"afi",  72,     0,	26000000,  mux_clk_m,			PERIPH_MANUAL_RESET),
22098d685bc5e5cad76c05c9986c23a821c5bcef7c16Mike Rapoport	PERIPH_CLK("pcie_xclk", NULL,		  "pcie_xclk",  74,     0,	26000000,  mux_clk_m,			PERIPH_MANUAL_RESET),
22109c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross
22119c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("avp.sclk",	"tegra-avp",		"sclk",	&tegra_clk_sclk),
22129c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("avp.emc",	"tegra-avp",		"emc",	&tegra_clk_emc),
22139c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("cpu.emc",	"cpu",			"emc",	&tegra_clk_emc),
22149c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("disp1.emc",	"tegradc.0",		"emc",	&tegra_clk_emc),
22159c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("disp2.emc",	"tegradc.1",		"emc",	&tegra_clk_emc),
22169c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("hdmi.emc",	"hdmi",			"emc",	&tegra_clk_emc),
22179c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("host.emc",	"tegra_grhost",		"emc",	&tegra_clk_emc),
22189c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("usbd.emc",	"fsl-tegra-udc",	"emc",	&tegra_clk_emc),
22199c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("usb1.emc",	"tegra-ehci.0",		"emc",	&tegra_clk_emc),
22209c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("usb2.emc",	"tegra-ehci.1",		"emc",	&tegra_clk_emc),
22219c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	SHARED_CLK("usb3.emc",	"tegra-ehci.2",		"emc",	&tegra_clk_emc),
2222d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2223d861196163e30c07add471562b45dce38517c9b2Colin Cross
2224d861196163e30c07add471562b45dce38517c9b2Colin Cross#define CLK_DUPLICATE(_name, _dev, _con)		\
2225d861196163e30c07add471562b45dce38517c9b2Colin Cross	{						\
2226d861196163e30c07add471562b45dce38517c9b2Colin Cross		.name	= _name,			\
2227d861196163e30c07add471562b45dce38517c9b2Colin Cross		.lookup	= {				\
2228d861196163e30c07add471562b45dce38517c9b2Colin Cross			.dev_id	= _dev,			\
2229d861196163e30c07add471562b45dce38517c9b2Colin Cross			.con_id		= _con,		\
2230d861196163e30c07add471562b45dce38517c9b2Colin Cross		},					\
2231d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
2232d861196163e30c07add471562b45dce38517c9b2Colin Cross
2233d861196163e30c07add471562b45dce38517c9b2Colin Cross/* Some clocks may be used by different drivers depending on the board
2234d861196163e30c07add471562b45dce38517c9b2Colin Cross * configuration.  List those here to register them twice in the clock lookup
2235d861196163e30c07add471562b45dce38517c9b2Colin Cross * table under two names.
2236d861196163e30c07add471562b45dce38517c9b2Colin Cross */
223787c6e46a2c96ce2081070701237c58ed7eec94e7Olof Johanssonstatic struct clk_duplicate tegra_clk_duplicates[] = {
2238d861196163e30c07add471562b45dce38517c9b2Colin Cross	CLK_DUPLICATE("uarta",	"tegra_uart.0",	NULL),
2239d861196163e30c07add471562b45dce38517c9b2Colin Cross	CLK_DUPLICATE("uartb",	"tegra_uart.1",	NULL),
2240d861196163e30c07add471562b45dce38517c9b2Colin Cross	CLK_DUPLICATE("uartc",	"tegra_uart.2",	NULL),
2241d861196163e30c07add471562b45dce38517c9b2Colin Cross	CLK_DUPLICATE("uartd",	"tegra_uart.3",	NULL),
2242d861196163e30c07add471562b45dce38517c9b2Colin Cross	CLK_DUPLICATE("uarte",	"tegra_uart.4",	NULL),
2243cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	CLK_DUPLICATE("usbd", "utmip-pad", NULL),
224471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	CLK_DUPLICATE("usbd", "tegra-ehci.0", NULL),
2245cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	CLK_DUPLICATE("usbd", "tegra-otg", NULL),
2246cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	CLK_DUPLICATE("hdmi", "tegradc.0", "hdmi"),
2247cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	CLK_DUPLICATE("hdmi", "tegradc.1", "hdmi"),
2248cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	CLK_DUPLICATE("pwm", "tegra_pwm.0", NULL),
2249cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	CLK_DUPLICATE("pwm", "tegra_pwm.1", NULL),
2250cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	CLK_DUPLICATE("pwm", "tegra_pwm.2", NULL),
2251cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	CLK_DUPLICATE("pwm", "tegra_pwm.3", NULL),
22529c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	CLK_DUPLICATE("host1x", "tegra_grhost", "host1x"),
22539c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	CLK_DUPLICATE("2d", "tegra_grhost", "gr2d"),
22549c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	CLK_DUPLICATE("3d", "tegra_grhost", "gr3d"),
22559c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	CLK_DUPLICATE("epp", "tegra_grhost", "epp"),
22569c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	CLK_DUPLICATE("mpe", "tegra_grhost", "mpe"),
22579c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	CLK_DUPLICATE("cop", "tegra-avp", "cop"),
22589c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	CLK_DUPLICATE("vde", "tegra-aes", "vde"),
2259d861196163e30c07add471562b45dce38517c9b2Colin Cross};
2260d861196163e30c07add471562b45dce38517c9b2Colin Cross
2261d861196163e30c07add471562b45dce38517c9b2Colin Cross#define CLK(dev, con, ck)	\
2262d861196163e30c07add471562b45dce38517c9b2Colin Cross	{			\
2263d861196163e30c07add471562b45dce38517c9b2Colin Cross		.dev_id = dev,	\
2264d861196163e30c07add471562b45dce38517c9b2Colin Cross		.con_id = con,	\
2265d861196163e30c07add471562b45dce38517c9b2Colin Cross		.clk = ck,	\
2266d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
2267d861196163e30c07add471562b45dce38517c9b2Colin Cross
226887c6e46a2c96ce2081070701237c58ed7eec94e7Olof Johanssonstatic struct clk *tegra_ptr_clks[] = {
22693ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_32k,
22703ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_s,
22713ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_m,
22723ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_m,
22733ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_m_out1,
22743ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_c,
22753ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_c_out1,
22763ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_p,
22773ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_p_out1,
22783ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_p_out2,
22793ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_p_out3,
22803ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_p_out4,
22813ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_a,
22823ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_a_out0,
22833ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_d,
22843ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_d_out0,
22853ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_u,
22863ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_x,
22873ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_pll_e,
22883ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_cclk,
22893ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_sclk,
22903ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_hclk,
22913ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_pclk,
22923ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_d,
2293ddb7d5d80edb58e8235f1bc6c350eac40bfe85d1Stephen Warren	&tegra_clk_cdev1,
2294ddb7d5d80edb58e8235f1bc6c350eac40bfe85d1Stephen Warren	&tegra_clk_cdev2,
22953ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_virtual_cpu,
22963ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	&tegra_clk_blink,
22979c7dc562cd78784f54261b9bedb44e8b0056f729Colin Cross	&tegra_clk_cop,
22986d2968284f63efa1d1849165f9e3a80402509212Colin Cross	&tegra_clk_emc,
22993ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross};
23003ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross
23013ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Crossstatic void tegra2_init_one_clock(struct clk *c)
23023ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross{
23033ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	clk_init(c);
2304310992ca4b994db8c869e1c0f32c004b7a196147Colin Cross	INIT_LIST_HEAD(&c->shared_bus_list);
23053ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	if (!c->lookup.dev_id && !c->lookup.con_id)
23063ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross		c->lookup.con_id = c->name;
23073ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	c->lookup.clk = c;
23083ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	clkdev_add(&c->lookup);
23093ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross}
2310d861196163e30c07add471562b45dce38517c9b2Colin Cross
2311d861196163e30c07add471562b45dce38517c9b2Colin Crossvoid __init tegra2_init_clocks(void)
2312d861196163e30c07add471562b45dce38517c9b2Colin Cross{
2313d861196163e30c07add471562b45dce38517c9b2Colin Cross	int i;
2314d861196163e30c07add471562b45dce38517c9b2Colin Cross	struct clk *c;
2315d861196163e30c07add471562b45dce38517c9b2Colin Cross
23163ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	for (i = 0; i < ARRAY_SIZE(tegra_ptr_clks); i++)
23173ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross		tegra2_init_one_clock(tegra_ptr_clks[i]);
2318d861196163e30c07add471562b45dce38517c9b2Colin Cross
23193ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross	for (i = 0; i < ARRAY_SIZE(tegra_list_clks); i++)
23203ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross		tegra2_init_one_clock(&tegra_list_clks[i]);
2321d861196163e30c07add471562b45dce38517c9b2Colin Cross
2322d861196163e30c07add471562b45dce38517c9b2Colin Cross	for (i = 0; i < ARRAY_SIZE(tegra_clk_duplicates); i++) {
23233ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross		c = tegra_get_clock_by_name(tegra_clk_duplicates[i].name);
23243ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross		if (!c) {
2325d861196163e30c07add471562b45dce38517c9b2Colin Cross			pr_err("%s: Unknown duplicate clock %s\n", __func__,
23263ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross				tegra_clk_duplicates[i].name);
23273ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross			continue;
2328d861196163e30c07add471562b45dce38517c9b2Colin Cross		}
23293ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross
23303ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross		tegra_clk_duplicates[i].lookup.clk = c;
23313ec349fbf1e88e84d4dffc54b6cb32129a32b7b0Colin Cross		clkdev_add(&tegra_clk_duplicates[i].lookup);
2332d861196163e30c07add471562b45dce38517c9b2Colin Cross	}
233371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
233471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	init_audio_sync_clock_mux();
233571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
233671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
233771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#ifdef CONFIG_PM
233871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossstatic u32 clk_rst_suspend[RST_DEVICES_NUM + CLK_OUT_ENB_NUM +
2339c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross			   PERIPH_CLK_SOURCE_NUM + 22];
234071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
234171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossvoid tegra_clk_suspend(void)
234271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
234371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	unsigned long off, i;
234471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	u32 *ctx = clk_rst_suspend;
234571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
234671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	*ctx++ = clk_readl(OSC_CTRL) & OSC_CTRL_MASK;
2347cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_pll_c.reg + PLL_BASE);
2348cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_pll_c.reg + PLL_MISC(&tegra_pll_c));
2349cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_pll_a.reg + PLL_BASE);
2350cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_pll_a.reg + PLL_MISC(&tegra_pll_a));
2351c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	*ctx++ = clk_readl(tegra_pll_s.reg + PLL_BASE);
2352c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	*ctx++ = clk_readl(tegra_pll_s.reg + PLL_MISC(&tegra_pll_s));
2353c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	*ctx++ = clk_readl(tegra_pll_d.reg + PLL_BASE);
2354c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	*ctx++ = clk_readl(tegra_pll_d.reg + PLL_MISC(&tegra_pll_d));
2355c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	*ctx++ = clk_readl(tegra_pll_u.reg + PLL_BASE);
2356c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	*ctx++ = clk_readl(tegra_pll_u.reg + PLL_MISC(&tegra_pll_u));
2357cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
2358cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_pll_m_out1.reg);
2359cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_pll_a_out0.reg);
2360cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_pll_c_out1.reg);
2361cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
2362cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_clk_cclk.reg);
2363cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_clk_cclk.reg + SUPER_CLK_DIVIDER);
2364cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
2365cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_clk_sclk.reg);
2366cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_clk_sclk.reg + SUPER_CLK_DIVIDER);
2367cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	*ctx++ = clk_readl(tegra_clk_pclk.reg);
236871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
2369c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	*ctx++ = clk_readl(tegra_clk_audio.reg);
2370c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross
237171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (off = PERIPH_CLK_SOURCE_I2S1; off <= PERIPH_CLK_SOURCE_OSC;
237271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			off += 4) {
237371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (off == PERIPH_CLK_SOURCE_EMC)
237471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			continue;
237571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		*ctx++ = clk_readl(off);
237671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
237771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
237871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	off = RST_DEVICES;
237971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (i = 0; i < RST_DEVICES_NUM; i++, off += 4)
238071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		*ctx++ = clk_readl(off);
238171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
238271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	off = CLK_OUT_ENB;
238371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (i = 0; i < CLK_OUT_ENB_NUM; i++, off += 4)
238471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		*ctx++ = clk_readl(off);
238571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
238671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	*ctx++ = clk_readl(MISC_CLK_ENB);
238771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	*ctx++ = clk_readl(CLK_MASK_ARM);
2388c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross
2389c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	BUG_ON(ctx - clk_rst_suspend != ARRAY_SIZE(clk_rst_suspend));
239071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross}
239171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
239271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Crossvoid tegra_clk_resume(void)
239371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross{
239471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	unsigned long off, i;
239571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	const u32 *ctx = clk_rst_suspend;
239671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	u32 val;
239771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
239871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	val = clk_readl(OSC_CTRL) & ~OSC_CTRL_MASK;
239971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	val |= *ctx++;
240071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	clk_writel(val, OSC_CTRL);
240171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
2402cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_pll_c.reg + PLL_BASE);
2403cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_pll_c.reg + PLL_MISC(&tegra_pll_c));
2404cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_pll_a.reg + PLL_BASE);
2405cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_pll_a.reg + PLL_MISC(&tegra_pll_a));
2406c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	clk_writel(*ctx++, tegra_pll_s.reg + PLL_BASE);
2407c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	clk_writel(*ctx++, tegra_pll_s.reg + PLL_MISC(&tegra_pll_s));
2408c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	clk_writel(*ctx++, tegra_pll_d.reg + PLL_BASE);
2409c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	clk_writel(*ctx++, tegra_pll_d.reg + PLL_MISC(&tegra_pll_d));
2410c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	clk_writel(*ctx++, tegra_pll_u.reg + PLL_BASE);
2411c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	clk_writel(*ctx++, tegra_pll_u.reg + PLL_MISC(&tegra_pll_u));
2412c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	udelay(1000);
2413cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
2414cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_pll_m_out1.reg);
2415cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_pll_a_out0.reg);
2416cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_pll_c_out1.reg);
2417cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
2418cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_clk_cclk.reg);
2419cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_clk_cclk.reg + SUPER_CLK_DIVIDER);
2420cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
2421cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_clk_sclk.reg);
2422cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_clk_sclk.reg + SUPER_CLK_DIVIDER);
2423cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross	clk_writel(*ctx++, tegra_clk_pclk.reg);
2424cea62c878dd8b73b67fb3e38f989e9d3241d5934Colin Cross
2425c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross	clk_writel(*ctx++, tegra_clk_audio.reg);
2426c2f44a9df9e1f8974911ef538565e301b38e0680Colin Cross
242771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	/* enable all clocks before configuring clock sources */
242871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	clk_writel(0xbffffff9ul, CLK_OUT_ENB);
242971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	clk_writel(0xfefffff7ul, CLK_OUT_ENB + 4);
243071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	clk_writel(0x77f01bfful, CLK_OUT_ENB + 8);
243171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	wmb();
243271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
243371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (off = PERIPH_CLK_SOURCE_I2S1; off <= PERIPH_CLK_SOURCE_OSC;
243471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			off += 4) {
243571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		if (off == PERIPH_CLK_SOURCE_EMC)
243671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross			continue;
243771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		clk_writel(*ctx++, off);
243871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	}
243971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	wmb();
244071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
244171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	off = RST_DEVICES;
244271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (i = 0; i < RST_DEVICES_NUM; i++, off += 4)
244371fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		clk_writel(*ctx++, off);
244471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	wmb();
244571fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
244671fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	off = CLK_OUT_ENB;
244771fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	for (i = 0; i < CLK_OUT_ENB_NUM; i++, off += 4)
244871fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross		clk_writel(*ctx++, off);
244971fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	wmb();
245071fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross
245171fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	clk_writel(*ctx++, MISC_CLK_ENB);
245271fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross	clk_writel(*ctx++, CLK_MASK_ARM);
2453d861196163e30c07add471562b45dce38517c9b2Colin Cross}
245471fc84cc35ee05913306bfe6e2454cdfc5bf7081Colin Cross#endif
2455