| .. | .. |
|---|
| 1 | +/* SPDX-License-Identifier: GPL-2.0-only */ |
|---|
| 1 | 2 | /* |
|---|
| 2 | 3 | * Copyright (c) 2012, NVIDIA CORPORATION. All rights reserved. |
|---|
| 3 | | - * |
|---|
| 4 | | - * This program is free software; you can redistribute it and/or modify it |
|---|
| 5 | | - * under the terms and conditions of the GNU General Public License, |
|---|
| 6 | | - * version 2, as published by the Free Software Foundation. |
|---|
| 7 | | - * |
|---|
| 8 | | - * This program is distributed in the hope it will be useful, but WITHOUT |
|---|
| 9 | | - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
|---|
| 10 | | - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for |
|---|
| 11 | | - * more details. |
|---|
| 12 | | - * |
|---|
| 13 | | - * You should have received a copy of the GNU General Public License |
|---|
| 14 | | - * along with this program. If not, see <http://www.gnu.org/licenses/>. |
|---|
| 15 | 4 | */ |
|---|
| 16 | 5 | |
|---|
| 17 | 6 | #ifndef __TEGRA_CLK_H |
|---|
| .. | .. |
|---|
| 20 | 9 | #include <linux/clk-provider.h> |
|---|
| 21 | 10 | #include <linux/clkdev.h> |
|---|
| 22 | 11 | #include <linux/delay.h> |
|---|
| 12 | + |
|---|
| 13 | +#define CLK_OUT_ENB_L 0x010 |
|---|
| 14 | +#define CLK_OUT_ENB_H 0x014 |
|---|
| 15 | +#define CLK_OUT_ENB_U 0x018 |
|---|
| 16 | +#define CLK_OUT_ENB_V 0x360 |
|---|
| 17 | +#define CLK_OUT_ENB_W 0x364 |
|---|
| 18 | +#define CLK_OUT_ENB_X 0x280 |
|---|
| 19 | +#define CLK_OUT_ENB_Y 0x298 |
|---|
| 20 | +#define CLK_ENB_PLLP_OUT_CPU BIT(31) |
|---|
| 21 | +#define CLK_OUT_ENB_SET_L 0x320 |
|---|
| 22 | +#define CLK_OUT_ENB_CLR_L 0x324 |
|---|
| 23 | +#define CLK_OUT_ENB_SET_H 0x328 |
|---|
| 24 | +#define CLK_OUT_ENB_CLR_H 0x32c |
|---|
| 25 | +#define CLK_OUT_ENB_SET_U 0x330 |
|---|
| 26 | +#define CLK_OUT_ENB_CLR_U 0x334 |
|---|
| 27 | +#define CLK_OUT_ENB_SET_V 0x440 |
|---|
| 28 | +#define CLK_OUT_ENB_CLR_V 0x444 |
|---|
| 29 | +#define CLK_OUT_ENB_SET_W 0x448 |
|---|
| 30 | +#define CLK_OUT_ENB_CLR_W 0x44c |
|---|
| 31 | +#define CLK_OUT_ENB_SET_X 0x284 |
|---|
| 32 | +#define CLK_OUT_ENB_CLR_X 0x288 |
|---|
| 33 | +#define CLK_OUT_ENB_SET_Y 0x29c |
|---|
| 34 | +#define CLK_OUT_ENB_CLR_Y 0x2a0 |
|---|
| 35 | + |
|---|
| 36 | +#define RST_DEVICES_L 0x004 |
|---|
| 37 | +#define RST_DEVICES_H 0x008 |
|---|
| 38 | +#define RST_DEVICES_U 0x00C |
|---|
| 39 | +#define RST_DEVICES_V 0x358 |
|---|
| 40 | +#define RST_DEVICES_W 0x35C |
|---|
| 41 | +#define RST_DEVICES_X 0x28C |
|---|
| 42 | +#define RST_DEVICES_Y 0x2a4 |
|---|
| 43 | +#define RST_DEVICES_SET_L 0x300 |
|---|
| 44 | +#define RST_DEVICES_CLR_L 0x304 |
|---|
| 45 | +#define RST_DEVICES_SET_H 0x308 |
|---|
| 46 | +#define RST_DEVICES_CLR_H 0x30c |
|---|
| 47 | +#define RST_DEVICES_SET_U 0x310 |
|---|
| 48 | +#define RST_DEVICES_CLR_U 0x314 |
|---|
| 49 | +#define RST_DEVICES_SET_V 0x430 |
|---|
| 50 | +#define RST_DEVICES_CLR_V 0x434 |
|---|
| 51 | +#define RST_DEVICES_SET_W 0x438 |
|---|
| 52 | +#define RST_DEVICES_CLR_W 0x43c |
|---|
| 53 | +#define RST_DEVICES_SET_X 0x290 |
|---|
| 54 | +#define RST_DEVICES_CLR_X 0x294 |
|---|
| 55 | +#define RST_DEVICES_SET_Y 0x2a8 |
|---|
| 56 | +#define RST_DEVICES_CLR_Y 0x2ac |
|---|
| 57 | + |
|---|
| 58 | +/* |
|---|
| 59 | + * Tegra CLK_OUT_ENB registers have some undefined bits which are not used and |
|---|
| 60 | + * any accidental write of 1 to these bits can cause PSLVERR. |
|---|
| 61 | + * So below are the valid mask defines for each CLK_OUT_ENB register used to |
|---|
| 62 | + * turn ON only the valid clocks. |
|---|
| 63 | + */ |
|---|
| 64 | +#define TEGRA210_CLK_ENB_VLD_MSK_L 0xdcd7dff9 |
|---|
| 65 | +#define TEGRA210_CLK_ENB_VLD_MSK_H 0x87d1f3e7 |
|---|
| 66 | +#define TEGRA210_CLK_ENB_VLD_MSK_U 0xf3fed3fa |
|---|
| 67 | +#define TEGRA210_CLK_ENB_VLD_MSK_V 0xffc18cfb |
|---|
| 68 | +#define TEGRA210_CLK_ENB_VLD_MSK_W 0x793fb7ff |
|---|
| 69 | +#define TEGRA210_CLK_ENB_VLD_MSK_X 0x3fe66fff |
|---|
| 70 | +#define TEGRA210_CLK_ENB_VLD_MSK_Y 0xfc1fc7ff |
|---|
| 23 | 71 | |
|---|
| 24 | 72 | /** |
|---|
| 25 | 73 | * struct tegra_clk_sync_source - external clock source from codec |
|---|
| .. | .. |
|---|
| 218 | 266 | * disabled. |
|---|
| 219 | 267 | * @dyn_ramp: Callback which can be used to define a custom |
|---|
| 220 | 268 | * dynamic ramp function for a given PLL. |
|---|
| 269 | + * @pre_rate_change: Callback which is invoked just before changing |
|---|
| 270 | + * PLL's rate. |
|---|
| 271 | + * @post_rate_change: Callback which is invoked right after changing |
|---|
| 272 | + * PLL's rate. |
|---|
| 221 | 273 | * |
|---|
| 222 | 274 | * Flags: |
|---|
| 223 | 275 | * TEGRA_PLL_USE_LOCK - This flag indicated to use lock bits for |
|---|
| .. | .. |
|---|
| 294 | 346 | void (*set_defaults)(struct tegra_clk_pll *pll); |
|---|
| 295 | 347 | int (*dyn_ramp)(struct tegra_clk_pll *pll, |
|---|
| 296 | 348 | struct tegra_clk_pll_freq_table *cfg); |
|---|
| 349 | + int (*pre_rate_change)(void); |
|---|
| 350 | + void (*post_rate_change)(void); |
|---|
| 297 | 351 | }; |
|---|
| 298 | 352 | |
|---|
| 299 | 353 | #define TEGRA_PLL_USE_LOCK BIT(0) |
|---|
| .. | .. |
|---|
| 680 | 734 | * Flags: |
|---|
| 681 | 735 | * TEGRA_DIVIDER_2 - LP cluster has additional divider. This flag indicates |
|---|
| 682 | 736 | * that this is LP cluster clock. |
|---|
| 737 | + * TEGRA210_CPU_CLK - This flag is used to identify CPU cluster for gen5 |
|---|
| 738 | + * super mux parent using PLLP branches. To use PLLP branches to CPU, need |
|---|
| 739 | + * to configure additional bit PLLP_OUT_CPU in the clock registers. |
|---|
| 740 | + * TEGRA20_SUPER_CLK - Tegra20 doesn't have a dedicated divider for Super |
|---|
| 741 | + * clocks, it only has a clock-skipper. |
|---|
| 683 | 742 | */ |
|---|
| 684 | 743 | struct tegra_clk_super_mux { |
|---|
| 685 | 744 | struct clk_hw hw; |
|---|
| .. | .. |
|---|
| 696 | 755 | #define to_clk_super_mux(_hw) container_of(_hw, struct tegra_clk_super_mux, hw) |
|---|
| 697 | 756 | |
|---|
| 698 | 757 | #define TEGRA_DIVIDER_2 BIT(0) |
|---|
| 758 | +#define TEGRA210_CPU_CLK BIT(1) |
|---|
| 759 | +#define TEGRA20_SUPER_CLK BIT(2) |
|---|
| 699 | 760 | |
|---|
| 700 | 761 | extern const struct clk_ops tegra_clk_super_ops; |
|---|
| 701 | 762 | struct clk *tegra_clk_register_super_mux(const char *name, |
|---|
| .. | .. |
|---|
| 706 | 767 | const char * const *parent_names, u8 num_parents, |
|---|
| 707 | 768 | unsigned long flags, void __iomem *reg, u8 clk_super_flags, |
|---|
| 708 | 769 | spinlock_t *lock); |
|---|
| 770 | +struct clk *tegra_clk_register_super_cclk(const char *name, |
|---|
| 771 | + const char * const *parent_names, u8 num_parents, |
|---|
| 772 | + unsigned long flags, void __iomem *reg, u8 clk_super_flags, |
|---|
| 773 | + spinlock_t *lock); |
|---|
| 774 | +int tegra_cclk_pre_pllx_rate_change(void); |
|---|
| 775 | +void tegra_cclk_post_pllx_rate_change(void); |
|---|
| 709 | 776 | |
|---|
| 710 | 777 | /** |
|---|
| 711 | 778 | * struct tegra_sdmmc_mux - switch divider with Low Jitter inputs for SDMMC |
|---|
| .. | .. |
|---|
| 802 | 869 | struct tegra_clk *tegra_clks, |
|---|
| 803 | 870 | struct tegra_clk_pll_params *pll_params); |
|---|
| 804 | 871 | |
|---|
| 805 | | -void tegra_pmc_clk_init(void __iomem *pmc_base, struct tegra_clk *tegra_clks); |
|---|
| 806 | 872 | void tegra_fixed_clk_init(struct tegra_clk *tegra_clks); |
|---|
| 807 | 873 | int tegra_osc_clk_init(void __iomem *clk_base, struct tegra_clk *clks, |
|---|
| 808 | 874 | unsigned long *input_freqs, unsigned int num, |
|---|
| .. | .. |
|---|
| 815 | 881 | void __iomem *pmc_base, struct tegra_clk *tegra_clks, |
|---|
| 816 | 882 | struct tegra_clk_pll_params *pll_params); |
|---|
| 817 | 883 | |
|---|
| 818 | | -#ifdef CONFIG_TEGRA_CLK_EMC |
|---|
| 884 | +#ifdef CONFIG_TEGRA124_EMC |
|---|
| 819 | 885 | struct clk *tegra_clk_register_emc(void __iomem *base, struct device_node *np, |
|---|
| 820 | 886 | spinlock_t *lock); |
|---|
| 821 | 887 | #else |
|---|
| .. | .. |
|---|
| 840 | 906 | int tegra_pll_p_div_to_hw(struct tegra_clk_pll *pll, u8 p_div); |
|---|
| 841 | 907 | int div_frac_get(unsigned long rate, unsigned parent_rate, u8 width, |
|---|
| 842 | 908 | u8 frac_width, u8 flags); |
|---|
| 909 | +void tegra_clk_osc_resume(void __iomem *clk_base); |
|---|
| 910 | +void tegra_clk_set_pllp_out_cpu(bool enable); |
|---|
| 911 | +void tegra_clk_periph_suspend(void); |
|---|
| 912 | +void tegra_clk_periph_resume(void); |
|---|
| 843 | 913 | |
|---|
| 844 | 914 | |
|---|
| 845 | 915 | /* Combined read fence with delay */ |
|---|
| .. | .. |
|---|
| 849 | 919 | udelay(delay); \ |
|---|
| 850 | 920 | } while (0) |
|---|
| 851 | 921 | |
|---|
| 922 | +bool tegra20_clk_emc_driver_available(struct clk_hw *emc_hw); |
|---|
| 923 | +struct clk *tegra20_clk_register_emc(void __iomem *ioaddr, bool low_jitter); |
|---|
| 924 | + |
|---|
| 925 | +struct clk *tegra210_clk_register_emc(struct device_node *np, |
|---|
| 926 | + void __iomem *regs); |
|---|
| 927 | + |
|---|
| 852 | 928 | #endif /* TEGRA_CLK_H */ |
|---|