From bcd78a0be617be07234e3ef4925cecaef66f2fa4 Mon Sep 17 00:00:00 2001 From: Seema Khowala Date: Tue, 31 Oct 2017 20:56:29 -0700 Subject: nvgpu: gv11b: implement railgate/unrailgate Implement gv11b platform specific rail gating functions by calling relevant powergate and unpowergate functions and linux clock frmework functions: gv11b_tegra_is_railgated gv11b_tegra_railgate gv11b_tegra_unrailgate These calls will take care of hot reset sequence required for gpu powergate and gpu unpowergate. Bug 200269361 Bug 200273571 Change-Id: Ib1825e4324d51fc508b3b5dc9e5e2fdb252eeff4 Signed-off-by: seshendra Gadagottu Signed-off-by: Seema Khowala Reviewed-on: https://git-master.nvidia.com/r/1589509 Reviewed-by: Automatic_Commit_Validation_User GVS: Gerrit_Virtual_Submit Reviewed-by: Terje Bergstrom Reviewed-by: mobile promotions Tested-by: mobile promotions --- drivers/gpu/nvgpu/gv11b/platform_gv11b_tegra.c | 59 ++++++++++++++++++++++++++ 1 file changed, 59 insertions(+) (limited to 'drivers/gpu/nvgpu/gv11b/platform_gv11b_tegra.c') diff --git a/drivers/gpu/nvgpu/gv11b/platform_gv11b_tegra.c b/drivers/gpu/nvgpu/gv11b/platform_gv11b_tegra.c index ca346d97..95d82254 100644 --- a/drivers/gpu/nvgpu/gv11b/platform_gv11b_tegra.c +++ b/drivers/gpu/nvgpu/gv11b/platform_gv11b_tegra.c @@ -28,11 +28,15 @@ #include #include #include +#include #include #include #include +#include +#include + #include "gk20a/gk20a.h" #include "common/linux/platform_gk20a.h" #include "common/linux/clk.h" @@ -103,18 +107,73 @@ static int gv11b_tegra_remove(struct device *dev) static bool gv11b_tegra_is_railgated(struct device *dev) { bool ret = false; +#ifdef TEGRA194_POWER_DOMAIN_GPU + struct gk20a *g = get_gk20a(dev); + + if (tegra_bpmp_running()) { + nvgpu_log(g, gpu_dbg_info, "bpmp running"); + ret = !tegra_powergate_is_powered(TEGRA194_POWER_DOMAIN_GPU); + nvgpu_log(g, gpu_dbg_info, "railgated? %s", ret ? "yes" : "no"); + } else { + nvgpu_log(g, gpu_dbg_info, "bpmp not running"); + } +#endif return ret; } static int gv11b_tegra_railgate(struct device *dev) { +#ifdef TEGRA194_POWER_DOMAIN_GPU + struct gk20a_platform *platform = gk20a_get_platform(dev); + struct gk20a *g = get_gk20a(dev); + int i; + + if (tegra_bpmp_running()) { + nvgpu_log(g, gpu_dbg_info, "bpmp running"); + if (!tegra_powergate_is_powered(TEGRA194_POWER_DOMAIN_GPU)) { + nvgpu_log(g, gpu_dbg_info, "powergate is not powered"); + return 0; + } + nvgpu_log(g, gpu_dbg_info, "clk_disable_unprepare"); + for (i = 0; i < platform->num_clks; i++) { + if (platform->clk[i]) + clk_disable_unprepare(platform->clk[i]); + } + nvgpu_log(g, gpu_dbg_info, "powergate_partition"); + tegra_powergate_partition(TEGRA194_POWER_DOMAIN_GPU); + } else { + nvgpu_log(g, gpu_dbg_info, "bpmp not running"); + } +#endif return 0; } static int gv11b_tegra_unrailgate(struct device *dev) { int ret = 0; +#ifdef TEGRA194_POWER_DOMAIN_GPU + struct gk20a_platform *platform = gk20a_get_platform(dev); + struct gk20a *g = get_gk20a(dev); + int i; + + if (tegra_bpmp_running()) { + nvgpu_log(g, gpu_dbg_info, "bpmp running"); + ret = tegra_unpowergate_partition(TEGRA194_POWER_DOMAIN_GPU); + if (ret) { + nvgpu_log(g, gpu_dbg_info, + "unpowergate partition failed"); + return ret; + } + nvgpu_log(g, gpu_dbg_info, "clk_prepare_enable"); + for (i = 0; i < platform->num_clks; i++) { + if (platform->clk[i]) + clk_prepare_enable(platform->clk[i]); + } + } else { + nvgpu_log(g, gpu_dbg_info, "bpmp not running"); + } +#endif return ret; } -- cgit v1.2.2