Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'tegra-for-4.7-clk' of git://git.kernel.org/pub/scm/linux/kernel/git/tegra/linux into clk-next

Pull tegra clk driver changes from Thierry Reding:

This set of changes contains a bunch of cleanups and minor fixes along
with some new clocks, mainly on Tegra210, in preparation for supporting
DisplayPort and HDMI 2.0.

* tag 'tegra-for-4.7-clk' of git://git.kernel.org/pub/scm/linux/kernel/git/tegra/linux:
clk: tegra: dfll: Reformat CVB frequency table
clk: tegra: dfll: Properly clean up on failure and removal
clk: tegra: dfll: Make code more comprehensible
clk: tegra: dfll: Reference CVB table instead of copying data
clk: tegra: dfll: Update kerneldoc
clk: tegra: Fix PLL_U post divider and initial rate on Tegra30
clk: tegra: Initialize PLL_C to sane rate on Tegra30
clk: tegra: Fix pllre Tegra210 and add pll_re_out1
clk: tegra: Add sor_safe clock
clk: tegra: dpaux and dpaux1 are fixed factor clocks
clk: tegra: Add dpaux1 clock
clk: tegra: Use correct parent for dpaux clock
clk: tegra: Add fixed factor peripheral clock type
clk: tegra: Special-case mipi-cal parent on Tegra114
clk: tegra: Remove trailing blank line
clk: tegra: Constify peripheral clock registers
clk: tegra: Add interface to enable hardware control of SATA/XUSB PLLs

+433 -115
+1
drivers/clk/tegra/Makefile
··· 3 3 obj-y += clk-dfll.o 4 4 obj-y += clk-divider.o 5 5 obj-y += clk-periph.o 6 + obj-y += clk-periph-fixed.o 6 7 obj-y += clk-periph-gate.o 7 8 obj-y += clk-pll.o 8 9 obj-y += clk-pll-out.o
+6 -5
drivers/clk/tegra/clk-dfll.c
··· 55 55 #include <linux/seq_file.h> 56 56 57 57 #include "clk-dfll.h" 58 + #include "cvb.h" 58 59 59 60 /* 60 61 * DFLL control registers - access via dfll_{readl,writel} ··· 443 442 { 444 443 td->tune_range = DFLL_TUNE_LOW; 445 444 446 - dfll_writel(td, td->soc->tune0_low, DFLL_TUNE0); 447 - dfll_writel(td, td->soc->tune1, DFLL_TUNE1); 445 + dfll_writel(td, td->soc->cvb->cpu_dfll_data.tune0_low, DFLL_TUNE0); 446 + dfll_writel(td, td->soc->cvb->cpu_dfll_data.tune1, DFLL_TUNE1); 448 447 dfll_wmb(td); 449 448 450 449 if (td->soc->set_clock_trimmers_low) ··· 1450 1449 } 1451 1450 v_max = dev_pm_opp_get_voltage(opp); 1452 1451 1453 - v = td->soc->min_millivolts * 1000; 1452 + v = td->soc->cvb->min_millivolts * 1000; 1454 1453 lut = find_vdd_map_entry_exact(td, v); 1455 1454 if (lut < 0) 1456 1455 goto out; ··· 1462 1461 break; 1463 1462 v_opp = dev_pm_opp_get_voltage(opp); 1464 1463 1465 - if (v_opp <= td->soc->min_millivolts * 1000) 1464 + if (v_opp <= td->soc->cvb->min_millivolts * 1000) 1466 1465 td->dvco_rate_min = dev_pm_opp_get_freq(opp); 1467 1466 1468 1467 for (;;) { ··· 1491 1490 1492 1491 if (!td->dvco_rate_min) 1493 1492 dev_err(td->dev, "no opp above DFLL minimum voltage %d mV\n", 1494 - td->soc->min_millivolts); 1493 + td->soc->cvb->min_millivolts); 1495 1494 else 1496 1495 ret = 0; 1497 1496
+9 -13
drivers/clk/tegra/clk-dfll.h
··· 24 24 25 25 /** 26 26 * struct tegra_dfll_soc_data - SoC-specific hooks/integration for the DFLL driver 27 - * @opp_dev: struct device * that holds the OPP table for the DFLL 28 - * @min_millivolts: minimum voltage (in mV) that the DFLL can operate 29 - * @tune0_low: DFLL tuning register 0 (low voltage range) 30 - * @tune0_high: DFLL tuning register 0 (high voltage range) 31 - * @tune1: DFLL tuning register 1 32 - * @assert_dvco_reset: fn ptr to place the DVCO in reset 33 - * @deassert_dvco_reset: fn ptr to release the DVCO reset 34 - * @set_clock_trimmers_high: fn ptr to tune clock trimmers for high voltage 35 - * @set_clock_trimmers_low: fn ptr to tune clock trimmers for low voltage 27 + * @dev: struct device * that holds the OPP table for the DFLL 28 + * @max_freq: maximum frequency supported on this SoC 29 + * @cvb: CPU frequency table for this SoC 30 + * @init_clock_trimmers: callback to initialize clock trimmers 31 + * @set_clock_trimmers_high: callback to tune clock trimmers for high voltage 32 + * @set_clock_trimmers_low: callback to tune clock trimmers for low voltage 36 33 */ 37 34 struct tegra_dfll_soc_data { 38 35 struct device *dev; 39 - unsigned int min_millivolts; 40 - u32 tune0_low; 41 - u32 tune0_high; 42 - u32 tune1; 36 + unsigned long max_freq; 37 + const struct cvb_table *cvb; 38 + 43 39 void (*init_clock_trimmers)(void); 44 40 void (*set_clock_trimmers_high)(void); 45 41 void (*set_clock_trimmers_low)(void);
+2
drivers/clk/tegra/clk-id.h
··· 71 71 tegra_clk_disp2_8, 72 72 tegra_clk_dp2, 73 73 tegra_clk_dpaux, 74 + tegra_clk_dpaux1, 74 75 tegra_clk_dsialp, 75 76 tegra_clk_dsia_mux, 76 77 tegra_clk_dsiblp, ··· 307 306 tegra_clk_xusb_ss_div2, 308 307 tegra_clk_xusb_ssp_src, 309 308 tegra_clk_sclk_mux, 309 + tegra_clk_sor_safe, 310 310 tegra_clk_max, 311 311 }; 312 312
+120
drivers/clk/tegra/clk-periph-fixed.c
··· 1 + /* 2 + * Copyright (c) 2015, 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 + */ 16 + 17 + #include <linux/clk-provider.h> 18 + 19 + #include "clk.h" 20 + 21 + static inline struct tegra_clk_periph_fixed * 22 + to_tegra_clk_periph_fixed(struct clk_hw *hw) 23 + { 24 + return container_of(hw, struct tegra_clk_periph_fixed, hw); 25 + } 26 + 27 + static int tegra_clk_periph_fixed_is_enabled(struct clk_hw *hw) 28 + { 29 + struct tegra_clk_periph_fixed *fixed = to_tegra_clk_periph_fixed(hw); 30 + u32 mask = 1 << (fixed->num % 32), value; 31 + 32 + value = readl(fixed->base + fixed->regs->enb_reg); 33 + if (value & mask) { 34 + value = readl(fixed->base + fixed->regs->rst_reg); 35 + if ((value & mask) == 0) 36 + return 1; 37 + } 38 + 39 + return 0; 40 + } 41 + 42 + static int tegra_clk_periph_fixed_enable(struct clk_hw *hw) 43 + { 44 + struct tegra_clk_periph_fixed *fixed = to_tegra_clk_periph_fixed(hw); 45 + u32 mask = 1 << (fixed->num % 32); 46 + 47 + writel(mask, fixed->base + fixed->regs->enb_set_reg); 48 + 49 + return 0; 50 + } 51 + 52 + static void tegra_clk_periph_fixed_disable(struct clk_hw *hw) 53 + { 54 + struct tegra_clk_periph_fixed *fixed = to_tegra_clk_periph_fixed(hw); 55 + u32 mask = 1 << (fixed->num % 32); 56 + 57 + writel(mask, fixed->base + fixed->regs->enb_clr_reg); 58 + } 59 + 60 + static unsigned long 61 + tegra_clk_periph_fixed_recalc_rate(struct clk_hw *hw, 62 + unsigned long parent_rate) 63 + { 64 + struct tegra_clk_periph_fixed *fixed = to_tegra_clk_periph_fixed(hw); 65 + unsigned long long rate; 66 + 67 + rate = (unsigned long long)parent_rate * fixed->mul; 68 + do_div(rate, fixed->div); 69 + 70 + return (unsigned long)rate; 71 + } 72 + 73 + static const struct clk_ops tegra_clk_periph_fixed_ops = { 74 + .is_enabled = tegra_clk_periph_fixed_is_enabled, 75 + .enable = tegra_clk_periph_fixed_enable, 76 + .disable = tegra_clk_periph_fixed_disable, 77 + .recalc_rate = tegra_clk_periph_fixed_recalc_rate, 78 + }; 79 + 80 + struct clk *tegra_clk_register_periph_fixed(const char *name, 81 + const char *parent, 82 + unsigned long flags, 83 + void __iomem *base, 84 + unsigned int mul, 85 + unsigned int div, 86 + unsigned int num) 87 + { 88 + const struct tegra_clk_periph_regs *regs; 89 + struct tegra_clk_periph_fixed *fixed; 90 + struct clk_init_data init; 91 + struct clk *clk; 92 + 93 + regs = get_reg_bank(num); 94 + if (!regs) 95 + return ERR_PTR(-EINVAL); 96 + 97 + fixed = kzalloc(sizeof(*fixed), GFP_KERNEL); 98 + if (!fixed) 99 + return ERR_PTR(-ENOMEM); 100 + 101 + init.name = name; 102 + init.flags = flags; 103 + init.parent_names = parent ? &parent : NULL; 104 + init.num_parents = parent ? 1 : 0; 105 + init.ops = &tegra_clk_periph_fixed_ops; 106 + 107 + fixed->base = base; 108 + fixed->regs = regs; 109 + fixed->mul = mul; 110 + fixed->div = div; 111 + fixed->num = num; 112 + 113 + fixed->hw.init = &init; 114 + 115 + clk = clk_register(NULL, &fixed->hw); 116 + if (IS_ERR(clk)) 117 + kfree(fixed); 118 + 119 + return clk; 120 + }
+1 -1
drivers/clk/tegra/clk-periph-gate.c
··· 134 134 struct tegra_clk_periph_gate *gate; 135 135 struct clk *clk; 136 136 struct clk_init_data init; 137 - struct tegra_clk_periph_regs *pregs; 137 + const struct tegra_clk_periph_regs *pregs; 138 138 139 139 pregs = get_reg_bank(clk_num); 140 140 if (!pregs)
+1 -1
drivers/clk/tegra/clk-periph.c
··· 145 145 { 146 146 struct clk *clk; 147 147 struct clk_init_data init; 148 - struct tegra_clk_periph_regs *bank; 148 + const struct tegra_clk_periph_regs *bank; 149 149 bool div = !(periph->gate.flags & TEGRA_PERIPH_NO_DIV); 150 150 151 151 if (periph->gate.flags & TEGRA_PERIPH_NO_DIV) {
+46
drivers/clk/tegra/clk-pll.c
··· 2013 2013 #endif 2014 2014 2015 2015 #if defined(CONFIG_ARCH_TEGRA_210_SOC) 2016 + struct clk *tegra_clk_register_pllre_tegra210(const char *name, 2017 + const char *parent_name, void __iomem *clk_base, 2018 + void __iomem *pmc, unsigned long flags, 2019 + struct tegra_clk_pll_params *pll_params, 2020 + spinlock_t *lock, unsigned long parent_rate) 2021 + { 2022 + u32 val; 2023 + struct tegra_clk_pll *pll; 2024 + struct clk *clk; 2025 + 2026 + pll_params->vco_min = _clip_vco_min(pll_params->vco_min, parent_rate); 2027 + 2028 + if (pll_params->adjust_vco) 2029 + pll_params->vco_min = pll_params->adjust_vco(pll_params, 2030 + parent_rate); 2031 + 2032 + pll = _tegra_init_pll(clk_base, pmc, pll_params, lock); 2033 + if (IS_ERR(pll)) 2034 + return ERR_CAST(pll); 2035 + 2036 + /* program minimum rate by default */ 2037 + 2038 + val = pll_readl_base(pll); 2039 + if (val & PLL_BASE_ENABLE) 2040 + WARN_ON(readl_relaxed(clk_base + pll_params->iddq_reg) & 2041 + BIT(pll_params->iddq_bit_idx)); 2042 + else { 2043 + val = 0x4 << divm_shift(pll); 2044 + val |= 0x41 << divn_shift(pll); 2045 + pll_writel_base(val, pll); 2046 + } 2047 + 2048 + /* disable lock override */ 2049 + 2050 + val = pll_readl_misc(pll); 2051 + val &= ~BIT(29); 2052 + pll_writel_misc(val, pll); 2053 + 2054 + clk = _tegra_clk_register_pll(pll, name, parent_name, flags, 2055 + &tegra_clk_pllre_ops); 2056 + if (IS_ERR(clk)) 2057 + kfree(pll); 2058 + 2059 + return clk; 2060 + } 2061 + 2016 2062 static int clk_plle_tegra210_enable(struct clk_hw *hw) 2017 2063 { 2018 2064 struct tegra_clk_pll *pll = to_clk_pll(hw);
-1
drivers/clk/tegra/clk-tegra-fixed.c
··· 107 107 *dt_clk = clk; 108 108 } 109 109 } 110 -
+2 -3
drivers/clk/tegra/clk-tegra-periph.c
··· 803 803 GATE("hda2hdmi", "clk_m", 128, TEGRA_PERIPH_ON_APB, tegra_clk_hda2hdmi, 0), 804 804 GATE("bsea", "clk_m", 62, 0, tegra_clk_bsea, 0), 805 805 GATE("bsev", "clk_m", 63, 0, tegra_clk_bsev, 0), 806 - GATE("mipi-cal", "clk_m", 56, 0, tegra_clk_mipi_cal, 0), 806 + GATE("mipi-cal", "clk72mhz", 56, 0, tegra_clk_mipi_cal, 0), 807 807 GATE("usbd", "clk_m", 22, 0, tegra_clk_usbd, 0), 808 808 GATE("usb2", "clk_m", 58, 0, tegra_clk_usb2, 0), 809 809 GATE("usb3", "clk_m", 59, 0, tegra_clk_usb3, 0), ··· 821 821 GATE("ispb", "clk_m", 3, 0, tegra_clk_ispb, 0), 822 822 GATE("vim2_clk", "clk_m", 11, 0, tegra_clk_vim2_clk, 0), 823 823 GATE("pcie", "clk_m", 70, 0, tegra_clk_pcie, 0), 824 - GATE("dpaux", "clk_m", 181, 0, tegra_clk_dpaux, 0), 825 824 GATE("gpu", "pll_ref", 184, 0, tegra_clk_gpu, 0), 826 825 GATE("pllg_ref", "pll_ref", 189, 0, tegra_clk_pll_g_ref, 0), 827 826 GATE("hsic_trk", "usb2_hsic_trk", 209, TEGRA_PERIPH_NO_RESET, tegra_clk_hsic_trk, 0), ··· 876 877 struct clk **dt_clk; 877 878 878 879 for (i = 0; i < ARRAY_SIZE(periph_clks); i++) { 879 - struct tegra_clk_periph_regs *bank; 880 + const struct tegra_clk_periph_regs *bank; 880 881 struct tegra_periph_init_data *data; 881 882 882 883 data = periph_clks + i;
+5 -1
drivers/clk/tegra/clk-tegra114.c
··· 743 743 [tegra_clk_csi] = { .dt_id = TEGRA114_CLK_CSI, .present = true }, 744 744 [tegra_clk_i2c2] = { .dt_id = TEGRA114_CLK_I2C2, .present = true }, 745 745 [tegra_clk_uartc] = { .dt_id = TEGRA114_CLK_UARTC, .present = true }, 746 - [tegra_clk_mipi_cal] = { .dt_id = TEGRA114_CLK_MIPI_CAL, .present = true }, 747 746 [tegra_clk_emc] = { .dt_id = TEGRA114_CLK_EMC, .present = true }, 748 747 [tegra_clk_usb2] = { .dt_id = TEGRA114_CLK_USB2, .present = true }, 749 748 [tegra_clk_usb3] = { .dt_id = TEGRA114_CLK_USB3, .present = true }, ··· 1235 1236 clk = tegra_clk_register_mc("mc", "emc_mux", clk_base + CLK_SOURCE_EMC, 1236 1237 &emc_lock); 1237 1238 clks[TEGRA114_CLK_MC] = clk; 1239 + 1240 + clk = tegra_clk_register_periph_gate("mipi-cal", "clk_m", 0, clk_base, 1241 + CLK_SET_RATE_PARENT, 56, 1242 + periph_clk_enb_refcnt); 1243 + clks[TEGRA114_CLK_MIPI_CAL] = clk; 1238 1244 1239 1245 for (i = 0; i < ARRAY_SIZE(tegra_periph_clk_list); i++) { 1240 1246 data = &tegra_periph_clk_list[i];
+60 -43
drivers/clk/tegra/clk-tegra124-dfll-fcpu.c
··· 47 47 }, 48 48 .speedo_scale = 100, 49 49 .voltage_scale = 1000, 50 - .cvb_table = { 51 - {204000000UL, {1112619, -29295, 402} }, 52 - {306000000UL, {1150460, -30585, 402} }, 53 - {408000000UL, {1190122, -31865, 402} }, 54 - {510000000UL, {1231606, -33155, 402} }, 55 - {612000000UL, {1274912, -34435, 402} }, 56 - {714000000UL, {1320040, -35725, 402} }, 57 - {816000000UL, {1366990, -37005, 402} }, 58 - {918000000UL, {1415762, -38295, 402} }, 59 - {1020000000UL, {1466355, -39575, 402} }, 60 - {1122000000UL, {1518771, -40865, 402} }, 61 - {1224000000UL, {1573009, -42145, 402} }, 62 - {1326000000UL, {1629068, -43435, 402} }, 63 - {1428000000UL, {1686950, -44715, 402} }, 64 - {1530000000UL, {1746653, -46005, 402} }, 65 - {1632000000UL, {1808179, -47285, 402} }, 66 - {1734000000UL, {1871526, -48575, 402} }, 67 - {1836000000UL, {1936696, -49855, 402} }, 68 - {1938000000UL, {2003687, -51145, 402} }, 69 - {2014500000UL, {2054787, -52095, 402} }, 70 - {2116500000UL, {2124957, -53385, 402} }, 71 - {2218500000UL, {2196950, -54665, 402} }, 72 - {2320500000UL, {2270765, -55955, 402} }, 73 - {2422500000UL, {2346401, -57235, 402} }, 74 - {2524500000UL, {2437299, -58535, 402} }, 75 - {0, { 0, 0, 0} }, 50 + .entries = { 51 + { 204000000UL, { 1112619, -29295, 402 } }, 52 + { 306000000UL, { 1150460, -30585, 402 } }, 53 + { 408000000UL, { 1190122, -31865, 402 } }, 54 + { 510000000UL, { 1231606, -33155, 402 } }, 55 + { 612000000UL, { 1274912, -34435, 402 } }, 56 + { 714000000UL, { 1320040, -35725, 402 } }, 57 + { 816000000UL, { 1366990, -37005, 402 } }, 58 + { 918000000UL, { 1415762, -38295, 402 } }, 59 + { 1020000000UL, { 1466355, -39575, 402 } }, 60 + { 1122000000UL, { 1518771, -40865, 402 } }, 61 + { 1224000000UL, { 1573009, -42145, 402 } }, 62 + { 1326000000UL, { 1629068, -43435, 402 } }, 63 + { 1428000000UL, { 1686950, -44715, 402 } }, 64 + { 1530000000UL, { 1746653, -46005, 402 } }, 65 + { 1632000000UL, { 1808179, -47285, 402 } }, 66 + { 1734000000UL, { 1871526, -48575, 402 } }, 67 + { 1836000000UL, { 1936696, -49855, 402 } }, 68 + { 1938000000UL, { 2003687, -51145, 402 } }, 69 + { 2014500000UL, { 2054787, -52095, 402 } }, 70 + { 2116500000UL, { 2124957, -53385, 402 } }, 71 + { 2218500000UL, { 2196950, -54665, 402 } }, 72 + { 2320500000UL, { 2270765, -55955, 402 } }, 73 + { 2422500000UL, { 2346401, -57235, 402 } }, 74 + { 2524500000UL, { 2437299, -58535, 402 } }, 75 + { 0UL, { 0, 0, 0 } }, 76 76 }, 77 77 .cpu_dfll_data = { 78 78 .tune0_low = 0x005020ff, ··· 84 84 85 85 static int tegra124_dfll_fcpu_probe(struct platform_device *pdev) 86 86 { 87 - int process_id, speedo_id, speedo_value; 87 + int process_id, speedo_id, speedo_value, err; 88 88 struct tegra_dfll_soc_data *soc; 89 - const struct cvb_table *cvb; 90 89 91 90 process_id = tegra_sku_info.cpu_process_id; 92 91 speedo_id = tegra_sku_info.cpu_speedo_id; ··· 107 108 return -ENODEV; 108 109 } 109 110 110 - cvb = tegra_cvb_build_opp_table(tegra124_cpu_cvb_tables, 111 - ARRAY_SIZE(tegra124_cpu_cvb_tables), 112 - process_id, speedo_id, speedo_value, 113 - cpu_max_freq_table[speedo_id], 114 - soc->dev); 115 - if (IS_ERR(cvb)) { 116 - dev_err(&pdev->dev, "couldn't build OPP table: %ld\n", 117 - PTR_ERR(cvb)); 118 - return PTR_ERR(cvb); 111 + soc->max_freq = cpu_max_freq_table[speedo_id]; 112 + 113 + soc->cvb = tegra_cvb_add_opp_table(soc->dev, tegra124_cpu_cvb_tables, 114 + ARRAY_SIZE(tegra124_cpu_cvb_tables), 115 + process_id, speedo_id, speedo_value, 116 + soc->max_freq); 117 + if (IS_ERR(soc->cvb)) { 118 + dev_err(&pdev->dev, "couldn't add OPP table: %ld\n", 119 + PTR_ERR(soc->cvb)); 120 + return PTR_ERR(soc->cvb); 119 121 } 120 122 121 - soc->min_millivolts = cvb->min_millivolts; 122 - soc->tune0_low = cvb->cpu_dfll_data.tune0_low; 123 - soc->tune0_high = cvb->cpu_dfll_data.tune0_high; 124 - soc->tune1 = cvb->cpu_dfll_data.tune1; 123 + err = tegra_dfll_register(pdev, soc); 124 + if (err < 0) { 125 + tegra_cvb_remove_opp_table(soc->dev, soc->cvb, soc->max_freq); 126 + return err; 127 + } 125 128 126 - return tegra_dfll_register(pdev, soc); 129 + platform_set_drvdata(pdev, soc); 130 + 131 + return 0; 132 + } 133 + 134 + static int tegra124_dfll_fcpu_remove(struct platform_device *pdev) 135 + { 136 + struct tegra_dfll_soc_data *soc = platform_get_drvdata(pdev); 137 + int err; 138 + 139 + err = tegra_dfll_unregister(pdev); 140 + if (err < 0) 141 + dev_err(&pdev->dev, "failed to unregister DFLL: %d\n", err); 142 + 143 + tegra_cvb_remove_opp_table(soc->dev, soc->cvb, soc->max_freq); 144 + 145 + return 0; 127 146 } 128 147 129 148 static const struct of_device_id tegra124_dfll_fcpu_of_match[] = { ··· 157 140 158 141 static struct platform_driver tegra124_dfll_fcpu_driver = { 159 142 .probe = tegra124_dfll_fcpu_probe, 160 - .remove = tegra_dfll_unregister, 143 + .remove = tegra124_dfll_fcpu_remove, 161 144 .driver = { 162 145 .name = "tegra124-dfll", 163 146 .of_match_table = tegra124_dfll_fcpu_of_match,
+4
drivers/clk/tegra/clk-tegra124.c
··· 1155 1155 1, 2); 1156 1156 clks[TEGRA124_CLK_XUSB_SS_DIV2] = clk; 1157 1157 1158 + clk = tegra_clk_register_periph_fixed("dpaux", "pll_p", 0, clk_base, 1159 + 1, 17, 181); 1160 + clks[TEGRA124_CLK_DPAUX] = clk; 1161 + 1158 1162 clk = clk_register_gate(NULL, "pll_d_dsi_out", "pll_d_out0", 0, 1159 1163 clk_base + PLLD_MISC, 30, 0, &pll_d_lock); 1160 1164 clks[TEGRA124_CLK_PLL_D_DSI_OUT] = clk;
+85 -2
drivers/clk/tegra/clk-tegra210.c
··· 92 92 #define PLLE_AUX 0x48c 93 93 #define PLLRE_BASE 0x4c4 94 94 #define PLLRE_MISC0 0x4c8 95 + #define PLLRE_OUT1 0x4cc 95 96 #define PLLDP_BASE 0x590 96 97 #define PLLDP_MISC 0x594 97 98 ··· 175 174 #define UTMIP_PLL_CFG1_FORCE_PLL_ENABLE_POWERUP BIT(15) 176 175 #define UTMIP_PLL_CFG1_FORCE_PLL_ENABLE_POWERDOWN BIT(14) 177 176 #define UTMIP_PLL_CFG1_FORCE_PLL_ACTIVE_POWERDOWN BIT(12) 177 + 178 + #define SATA_PLL_CFG0 0x490 179 + #define SATA_PLL_CFG0_PADPLL_RESET_SWCTL BIT(0) 180 + #define SATA_PLL_CFG0_PADPLL_USE_LOCKDET BIT(2) 181 + #define SATA_PLL_CFG0_PADPLL_SLEEP_IDDQ BIT(13) 182 + #define SATA_PLL_CFG0_SEQ_ENABLE BIT(24) 183 + 184 + #define XUSBIO_PLL_CFG0 0x51c 185 + #define XUSBIO_PLL_CFG0_PADPLL_RESET_SWCTL BIT(0) 186 + #define XUSBIO_PLL_CFG0_CLK_ENABLE_SWCTL BIT(2) 187 + #define XUSBIO_PLL_CFG0_PADPLL_USE_LOCKDET BIT(6) 188 + #define XUSBIO_PLL_CFG0_PADPLL_SLEEP_IDDQ BIT(13) 189 + #define XUSBIO_PLL_CFG0_SEQ_ENABLE BIT(24) 178 190 179 191 #define UTMIPLL_HW_PWRDN_CFG0 0x52c 180 192 #define UTMIPLL_HW_PWRDN_CFG0_UTMIPLL_LOCK BIT(31) ··· 429 415 430 416 #define PLLU_MISC0_WRITE_MASK 0xbfffffff 431 417 #define PLLU_MISC1_WRITE_MASK 0x00000007 418 + 419 + void tegra210_xusb_pll_hw_control_enable(void) 420 + { 421 + u32 val; 422 + 423 + val = readl_relaxed(clk_base + XUSBIO_PLL_CFG0); 424 + val &= ~(XUSBIO_PLL_CFG0_CLK_ENABLE_SWCTL | 425 + XUSBIO_PLL_CFG0_PADPLL_RESET_SWCTL); 426 + val |= XUSBIO_PLL_CFG0_PADPLL_USE_LOCKDET | 427 + XUSBIO_PLL_CFG0_PADPLL_SLEEP_IDDQ; 428 + writel_relaxed(val, clk_base + XUSBIO_PLL_CFG0); 429 + } 430 + EXPORT_SYMBOL_GPL(tegra210_xusb_pll_hw_control_enable); 431 + 432 + void tegra210_xusb_pll_hw_sequence_start(void) 433 + { 434 + u32 val; 435 + 436 + val = readl_relaxed(clk_base + XUSBIO_PLL_CFG0); 437 + val |= XUSBIO_PLL_CFG0_SEQ_ENABLE; 438 + writel_relaxed(val, clk_base + XUSBIO_PLL_CFG0); 439 + } 440 + EXPORT_SYMBOL_GPL(tegra210_xusb_pll_hw_sequence_start); 441 + 442 + void tegra210_sata_pll_hw_control_enable(void) 443 + { 444 + u32 val; 445 + 446 + val = readl_relaxed(clk_base + SATA_PLL_CFG0); 447 + val &= ~SATA_PLL_CFG0_PADPLL_RESET_SWCTL; 448 + val |= SATA_PLL_CFG0_PADPLL_USE_LOCKDET | 449 + SATA_PLL_CFG0_PADPLL_SLEEP_IDDQ; 450 + writel_relaxed(val, clk_base + SATA_PLL_CFG0); 451 + } 452 + EXPORT_SYMBOL_GPL(tegra210_sata_pll_hw_control_enable); 453 + 454 + void tegra210_sata_pll_hw_sequence_start(void) 455 + { 456 + u32 val; 457 + 458 + val = readl_relaxed(clk_base + SATA_PLL_CFG0); 459 + val |= SATA_PLL_CFG0_SEQ_ENABLE; 460 + writel_relaxed(val, clk_base + SATA_PLL_CFG0); 461 + } 462 + EXPORT_SYMBOL_GPL(tegra210_sata_pll_hw_sequence_start); 432 463 433 464 static inline void _pll_misc_chk_default(void __iomem *base, 434 465 struct tegra_clk_pll_params *params, ··· 2151 2092 [tegra_clk_clk72Mhz_8] = { .dt_id = TEGRA210_CLK_CLK72MHZ, .present = true }, 2152 2093 [tegra_clk_vic03_8] = { .dt_id = TEGRA210_CLK_VIC03, .present = true }, 2153 2094 [tegra_clk_dpaux] = { .dt_id = TEGRA210_CLK_DPAUX, .present = true }, 2095 + [tegra_clk_dpaux1] = { .dt_id = TEGRA210_CLK_DPAUX1, .present = true }, 2154 2096 [tegra_clk_sor0] = { .dt_id = TEGRA210_CLK_SOR0, .present = true }, 2155 2097 [tegra_clk_sor0_lvds] = { .dt_id = TEGRA210_CLK_SOR0_LVDS, .present = true }, 2156 2098 [tegra_clk_gpu] = { .dt_id = TEGRA210_CLK_GPU, .present = true }, ··· 2463 2403 1, 2); 2464 2404 clks[TEGRA210_CLK_XUSB_SS_DIV2] = clk; 2465 2405 2406 + clk = tegra_clk_register_periph_fixed("dpaux", "pll_p", 0, clk_base, 2407 + 1, 17, 181); 2408 + clks[TEGRA210_CLK_DPAUX] = clk; 2409 + 2410 + clk = tegra_clk_register_periph_fixed("dpaux1", "pll_p", 0, clk_base, 2411 + 1, 17, 207); 2412 + clks[TEGRA210_CLK_DPAUX1] = clk; 2413 + 2414 + clk = tegra_clk_register_periph_fixed("sor_safe", "pll_p", 0, clk_base, 2415 + 1, 17, 222); 2416 + clks[TEGRA210_CLK_SOR_SAFE] = clk; 2417 + 2466 2418 /* pll_d_dsi_out */ 2467 2419 clk = clk_register_gate(NULL, "pll_d_dsi_out", "pll_d_out0", 0, 2468 2420 clk_base + PLLD_MISC0, 21, 0, &pll_d_lock); ··· 2654 2582 clks[TEGRA210_CLK_PLL_D_OUT0] = clk; 2655 2583 2656 2584 /* PLLRE */ 2657 - clk = tegra_clk_register_pllre("pll_re_vco", "pll_ref", clk_base, pmc, 2658 - 0, &pll_re_vco_params, &pll_re_lock, pll_ref_freq); 2585 + clk = tegra_clk_register_pllre_tegra210("pll_re_vco", "pll_ref", 2586 + clk_base, pmc, 0, 2587 + &pll_re_vco_params, 2588 + &pll_re_lock, pll_ref_freq); 2659 2589 clk_register_clkdev(clk, "pll_re_vco", NULL); 2660 2590 clks[TEGRA210_CLK_PLL_RE_VCO] = clk; 2661 2591 ··· 2666 2592 pll_vco_post_div_table, &pll_re_lock); 2667 2593 clk_register_clkdev(clk, "pll_re_out", NULL); 2668 2594 clks[TEGRA210_CLK_PLL_RE_OUT] = clk; 2595 + 2596 + clk = tegra_clk_register_divider("pll_re_out1_div", "pll_re_vco", 2597 + clk_base + PLLRE_OUT1, 0, 2598 + TEGRA_DIVIDER_ROUND_UP, 2599 + 8, 8, 1, NULL); 2600 + clk = tegra_clk_register_pll_out("pll_re_out1", "pll_re_out1_div", 2601 + clk_base + PLLRE_OUT1, 1, 0, 2602 + CLK_SET_RATE_PARENT, 0, NULL); 2603 + clks[TEGRA210_CLK_PLL_RE_OUT1] = clk; 2669 2604 2670 2605 /* PLLE */ 2671 2606 clk = tegra_clk_register_plle_tegra210("pll_e", "pll_ref",
+7 -5
drivers/clk/tegra/clk-tegra30.c
··· 339 339 }; 340 340 341 341 static struct tegra_clk_pll_freq_table pll_u_freq_table[] = { 342 - { 12000000, 480000000, 960, 12, 1, 12 }, 343 - { 13000000, 480000000, 960, 13, 1, 12 }, 344 - { 16800000, 480000000, 400, 7, 1, 5 }, 345 - { 19200000, 480000000, 200, 4, 1, 3 }, 346 - { 26000000, 480000000, 960, 26, 1, 12 }, 342 + { 12000000, 480000000, 960, 12, 2, 12 }, 343 + { 13000000, 480000000, 960, 13, 2, 12 }, 344 + { 16800000, 480000000, 400, 7, 2, 5 }, 345 + { 19200000, 480000000, 200, 4, 2, 3 }, 346 + { 26000000, 480000000, 960, 26, 2, 12 }, 347 347 { 0, 0, 0, 0, 0, 0 }, 348 348 }; 349 349 ··· 1372 1372 { TEGRA30_CLK_SBC4, TEGRA30_CLK_PLL_P, 100000000, 0 }, 1373 1373 { TEGRA30_CLK_SBC5, TEGRA30_CLK_PLL_P, 100000000, 0 }, 1374 1374 { TEGRA30_CLK_SBC6, TEGRA30_CLK_PLL_P, 100000000, 0 }, 1375 + { TEGRA30_CLK_PLL_C, TEGRA30_CLK_CLK_MAX, 600000000, 0 }, 1375 1376 { TEGRA30_CLK_HOST1X, TEGRA30_CLK_PLL_C, 150000000, 0 }, 1376 1377 { TEGRA30_CLK_DISP1, TEGRA30_CLK_PLL_P, 600000000, 0 }, 1377 1378 { TEGRA30_CLK_DISP2, TEGRA30_CLK_PLL_P, 600000000, 0 }, ··· 1380 1379 { TEGRA30_CLK_GR2D, TEGRA30_CLK_PLL_C, 300000000, 0 }, 1381 1380 { TEGRA30_CLK_GR3D, TEGRA30_CLK_PLL_C, 300000000, 0 }, 1382 1381 { TEGRA30_CLK_GR3D2, TEGRA30_CLK_PLL_C, 300000000, 0 }, 1382 + { TEGRA30_CLK_PLL_U, TEGRA30_CLK_CLK_MAX, 480000000, 0 }, 1383 1383 /* must be the last entry */ 1384 1384 { TEGRA30_CLK_CLK_MAX, TEGRA30_CLK_CLK_MAX, 0, 0 }, 1385 1385 };
+2 -2
drivers/clk/tegra/clk.c
··· 84 84 static int (*special_reset_deassert)(unsigned long); 85 85 static unsigned int num_special_reset; 86 86 87 - static struct tegra_clk_periph_regs periph_regs[] = { 87 + static const struct tegra_clk_periph_regs periph_regs[] = { 88 88 [0] = { 89 89 .enb_reg = CLK_OUT_ENB_L, 90 90 .enb_set_reg = CLK_OUT_ENB_SET_L, ··· 182 182 return -EINVAL; 183 183 } 184 184 185 - struct tegra_clk_periph_regs *get_reg_bank(int clkid) 185 + const struct tegra_clk_periph_regs *get_reg_bank(int clkid) 186 186 { 187 187 int reg_bank = clkid / 32; 188 188
+25 -2
drivers/clk/tegra/clk.h
··· 386 386 struct tegra_clk_pll_params *pll_params, 387 387 spinlock_t *lock, unsigned long parent_rate); 388 388 389 + struct clk *tegra_clk_register_pllre_tegra210(const char *name, 390 + const char *parent_name, void __iomem *clk_base, 391 + void __iomem *pmc, unsigned long flags, 392 + struct tegra_clk_pll_params *pll_params, 393 + spinlock_t *lock, unsigned long parent_rate); 394 + 389 395 struct clk *tegra_clk_register_plle_tegra114(const char *name, 390 396 const char *parent_name, 391 397 void __iomem *clk_base, unsigned long flags, ··· 502 496 u8 flags; 503 497 int clk_num; 504 498 int *enable_refcnt; 505 - struct tegra_clk_periph_regs *regs; 499 + const struct tegra_clk_periph_regs *regs; 506 500 }; 507 501 508 502 #define to_clk_periph_gate(_hw) \ ··· 521 515 struct clk *tegra_clk_register_periph_gate(const char *name, 522 516 const char *parent_name, u8 gate_flags, void __iomem *clk_base, 523 517 unsigned long flags, int clk_num, int *enable_refcnt); 518 + 519 + struct tegra_clk_periph_fixed { 520 + struct clk_hw hw; 521 + void __iomem *base; 522 + const struct tegra_clk_periph_regs *regs; 523 + unsigned int mul; 524 + unsigned int div; 525 + unsigned int num; 526 + }; 527 + 528 + struct clk *tegra_clk_register_periph_fixed(const char *name, 529 + const char *parent, 530 + unsigned long flags, 531 + void __iomem *base, 532 + unsigned int mul, 533 + unsigned int div, 534 + unsigned int num); 524 535 525 536 /** 526 537 * struct clk-periph - peripheral clock ··· 739 716 void tegra_init_dup_clks(struct tegra_clk_duplicate *dup_list, 740 717 struct clk *clks[], int clk_max); 741 718 742 - struct tegra_clk_periph_regs *get_reg_bank(int clkid); 719 + const struct tegra_clk_periph_regs *get_reg_bank(int clkid); 743 720 struct clk **tegra_clk_init(void __iomem *clk_base, int num, int periph_banks); 744 721 745 722 struct clk **tegra_lookup_dt_id(int clk_id, struct tegra_clk *tegra_clk);
+43 -28
drivers/clk/tegra/cvb.c
··· 61 61 return mv; 62 62 } 63 63 64 - static int build_opp_table(const struct cvb_table *d, 65 - int speedo_value, 66 - unsigned long max_freq, 67 - struct device *opp_dev) 64 + static int build_opp_table(struct device *dev, const struct cvb_table *table, 65 + int speedo_value, unsigned long max_freq) 68 66 { 67 + const struct rail_alignment *align = &table->alignment; 69 68 int i, ret, dfll_mv, min_mv, max_mv; 70 - const struct cvb_table_freq_entry *table = NULL; 71 - const struct rail_alignment *align = &d->alignment; 72 69 73 - min_mv = round_voltage(d->min_millivolts, align, UP); 74 - max_mv = round_voltage(d->max_millivolts, align, DOWN); 70 + min_mv = round_voltage(table->min_millivolts, align, UP); 71 + max_mv = round_voltage(table->max_millivolts, align, DOWN); 75 72 76 73 for (i = 0; i < MAX_DVFS_FREQS; i++) { 77 - table = &d->cvb_table[i]; 78 - if (!table->freq || (table->freq > max_freq)) 74 + const struct cvb_table_freq_entry *entry = &table->entries[i]; 75 + 76 + if (!entry->freq || (entry->freq > max_freq)) 79 77 break; 80 78 81 - dfll_mv = get_cvb_voltage( 82 - speedo_value, d->speedo_scale, &table->coefficients); 83 - dfll_mv = round_cvb_voltage(dfll_mv, d->voltage_scale, align); 79 + dfll_mv = get_cvb_voltage(speedo_value, table->speedo_scale, 80 + &entry->coefficients); 81 + dfll_mv = round_cvb_voltage(dfll_mv, table->voltage_scale, 82 + align); 84 83 dfll_mv = clamp(dfll_mv, min_mv, max_mv); 85 84 86 - ret = dev_pm_opp_add(opp_dev, table->freq, dfll_mv * 1000); 85 + ret = dev_pm_opp_add(dev, entry->freq, dfll_mv * 1000); 87 86 if (ret) 88 87 return ret; 89 88 } ··· 91 92 } 92 93 93 94 /** 94 - * tegra_cvb_build_opp_table - build OPP table from Tegra CVB tables 95 + * tegra_cvb_add_opp_table - build OPP table from Tegra CVB tables 95 96 * @cvb_tables: array of CVB tables 96 97 * @sz: size of the previously mentioned array 97 98 * @process_id: process id of the HW module ··· 107 108 * given @opp_dev. Returns a pointer to the struct cvb_table that matched 108 109 * or an ERR_PTR on failure. 109 110 */ 110 - const struct cvb_table *tegra_cvb_build_opp_table( 111 - const struct cvb_table *cvb_tables, 112 - size_t sz, int process_id, 113 - int speedo_id, int speedo_value, 114 - unsigned long max_rate, 115 - struct device *opp_dev) 111 + const struct cvb_table * 112 + tegra_cvb_add_opp_table(struct device *dev, const struct cvb_table *tables, 113 + size_t count, int process_id, int speedo_id, 114 + int speedo_value, unsigned long max_freq) 116 115 { 117 - int i, ret; 116 + size_t i; 117 + int ret; 118 118 119 - for (i = 0; i < sz; i++) { 120 - const struct cvb_table *d = &cvb_tables[i]; 119 + for (i = 0; i < count; i++) { 120 + const struct cvb_table *table = &tables[i]; 121 121 122 - if (d->speedo_id != -1 && d->speedo_id != speedo_id) 122 + if (table->speedo_id != -1 && table->speedo_id != speedo_id) 123 123 continue; 124 - if (d->process_id != -1 && d->process_id != process_id) 124 + 125 + if (table->process_id != -1 && table->process_id != process_id) 125 126 continue; 126 127 127 - ret = build_opp_table(d, speedo_value, max_rate, opp_dev); 128 - return ret ? ERR_PTR(ret) : d; 128 + ret = build_opp_table(dev, table, speedo_value, max_freq); 129 + return ret ? ERR_PTR(ret) : table; 129 130 } 130 131 131 132 return ERR_PTR(-EINVAL); 133 + } 134 + 135 + void tegra_cvb_remove_opp_table(struct device *dev, 136 + const struct cvb_table *table, 137 + unsigned long max_freq) 138 + { 139 + unsigned int i; 140 + 141 + for (i = 0; i < MAX_DVFS_FREQS; i++) { 142 + const struct cvb_table_freq_entry *entry = &table->entries[i]; 143 + 144 + if (!entry->freq || (entry->freq > max_freq)) 145 + break; 146 + 147 + dev_pm_opp_remove(dev, entry->freq); 148 + } 132 149 }
+8 -7
drivers/clk/tegra/cvb.h
··· 53 53 54 54 int speedo_scale; 55 55 int voltage_scale; 56 - struct cvb_table_freq_entry cvb_table[MAX_DVFS_FREQS]; 56 + struct cvb_table_freq_entry entries[MAX_DVFS_FREQS]; 57 57 struct cvb_cpu_dfll_data cpu_dfll_data; 58 58 }; 59 59 60 - const struct cvb_table *tegra_cvb_build_opp_table( 61 - const struct cvb_table *cvb_tables, 62 - size_t sz, int process_id, 63 - int speedo_id, int speedo_value, 64 - unsigned long max_rate, 65 - struct device *opp_dev); 60 + const struct cvb_table * 61 + tegra_cvb_add_opp_table(struct device *dev, const struct cvb_table *cvb_tables, 62 + size_t count, int process_id, int speedo_id, 63 + int speedo_value, unsigned long max_freq); 64 + void tegra_cvb_remove_opp_table(struct device *dev, 65 + const struct cvb_table *table, 66 + unsigned long max_freq); 66 67 67 68 #endif
+1 -1
include/dt-bindings/clock/tegra210-car.h
··· 346 346 #define TEGRA210_CLK_PLL_P_OUT_HSIO 316 347 347 #define TEGRA210_CLK_PLL_P_OUT_XUSB 317 348 348 #define TEGRA210_CLK_XUSB_SSP_SRC 318 349 - /* 319 */ 349 + #define TEGRA210_CLK_PLL_RE_OUT1 319 350 350 /* 320 */ 351 351 /* 321 */ 352 352 /* 322 */
+5
include/linux/clk/tegra.h
··· 121 121 } 122 122 #endif 123 123 124 + extern void tegra210_xusb_pll_hw_control_enable(void); 125 + extern void tegra210_xusb_pll_hw_sequence_start(void); 126 + extern void tegra210_sata_pll_hw_control_enable(void); 127 + extern void tegra210_sata_pll_hw_sequence_start(void); 128 + 124 129 #endif /* __LINUX_CLK_TEGRA_H_ */