summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDebarshi Dutta <ddutta@nvidia.com>2019-09-03 04:35:20 -0400
committermobile promotions <svcmobile_promotions@nvidia.com>2019-09-04 15:03:30 -0400
commit066383830893c0fc43ec28f833185eab91e9dfc9 (patch)
tree13ea22555de69d576ff8b7f81122f58bc9d08365
parent1d532589b0a8815b4c4f33b8527fae4b3a5b4bbe (diff)
gpu: nvgpu: correct handling of pbdma rc
The current code reads the pbdma_status info after clearing the interrupt. Other interrupts/sleep can cause enough delay between clearing the interrupt and pbdma switching the channel leading to invalid channel/tsg ID. Correct that by reading the pbdma_status info register before clearing of the pbdma interrupt to correctly read the context information before the pbdma can switch out the context. Bug 200533450 Change-Id: Ic2f0682526e00d14ad58f0411472f34388183f2b Signed-off-by: Debarshi Dutta <ddutta@nvidia.com> Reviewed-on: https://git-master.nvidia.com/r/2165047 (cherry-picked from 0ef96e4b1a7979d2bae0e52924e976515cb87400 in dev-main) Reviewed-on: https://git-master.nvidia.com/r/2188861 Reviewed-by: Automatic_Commit_Validation_User GVS: Gerrit_Virtual_Submit Reviewed-by: Bibek Basu <bbasu@nvidia.com> Reviewed-by: mobile promotions <svcmobile_promotions@nvidia.com> Tested-by: mobile promotions <svcmobile_promotions@nvidia.com>
-rw-r--r--drivers/gpu/nvgpu/gk20a/fifo_gk20a.c14
1 files changed, 10 insertions, 4 deletions
diff --git a/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c b/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c
index 5aca7d62..1b18a8f9 100644
--- a/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c
+++ b/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c
@@ -2769,14 +2769,12 @@ unsigned int gk20a_fifo_handle_pbdma_intr_1(struct gk20a *g,
2769 2769
2770static void gk20a_fifo_pbdma_fault_rc(struct gk20a *g, 2770static void gk20a_fifo_pbdma_fault_rc(struct gk20a *g,
2771 struct fifo_gk20a *f, u32 pbdma_id, 2771 struct fifo_gk20a *f, u32 pbdma_id,
2772 u32 error_notifier) 2772 u32 error_notifier, u32 status)
2773{ 2773{
2774 u32 status;
2775 u32 id; 2774 u32 id;
2776 2775
2777 nvgpu_log(g, gpu_dbg_info, "pbdma id %d error notifier %d", 2776 nvgpu_log(g, gpu_dbg_info, "pbdma id %d error notifier %d",
2778 pbdma_id, error_notifier); 2777 pbdma_id, error_notifier);
2779 status = gk20a_readl(g, fifo_pbdma_status_r(pbdma_id));
2780 /* Remove channel from runlist */ 2778 /* Remove channel from runlist */
2781 id = fifo_pbdma_status_id_v(status); 2779 id = fifo_pbdma_status_id_v(status);
2782 if (fifo_pbdma_status_id_type_v(status) 2780 if (fifo_pbdma_status_id_type_v(status)
@@ -2816,6 +2814,7 @@ u32 gk20a_fifo_handle_pbdma_intr(struct gk20a *g, struct fifo_gk20a *f,
2816 u32 handled = 0; 2814 u32 handled = 0;
2817 u32 error_notifier = NVGPU_ERR_NOTIFIER_PBDMA_ERROR; 2815 u32 error_notifier = NVGPU_ERR_NOTIFIER_PBDMA_ERROR;
2818 unsigned int rc_type = RC_TYPE_NO_RC; 2816 unsigned int rc_type = RC_TYPE_NO_RC;
2817 u32 pbdma_status_info = 0;
2819 2818
2820 if (pbdma_intr_0) { 2819 if (pbdma_intr_0) {
2821 nvgpu_log(g, gpu_dbg_info | gpu_dbg_intr, 2820 nvgpu_log(g, gpu_dbg_info | gpu_dbg_intr,
@@ -2825,6 +2824,9 @@ u32 gk20a_fifo_handle_pbdma_intr(struct gk20a *g, struct fifo_gk20a *f,
2825 if (g->ops.fifo.handle_pbdma_intr_0(g, pbdma_id, pbdma_intr_0, 2824 if (g->ops.fifo.handle_pbdma_intr_0(g, pbdma_id, pbdma_intr_0,
2826 &handled, &error_notifier) != RC_TYPE_NO_RC) { 2825 &handled, &error_notifier) != RC_TYPE_NO_RC) {
2827 rc_type = RC_TYPE_PBDMA_FAULT; 2826 rc_type = RC_TYPE_PBDMA_FAULT;
2827
2828 pbdma_status_info = gk20a_readl(g,
2829 fifo_pbdma_status_r(pbdma_id));
2828 } 2830 }
2829 gk20a_writel(g, pbdma_intr_0_r(pbdma_id), pbdma_intr_0); 2831 gk20a_writel(g, pbdma_intr_0_r(pbdma_id), pbdma_intr_0);
2830 } 2832 }
@@ -2837,12 +2839,16 @@ u32 gk20a_fifo_handle_pbdma_intr(struct gk20a *g, struct fifo_gk20a *f,
2837 if (g->ops.fifo.handle_pbdma_intr_1(g, pbdma_id, pbdma_intr_1, 2839 if (g->ops.fifo.handle_pbdma_intr_1(g, pbdma_id, pbdma_intr_1,
2838 &handled, &error_notifier) != RC_TYPE_NO_RC) { 2840 &handled, &error_notifier) != RC_TYPE_NO_RC) {
2839 rc_type = RC_TYPE_PBDMA_FAULT; 2841 rc_type = RC_TYPE_PBDMA_FAULT;
2842
2843 pbdma_status_info = gk20a_readl(g,
2844 fifo_pbdma_status_r(pbdma_id));
2840 } 2845 }
2841 gk20a_writel(g, pbdma_intr_1_r(pbdma_id), pbdma_intr_1); 2846 gk20a_writel(g, pbdma_intr_1_r(pbdma_id), pbdma_intr_1);
2842 } 2847 }
2843 2848
2844 if (rc == RC_YES && rc_type == RC_TYPE_PBDMA_FAULT) { 2849 if (rc == RC_YES && rc_type == RC_TYPE_PBDMA_FAULT) {
2845 gk20a_fifo_pbdma_fault_rc(g, f, pbdma_id, error_notifier); 2850 gk20a_fifo_pbdma_fault_rc(g, f, pbdma_id, error_notifier,
2851 pbdma_status_info);
2846 } 2852 }
2847 2853
2848 return handled; 2854 return handled;