summaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorDeepak Nibade <dnibade@nvidia.com>2014-11-03 04:05:53 -0500
committerDan Willemsen <dwillemsen@nvidia.com>2015-03-18 15:12:00 -0400
commitc3661adef806869a7e0df884fc621c48436961d4 (patch)
treef5dae90d31852f8c49eb9bdab4b206c347dc1149 /drivers
parentca95cc76bbaf0d15804d554a9ebfcc708a20c8c4 (diff)
gpu: nvgpu: fix reset clock in gm20b
To assert reset on GPU, we store "gpu_ref" clock in platform->clk[0] and use it to assert/deassert reset But for gm20b, "gpu_ref" is no longer resettable. To fix this, add two callbacks in gk20a_platform : .reset_assert and .reset_deassert Also, add a pointer "clk_reset" to store the clock which needs to be reset For gk20a specific implementation, we continue to reset platform->clk[0] For gm20b specific implementation, we first request "gpu_gate" clock, store it and use it to assert reset Bug 1513685 Bug 1517584 Change-Id: I15a583a4a07eb663b442084be8b8c7d0c7c7a142 Signed-off-by: Deepak Nibade <dnibade@nvidia.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/gpu/nvgpu/gk20a/gk20a.c8
-rw-r--r--drivers/gpu/nvgpu/gk20a/platform_gk20a.h5
-rw-r--r--drivers/gpu/nvgpu/gk20a/platform_gk20a_tegra.c51
3 files changed, 62 insertions, 2 deletions
diff --git a/drivers/gpu/nvgpu/gk20a/gk20a.c b/drivers/gpu/nvgpu/gk20a/gk20a.c
index d411d011..c7d40fcd 100644
--- a/drivers/gpu/nvgpu/gk20a/gk20a.c
+++ b/drivers/gpu/nvgpu/gk20a/gk20a.c
@@ -1671,10 +1671,14 @@ int __gk20a_do_idle(struct platform_device *pdev)
1671 else 1671 else
1672 goto fail_timeout; 1672 goto fail_timeout;
1673 } else { 1673 } else {
1674 if (!platform->reset_assert || !platform->reset_deassert)
1675 goto fail_timeout;
1676
1674 pm_runtime_get_sync(&pdev->dev); 1677 pm_runtime_get_sync(&pdev->dev);
1675 gk20a_pm_prepare_poweroff(&pdev->dev); 1678 gk20a_pm_prepare_poweroff(&pdev->dev);
1676 1679
1677 tegra_periph_reset_assert(platform->clk[0]); 1680 platform->reset_assert(pdev);
1681
1678 udelay(10); 1682 udelay(10);
1679 1683
1680 g->forced_reset = true; 1684 g->forced_reset = true;
@@ -1717,7 +1721,7 @@ int __gk20a_do_unidle(struct platform_device *pdev)
1717 struct gk20a_platform *platform = dev_get_drvdata(&pdev->dev); 1721 struct gk20a_platform *platform = dev_get_drvdata(&pdev->dev);
1718 1722
1719 if (g->forced_reset) { 1723 if (g->forced_reset) {
1720 tegra_periph_reset_deassert(platform->clk[0]); 1724 platform->reset_deassert(pdev);
1721 1725
1722 gk20a_pm_finalize_poweron(&pdev->dev); 1726 gk20a_pm_finalize_poweron(&pdev->dev);
1723 pm_runtime_put_sync(&pdev->dev); 1727 pm_runtime_put_sync(&pdev->dev);
diff --git a/drivers/gpu/nvgpu/gk20a/platform_gk20a.h b/drivers/gpu/nvgpu/gk20a/platform_gk20a.h
index 0cc04595..5f7285bf 100644
--- a/drivers/gpu/nvgpu/gk20a/platform_gk20a.h
+++ b/drivers/gpu/nvgpu/gk20a/platform_gk20a.h
@@ -155,6 +155,11 @@ struct gk20a_platform {
155 */ 155 */
156 void (*dump_platform_dependencies)(struct platform_device *dev); 156 void (*dump_platform_dependencies)(struct platform_device *dev);
157 157
158 /* Callbacks to assert/deassert GPU reset */
159 int (*reset_assert)(struct platform_device *pdev);
160 int (*reset_deassert)(struct platform_device *pdev);
161 struct clk *clk_reset;
162
158 bool virtual_dev; 163 bool virtual_dev;
159#ifdef CONFIG_TEGRA_GR_VIRTUALIZATION 164#ifdef CONFIG_TEGRA_GR_VIRTUALIZATION
160 u64 virt_handle; 165 u64 virt_handle;
diff --git a/drivers/gpu/nvgpu/gk20a/platform_gk20a_tegra.c b/drivers/gpu/nvgpu/gk20a/platform_gk20a_tegra.c
index e9530844..185d661e 100644
--- a/drivers/gpu/nvgpu/gk20a/platform_gk20a_tegra.c
+++ b/drivers/gpu/nvgpu/gk20a/platform_gk20a_tegra.c
@@ -24,6 +24,7 @@
24#include <linux/dma-buf.h> 24#include <linux/dma-buf.h>
25#include <linux/nvmap.h> 25#include <linux/nvmap.h>
26#include <linux/tegra_pm_domains.h> 26#include <linux/tegra_pm_domains.h>
27#include <linux/platform/tegra/clock.h>
27 28
28#include "gk20a.h" 29#include "gk20a.h"
29#include "hal_gk20a.h" 30#include "hal_gk20a.h"
@@ -321,6 +322,47 @@ err_get_clock:
321 return ret; 322 return ret;
322} 323}
323 324
325static int gk20a_tegra_reset_assert(struct platform_device *dev)
326{
327 struct gk20a_platform *platform = gk20a_get_platform(dev);
328
329 if (!platform->clk_reset)
330 platform->clk_reset = platform->clk[0];
331
332 tegra_periph_reset_assert(platform->clk_reset);
333
334 return 0;
335}
336
337static int gk20a_tegra_reset_deassert(struct platform_device *dev)
338{
339 struct gk20a_platform *platform = gk20a_get_platform(dev);
340
341 if (!platform->clk_reset)
342 return -EINVAL;
343
344 tegra_periph_reset_deassert(platform->clk_reset);
345
346 return 0;
347}
348
349static int gm20b_tegra_reset_assert(struct platform_device *dev)
350{
351 struct gk20a_platform *platform = gk20a_get_platform(dev);
352
353 if (!platform->clk_reset) {
354 platform->clk_reset = clk_get(&dev->dev, "gpu_gate");
355 if (IS_ERR(platform->clk_reset)) {
356 gk20a_err(&dev->dev, "fail to get gpu reset clk\n");
357 return PTR_ERR(platform->clk_reset);
358 }
359 }
360
361 tegra_periph_reset_assert(platform->clk_reset);
362
363 return 0;
364}
365
324static void gk20a_tegra_scale_init(struct platform_device *pdev) 366static void gk20a_tegra_scale_init(struct platform_device *pdev)
325{ 367{
326 struct gk20a_platform *platform = gk20a_get_platform(pdev); 368 struct gk20a_platform *platform = gk20a_get_platform(pdev);
@@ -457,6 +499,9 @@ struct gk20a_platform t132_gk20a_tegra_platform = {
457 .busy = gk20a_tegra_busy, 499 .busy = gk20a_tegra_busy,
458 .idle = gk20a_tegra_idle, 500 .idle = gk20a_tegra_idle,
459 501
502 .reset_assert = gk20a_tegra_reset_assert,
503 .reset_deassert = gk20a_tegra_reset_deassert,
504
460 /* frequency scaling configuration */ 505 /* frequency scaling configuration */
461 .prescale = gk20a_tegra_prescale, 506 .prescale = gk20a_tegra_prescale,
462 .postscale = gk20a_tegra_postscale, 507 .postscale = gk20a_tegra_postscale,
@@ -495,6 +540,9 @@ struct gk20a_platform gk20a_tegra_platform = {
495 .busy = gk20a_tegra_busy, 540 .busy = gk20a_tegra_busy,
496 .idle = gk20a_tegra_idle, 541 .idle = gk20a_tegra_idle,
497 542
543 .reset_assert = gk20a_tegra_reset_assert,
544 .reset_deassert = gk20a_tegra_reset_deassert,
545
498 /* frequency scaling configuration */ 546 /* frequency scaling configuration */
499 .prescale = gk20a_tegra_prescale, 547 .prescale = gk20a_tegra_prescale,
500 .postscale = gk20a_tegra_postscale, 548 .postscale = gk20a_tegra_postscale,
@@ -534,6 +582,9 @@ struct gk20a_platform gm20b_tegra_platform = {
534 .busy = gk20a_tegra_busy, 582 .busy = gk20a_tegra_busy,
535 .idle = gk20a_tegra_idle, 583 .idle = gk20a_tegra_idle,
536 584
585 .reset_assert = gm20b_tegra_reset_assert,
586 .reset_deassert = gk20a_tegra_reset_deassert,
587
537 /* frequency scaling configuration */ 588 /* frequency scaling configuration */
538 .prescale = gk20a_tegra_prescale, 589 .prescale = gk20a_tegra_prescale,
539 .postscale = gk20a_tegra_postscale, 590 .postscale = gk20a_tegra_postscale,