Module Name: src Committed By: jmcneill Date: Sat Apr 22 23:53:24 UTC 2017
Modified Files: src/sys/arch/arm/nvidia: files.tegra soc_tegra124.c tegra_cpufreq.c tegra_fdt.c tegra_soc.c tegra_var.h src/sys/arch/evbarm/conf: TEGRA Log Message: Get rid of tegra_cpuinit after scanning fdt and attach the cpufreq support to the /cpus node. Use regulator API instead of poking directly at the I2C controller to set voltages. To generate a diff of this commit: cvs rdiff -u -r1.31 -r1.32 src/sys/arch/arm/nvidia/files.tegra cvs rdiff -u -r1.15 -r1.16 src/sys/arch/arm/nvidia/soc_tegra124.c cvs rdiff -u -r1.4 -r1.5 src/sys/arch/arm/nvidia/tegra_cpufreq.c \ src/sys/arch/arm/nvidia/tegra_fdt.c cvs rdiff -u -r1.9 -r1.10 src/sys/arch/arm/nvidia/tegra_soc.c cvs rdiff -u -r1.32 -r1.33 src/sys/arch/arm/nvidia/tegra_var.h cvs rdiff -u -r1.16 -r1.17 src/sys/arch/evbarm/conf/TEGRA Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/arch/arm/nvidia/files.tegra diff -u src/sys/arch/arm/nvidia/files.tegra:1.31 src/sys/arch/arm/nvidia/files.tegra:1.32 --- src/sys/arch/arm/nvidia/files.tegra:1.31 Fri Apr 21 23:35:29 2017 +++ src/sys/arch/arm/nvidia/files.tegra Sat Apr 22 23:53:24 2017 @@ -1,4 +1,4 @@ -# $NetBSD: files.tegra,v 1.31 2017/04/21 23:35:29 jmcneill Exp $ +# $NetBSD: files.tegra,v 1.32 2017/04/22 23:53:24 jmcneill Exp $ # # Configuration info for NVIDIA Tegra ARM Peripherals # @@ -13,15 +13,19 @@ file arch/arm/arm32/irq_dispatch.S file arch/arm/arm32/armv7_generic_space.c file arch/arm/arm/bus_space_a4x.S -file arch/arm/nvidia/tegra_soc.c -file arch/arm/nvidia/tegra_cpufreq.c -file arch/arm/nvidia/soc_tegra124.c soc_tegra124 - -# On-board I/O +# Devicetree device tegrafdt : bus_space_generic, fdtbus attach tegrafdt at mainbus with tegra_fdt file arch/arm/nvidia/tegra_fdt.c tegra_fdt +file arch/arm/nvidia/tegra_soc.c +file arch/arm/nvidia/tegra_cpufreq.c + +# Tegra T124 (32-bit K1) support +device tegra124cpu +attach tegra124cpu at fdt with tegra124_cpu +file arch/arm/nvidia/soc_tegra124.c soc_tegra124 | tegra124_cpu + # Interrupt controller device tegralic attach tegralic at fdt with tegra_lic Index: src/sys/arch/arm/nvidia/soc_tegra124.c diff -u src/sys/arch/arm/nvidia/soc_tegra124.c:1.15 src/sys/arch/arm/nvidia/soc_tegra124.c:1.16 --- src/sys/arch/arm/nvidia/soc_tegra124.c:1.15 Mon Apr 17 00:43:42 2017 +++ src/sys/arch/arm/nvidia/soc_tegra124.c Sat Apr 22 23:53:24 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: soc_tegra124.c,v 1.15 2017/04/17 00:43:42 jmcneill Exp $ */ +/* $NetBSD: soc_tegra124.c,v 1.16 2017/04/22 23:53:24 jmcneill Exp $ */ /*- * Copyright (c) 2015 Jared D. McNeill <jmcne...@invisible.ca> @@ -30,7 +30,7 @@ #include "opt_multiprocessor.h" #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: soc_tegra124.c,v 1.15 2017/04/17 00:43:42 jmcneill Exp $"); +__KERNEL_RCSID(0, "$NetBSD: soc_tegra124.c,v 1.16 2017/04/22 23:53:24 jmcneill Exp $"); #include <sys/param.h> #include <sys/bus.h> @@ -39,8 +39,6 @@ __KERNEL_RCSID(0, "$NetBSD: soc_tegra124 #include <uvm/uvm_extern.h> -#include <dev/clk/clk.h> -#include <dev/i2c/i2cvar.h> #include <dev/fdt/fdtvar.h> #include <arm/cpufunc.h> @@ -71,6 +69,13 @@ static u_int tegra124_cpufreq_set_rate(u static u_int tegra124_cpufreq_get_rate(void); static size_t tegra124_cpufreq_get_available(u_int *, size_t); +static int tegra124_cpu_match(device_t, cfdata_t, void *); +static void tegra124_cpu_attach(device_t, device_t, void *); +static void tegra124_cpu_init_cpufreq(device_t); + +CFATTACH_DECL_NEW(tegra124_cpu, 0, tegra124_cpu_match, tegra124_cpu_attach, + NULL, NULL); + static const struct tegra_cpufreq_func tegra124_cpufreq_func = { .set_rate = tegra124_cpufreq_set_rate, .get_rate = tegra124_cpufreq_get_rate, @@ -82,16 +87,17 @@ static struct tegra124_cpufreq_rate { u_int divm; u_int divn; u_int divp; + u_int uvol; } tegra124_cpufreq_rates[] = { - { 2316, 1, 193, 0 }, - { 2100, 1, 175, 0 }, - { 1896, 1, 158, 0 }, - { 1692, 1, 141, 0 }, - { 1500, 1, 125, 0 }, - { 1296, 1, 108, 0 }, - { 1092, 1, 91, 0 }, - { 900, 1, 75, 0 }, - { 696, 1, 58, 0 } + { 2316, 1, 193, 0, 1400000 }, + { 2100, 1, 175, 0, 1400000 }, + { 1896, 1, 158, 0, 1400000 }, + { 1692, 1, 141, 0, 1400000 }, + { 1500, 1, 125, 0, 1400000 }, + { 1296, 1, 108, 0, 1400000 }, + { 1092, 1, 91, 0, 1400000 }, + { 900, 1, 75, 0, 1400000 }, + { 696, 1, 58, 0, 1400000 } }; static const u_int tegra124_cpufreq_max[] = { @@ -112,42 +118,46 @@ static struct tegra124_speedo { }; static struct clk *tegra124_clk_pllx = NULL; +static struct fdtbus_regulator *tegra124_reg_vddcpu = NULL; -void -tegra124_cpuinit(void) +static int +tegra124_cpu_match(device_t parent, cfdata_t cf, void *aux) { - int i2c_node = OF_finddevice("/i2c@7000d000"); - if (i2c_node == -1) - i2c_node = OF_finddevice("/i2c@0,7000d000"); /* old DTB */ - if (i2c_node == -1) { - aprint_error("cpufreq: ERROR: couldn't find i2c@7000d000\n"); - return; - } - i2c_tag_t ic = fdtbus_get_i2c_tag(i2c_node); + const char * const compatible[] = { "nvidia,tegra124", NULL }; + struct fdt_attach_args *faa = aux; - /* Set VDD_CPU voltage to 1.4V */ - const u_int target_mv = 1400; - const u_int sd0_vsel = (target_mv - 600) / 10; - uint8_t data[2] = { 0x00, sd0_vsel }; - - iic_acquire_bus(ic, I2C_F_POLL); - const int error = iic_exec(ic, I2C_OP_WRITE_WITH_STOP, 0x40, - NULL, 0, data, sizeof(data), I2C_F_POLL); - iic_release_bus(ic, I2C_F_POLL); - if (error) { - aprint_error("cpufreq: ERROR: couldn't set VDD_CPU: %d\n", - error); - return; - } - delay(10000); + if (OF_finddevice("/cpus") != faa->faa_phandle) + return 0; + + return of_match_compatible(OF_finddevice("/"), compatible); +} + +static void +tegra124_cpu_attach(device_t parent, device_t self, void *aux) +{ + aprint_naive("\n"); + aprint_normal(": CPU complex\n"); + + config_defer(self, tegra124_cpu_init_cpufreq); +} +static void +tegra124_cpu_init_cpufreq(device_t dev) +{ tegra124_speedo_init(); int cpu_node = OF_finddevice("/cpus/cpu@0"); - if (cpu_node != -1) + if (cpu_node != -1) { tegra124_clk_pllx = fdtbus_clock_get(cpu_node, "pll_x"); + tegra124_reg_vddcpu = fdtbus_regulator_acquire(cpu_node, + "vdd-cpu-supply"); + } if (tegra124_clk_pllx == NULL) { - aprint_error("cpufreq: ERROR: couldn't find pll_x\n"); + aprint_error_dev(dev, "couldn't find clock pll_x\n"); + return; + } + if (tegra124_reg_vddcpu == NULL) { + aprint_error_dev(dev, "couldn't find voltage regulator\n"); return; } @@ -226,6 +236,7 @@ tegra124_cpufreq_set_rate(u_int rate) const struct tegra124_cpufreq_rate *r = NULL; CPU_INFO_ITERATOR cii; struct cpu_info *ci; + u_int cur_uvol; int error; if (tegra124_speedo_rate_ok(rate) == false) @@ -240,6 +251,17 @@ tegra124_cpufreq_set_rate(u_int rate) if (r == NULL) return EINVAL; + error = fdtbus_regulator_get_voltage(tegra124_reg_vddcpu, &cur_uvol); + if (error != 0) + return error; + + if (cur_uvol < r->uvol) { + error = fdtbus_regulator_set_voltage(tegra124_reg_vddcpu, + r->uvol, r->uvol); + if (error != 0) + return error; + } + error = clk_set_rate(tegra124_clk_pllx, r->rate * 1000000); if (error == 0) { rate = tegra124_cpufreq_get_rate(); @@ -248,6 +270,11 @@ tegra124_cpufreq_set_rate(u_int rate) } } + if (cur_uvol > r->uvol) { + (void)fdtbus_regulator_set_voltage(tegra124_reg_vddcpu, + r->uvol, r->uvol); + } + return error; } Index: src/sys/arch/arm/nvidia/tegra_cpufreq.c diff -u src/sys/arch/arm/nvidia/tegra_cpufreq.c:1.4 src/sys/arch/arm/nvidia/tegra_cpufreq.c:1.5 --- src/sys/arch/arm/nvidia/tegra_cpufreq.c:1.4 Mon Nov 21 04:10:05 2016 +++ src/sys/arch/arm/nvidia/tegra_cpufreq.c Sat Apr 22 23:53:24 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: tegra_cpufreq.c,v 1.4 2016/11/21 04:10:05 ozaki-r Exp $ */ +/* $NetBSD: tegra_cpufreq.c,v 1.5 2017/04/22 23:53:24 jmcneill Exp $ */ /*- * Copyright (c) 2015 Jared D. McNeill <jmcne...@invisible.ca> @@ -29,7 +29,7 @@ #include "locators.h" #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: tegra_cpufreq.c,v 1.4 2016/11/21 04:10:05 ozaki-r Exp $"); +__KERNEL_RCSID(0, "$NetBSD: tegra_cpufreq.c,v 1.5 2017/04/22 23:53:24 jmcneill Exp $"); #include <sys/param.h> #include <sys/bus.h> @@ -59,20 +59,13 @@ static char tegra_cpufreq_available[TEG void tegra_cpufreq_register(const struct tegra_cpufreq_func *cf) { - KASSERT(cpufreq_func == NULL); - cpufreq_func = cf; -} - -void -tegra_cpufreq_init(void) -{ const struct sysctlnode *node, *cpunode, *freqnode; u_int availfreq[TEGRA_CPUFREQ_MAX]; size_t nfreq; int error; - if (cpufreq_func == NULL) - return; + KASSERT(cpufreq_func == NULL); + cpufreq_func = cf; nfreq = cpufreq_get_available(availfreq, TEGRA_CPUFREQ_MAX); if (nfreq == 0) Index: src/sys/arch/arm/nvidia/tegra_fdt.c diff -u src/sys/arch/arm/nvidia/tegra_fdt.c:1.4 src/sys/arch/arm/nvidia/tegra_fdt.c:1.5 --- src/sys/arch/arm/nvidia/tegra_fdt.c:1.4 Sun Apr 16 12:27:47 2017 +++ src/sys/arch/arm/nvidia/tegra_fdt.c Sat Apr 22 23:53:24 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: tegra_fdt.c,v 1.4 2017/04/16 12:27:47 jmcneill Exp $ */ +/* $NetBSD: tegra_fdt.c,v 1.5 2017/04/22 23:53:24 jmcneill Exp $ */ /*- * Copyright (c) 2015 Jared D. McNeill <jmcne...@invisible.ca> @@ -29,7 +29,7 @@ #include "opt_tegra.h" #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: tegra_fdt.c,v 1.4 2017/04/16 12:27:47 jmcneill Exp $"); +__KERNEL_RCSID(0, "$NetBSD: tegra_fdt.c,v 1.5 2017/04/22 23:53:24 jmcneill Exp $"); #include <sys/param.h> #include <sys/systm.h> @@ -77,6 +77,4 @@ tegrafdt_attach(device_t parent, device_ .faa_phandle = OF_peer(0), }; config_found(self, &faa, NULL); - - tegra_cpuinit(); } Index: src/sys/arch/arm/nvidia/tegra_soc.c diff -u src/sys/arch/arm/nvidia/tegra_soc.c:1.9 src/sys/arch/arm/nvidia/tegra_soc.c:1.10 --- src/sys/arch/arm/nvidia/tegra_soc.c:1.9 Sat Mar 26 09:07:31 2016 +++ src/sys/arch/arm/nvidia/tegra_soc.c Sat Apr 22 23:53:24 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: tegra_soc.c,v 1.9 2016/03/26 09:07:31 skrll Exp $ */ +/* $NetBSD: tegra_soc.c,v 1.10 2017/04/22 23:53:24 jmcneill Exp $ */ /*- * Copyright (c) 2015 Jared D. McNeill <jmcne...@invisible.ca> @@ -30,7 +30,7 @@ #include "opt_multiprocessor.h" #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: tegra_soc.c,v 1.9 2016/03/26 09:07:31 skrll Exp $"); +__KERNEL_RCSID(0, "$NetBSD: tegra_soc.c,v 1.10 2017/04/22 23:53:24 jmcneill Exp $"); #define _ARM32_BUS_DMA_PRIVATE #include <sys/param.h> @@ -89,20 +89,6 @@ tegra_dma_bootstrap(psize_t psize) { } -void -tegra_cpuinit(void) -{ - switch (tegra_chip_id()) { -#ifdef SOC_TEGRA124 - case CHIP_ID_TEGRA124: - tegra124_cpuinit(); - break; -#endif - } - - tegra_cpufreq_init(); -} - static void tegra_mpinit(void) { Index: src/sys/arch/arm/nvidia/tegra_var.h diff -u src/sys/arch/arm/nvidia/tegra_var.h:1.32 src/sys/arch/arm/nvidia/tegra_var.h:1.33 --- src/sys/arch/arm/nvidia/tegra_var.h:1.32 Fri Apr 21 21:13:04 2017 +++ src/sys/arch/arm/nvidia/tegra_var.h Sat Apr 22 23:53:24 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: tegra_var.h,v 1.32 2017/04/21 21:13:04 jmcneill Exp $ */ +/* $NetBSD: tegra_var.h,v 1.33 2017/04/22 23:53:24 jmcneill Exp $ */ /*- * Copyright (c) 2015 Jared D. McNeill <jmcne...@invisible.ca> @@ -51,7 +51,6 @@ u_int tegra_chip_id(void); const char *tegra_chip_name(void); void tegra_bootstrap(void); void tegra_dma_bootstrap(psize_t); -void tegra_cpuinit(void); struct tegra_gpio_pin; struct tegra_gpio_pin *tegra_gpio_acquire(const char *, u_int); @@ -103,10 +102,8 @@ struct tegra_cpufreq_func { size_t (*get_available)(u_int *, size_t); }; void tegra_cpufreq_register(const struct tegra_cpufreq_func *); -void tegra_cpufreq_init(void); #if defined(SOC_TEGRA124) -void tegra124_cpuinit(void); void tegra124_mpinit(void); #endif Index: src/sys/arch/evbarm/conf/TEGRA diff -u src/sys/arch/evbarm/conf/TEGRA:1.16 src/sys/arch/evbarm/conf/TEGRA:1.17 --- src/sys/arch/evbarm/conf/TEGRA:1.16 Sat Apr 22 21:50:13 2017 +++ src/sys/arch/evbarm/conf/TEGRA Sat Apr 22 23:53:24 2017 @@ -1,5 +1,5 @@ # -# $NetBSD: TEGRA,v 1.16 2017/04/22 21:50:13 jmcneill Exp $ +# $NetBSD: TEGRA,v 1.17 2017/04/22 23:53:24 jmcneill Exp $ # # NVIDIA Tegra K1 (T124) # @@ -39,6 +39,9 @@ armgtmr0 at armperiph? # ARM Generic tegrafdt0 at mainbus? fdt* at fdtbus? +# CPU frequency scaling +tegra124cpu* at fdt? + fclock* at fdt? fregulator* at fdt? gpiokeys* at fdt?