diff options
| author | Jonathan Herman <hermanjl@cs.unc.edu> | 2013-01-22 10:38:37 -0500 |
|---|---|---|
| committer | Jonathan Herman <hermanjl@cs.unc.edu> | 2013-01-22 10:38:37 -0500 |
| commit | fcc9d2e5a6c89d22b8b773a64fb4ad21ac318446 (patch) | |
| tree | a57612d1888735a2ec7972891b68c1ac5ec8faea /arch/arm/mach-tegra/clock-common.c | |
| parent | 8dea78da5cee153b8af9c07a2745f6c55057fe12 (diff) | |
Diffstat (limited to 'arch/arm/mach-tegra/clock-common.c')
| -rw-r--r-- | arch/arm/mach-tegra/clock-common.c | 73 |
1 files changed, 73 insertions, 0 deletions
diff --git a/arch/arm/mach-tegra/clock-common.c b/arch/arm/mach-tegra/clock-common.c new file mode 100644 index 00000000000..67c5d51378a --- /dev/null +++ b/arch/arm/mach-tegra/clock-common.c | |||
| @@ -0,0 +1,73 @@ | |||
| 1 | /* | ||
| 2 | * Copyright (C) 2010-2012 NVIDIA Corporation | ||
| 3 | * | ||
| 4 | * This software is licensed under the terms of the GNU General Public | ||
| 5 | * License version 2, as published by the Free Software Foundation, and | ||
| 6 | * may be copied, distributed, and modified under those terms. | ||
| 7 | * | ||
| 8 | * This program is distributed in the hope that it will be useful, | ||
| 9 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 10 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 11 | * GNU General Public License for more details. | ||
| 12 | * | ||
| 13 | */ | ||
| 14 | |||
| 15 | #include <linux/kernel.h> | ||
| 16 | #include <linux/clk.h> | ||
| 17 | #include <linux/clkdev.h> | ||
| 18 | #include <linux/io.h> | ||
| 19 | |||
| 20 | #include <mach/clk.h> | ||
| 21 | #include <mach/iomap.h> | ||
| 22 | |||
| 23 | #include "clock.h" | ||
| 24 | |||
| 25 | #define clk_writel(value, reg) \ | ||
| 26 | __raw_writel(value, (u32)reg_clk_base + (reg)) | ||
| 27 | #define clk_readl(reg) \ | ||
| 28 | __raw_readl((u32)reg_clk_base + (reg)) | ||
| 29 | |||
| 30 | #define OSC_FREQ_DET 0x58 | ||
| 31 | #define OSC_FREQ_DET_TRIG (1<<31) | ||
| 32 | |||
| 33 | #define OSC_FREQ_DET_STATUS 0x5C | ||
| 34 | #define OSC_FREQ_DET_BUSY (1<<31) | ||
| 35 | #define OSC_FREQ_DET_CNT_MASK 0xFFFF | ||
| 36 | |||
| 37 | static void __iomem *reg_clk_base = IO_ADDRESS(TEGRA_CLK_RESET_BASE); | ||
| 38 | static unsigned long osc_input_freq; | ||
| 39 | |||
| 40 | unsigned long tegra_clk_measure_input_freq(void) | ||
| 41 | { | ||
| 42 | u32 clock_autodetect; | ||
| 43 | |||
| 44 | if (osc_input_freq) | ||
| 45 | return osc_input_freq; | ||
| 46 | |||
| 47 | clk_writel(OSC_FREQ_DET_TRIG | 1, OSC_FREQ_DET); | ||
| 48 | do {} while (clk_readl(OSC_FREQ_DET_STATUS) & OSC_FREQ_DET_BUSY); | ||
| 49 | clock_autodetect = clk_readl(OSC_FREQ_DET_STATUS); | ||
| 50 | |||
| 51 | if (clock_autodetect >= 732 - 3 && clock_autodetect <= 732 + 3) | ||
| 52 | osc_input_freq = 12000000; | ||
| 53 | else if (clock_autodetect >= 794 - 3 && clock_autodetect <= 794 + 3) | ||
| 54 | osc_input_freq = 13000000; | ||
| 55 | else if (clock_autodetect >= 1172 - 3 && clock_autodetect <= 1172 + 3) | ||
| 56 | osc_input_freq = 19200000; | ||
| 57 | else if (clock_autodetect >= 1587 - 3 && clock_autodetect <= 1587 + 3) | ||
| 58 | osc_input_freq = 26000000; | ||
| 59 | #ifndef CONFIG_ARCH_TEGRA_2x_SOC | ||
| 60 | else if (clock_autodetect >= 1025 - 3 && clock_autodetect <= 1025 + 3) | ||
| 61 | osc_input_freq = 16800000; | ||
| 62 | else if (clock_autodetect >= 2344 - 3 && clock_autodetect <= 2344 + 3) | ||
| 63 | osc_input_freq = 38400000; | ||
| 64 | else if (clock_autodetect >= 2928 - 3 && clock_autodetect <= 2928 + 3) | ||
| 65 | osc_input_freq = 48000000; | ||
| 66 | #endif | ||
| 67 | else { | ||
| 68 | pr_err("%s: Unexpected clock autodetect value %d", __func__, | ||
| 69 | clock_autodetect); | ||
| 70 | BUG(); | ||
| 71 | } | ||
| 72 | return osc_input_freq; | ||
| 73 | } | ||
