diff options
Diffstat (limited to 'drivers/clk/tegra/clk-tegra210.c')
-rw-r--r-- | drivers/clk/tegra/clk-tegra210.c | 53 |
1 files changed, 52 insertions, 1 deletions
diff --git a/drivers/clk/tegra/clk-tegra210.c b/drivers/clk/tegra/clk-tegra210.c index 68cbb98af567..b9099012dc7b 100644 --- a/drivers/clk/tegra/clk-tegra210.c +++ b/drivers/clk/tegra/clk-tegra210.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0-only /* - * Copyright (c) 2012-2014 NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2012-2020 NVIDIA CORPORATION. All rights reserved. */ #include <linux/io.h> @@ -403,6 +403,14 @@ static unsigned long tegra210_input_freq[] = { #define PLLRE_BASE_DEFAULT_MASK 0x1c000000 #define PLLRE_MISC0_WRITE_MASK 0x67ffffff +/* PLLE */ +#define PLLE_MISC_IDDQ_SW_CTRL (1 << 14) +#define PLLE_AUX_USE_LOCKDET (1 << 3) +#define PLLE_AUX_SS_SEQ_INCLUDE (1 << 31) +#define PLLE_AUX_ENABLE_SWCTL (1 << 4) +#define PLLE_AUX_SS_SWCTL (1 << 6) +#define PLLE_AUX_SEQ_ENABLE (1 << 24) + /* PLLX */ #define PLLX_USE_DYN_RAMP 1 #define PLLX_BASE_LOCK (1 << 27) @@ -489,6 +497,49 @@ static unsigned long tegra210_input_freq[] = { #define PLLU_MISC0_WRITE_MASK 0xbfffffff #define PLLU_MISC1_WRITE_MASK 0x00000007 +bool tegra210_plle_hw_sequence_is_enabled(void) +{ + u32 value; + + value = readl_relaxed(clk_base + PLLE_AUX); + if (value & PLLE_AUX_SEQ_ENABLE) + return true; + + return false; +} +EXPORT_SYMBOL_GPL(tegra210_plle_hw_sequence_is_enabled); + +int tegra210_plle_hw_sequence_start(void) +{ + u32 value; + + if (tegra210_plle_hw_sequence_is_enabled()) + return 0; + + /* skip if PLLE is not enabled yet */ + value = readl_relaxed(clk_base + PLLE_MISC0); + if (!(value & PLLE_MISC_LOCK)) + return -EIO; + + value &= ~PLLE_MISC_IDDQ_SW_CTRL; + writel_relaxed(value, clk_base + PLLE_MISC0); + + value = readl_relaxed(clk_base + PLLE_AUX); + value |= (PLLE_AUX_USE_LOCKDET | PLLE_AUX_SS_SEQ_INCLUDE); + value &= ~(PLLE_AUX_ENABLE_SWCTL | PLLE_AUX_SS_SWCTL); + writel_relaxed(value, clk_base + PLLE_AUX); + + fence_udelay(1, clk_base); + + value |= PLLE_AUX_SEQ_ENABLE; + writel_relaxed(value, clk_base + PLLE_AUX); + + fence_udelay(1, clk_base); + + return 0; +} +EXPORT_SYMBOL_GPL(tegra210_plle_hw_sequence_start); + void tegra210_xusb_pll_hw_control_enable(void) { u32 val; |