From cbf6394482aa5ac2b774a5d948f870ba1a87d1ef Mon Sep 17 00:00:00 2001 From: Seema Khowala Date: Wed, 17 Oct 2018 14:40:59 -0700 Subject: gpu: nvgpu: check ch_timedout for poll/restart poll_timeouts and timeout_restart_all_channels should only handle channels that have not been recovered/aborted. Check ch_timedout status of the channel to make sure channel is still alive to be used. A channel reference could still be available even if it is recovered but not closed. Bug 2404865 Change-Id: I016c8b9952ef1d4c349c2a2a2ca55cb81326d380 Signed-off-by: Seema Khowala Reviewed-on: https://git-master.nvidia.com/r/1929339 Signed-off-by: Debarshi Dutta (cherry picked from commit def687d4dfbc92dbc8a13781f8cee606eab4f3f3 in rel-32) Reviewed-on: https://git-master.nvidia.com/r/2016995 GVS: Gerrit_Virtual_Submit Reviewed-by: Alex Waterman Reviewed-by: Bibek Basu Reviewed-by: mobile promotions Tested-by: mobile promotions --- drivers/gpu/nvgpu/common/fifo/channel.c | 33 +++++++++++++++++++++++---------- 1 file changed, 23 insertions(+), 10 deletions(-) (limited to 'drivers/gpu/nvgpu/common/fifo/channel.c') diff --git a/drivers/gpu/nvgpu/common/fifo/channel.c b/drivers/gpu/nvgpu/common/fifo/channel.c index 2ada3911..0174e369 100644 --- a/drivers/gpu/nvgpu/common/fifo/channel.c +++ b/drivers/gpu/nvgpu/common/fifo/channel.c @@ -1387,6 +1387,11 @@ u32 nvgpu_get_gp_free_count(struct channel_gk20a *c) static void __gk20a_channel_timeout_start(struct channel_gk20a *ch) { + if (gk20a_channel_check_timedout(ch)) { + ch->timeout.running = false; + return; + } + ch->timeout.gp_get = ch->g->ops.fifo.userd_gp_get(ch->g, ch); ch->timeout.pb_get = ch->g->ops.fifo.userd_pb_get(ch->g, ch); ch->timeout.running = true; @@ -1484,16 +1489,16 @@ void gk20a_channel_timeout_restart_all_channels(struct gk20a *g) for (chid = 0; chid < f->num_channels; chid++) { struct channel_gk20a *ch = gk20a_channel_from_id(g, chid); - if (ch == NULL) - continue; - - nvgpu_raw_spinlock_acquire(&ch->timeout.lock); - if (ch->timeout.running) { - __gk20a_channel_timeout_start(ch); + if (ch != NULL) { + if (!gk20a_channel_check_timedout(ch)) { + nvgpu_raw_spinlock_acquire(&ch->timeout.lock); + if (ch->timeout.running) { + __gk20a_channel_timeout_start(ch); + } + nvgpu_raw_spinlock_release(&ch->timeout.lock); + } + gk20a_channel_put(ch); } - nvgpu_raw_spinlock_release(&ch->timeout.lock); - - gk20a_channel_put(ch); } } @@ -1517,6 +1522,12 @@ static void gk20a_channel_timeout_handler(struct channel_gk20a *ch) nvgpu_log_fn(g, " "); + if (gk20a_channel_check_timedout(ch)) { + /* channel is already recovered */ + gk20a_channel_timeout_stop(ch); + return; + } + /* Get status but keep timer running */ nvgpu_raw_spinlock_acquire(&ch->timeout.lock); gp_get = ch->timeout.gp_get; @@ -1587,7 +1598,9 @@ static void gk20a_channel_poll_timeouts(struct gk20a *g) struct channel_gk20a *ch = gk20a_channel_from_id(g, chid); if (ch != NULL) { - gk20a_channel_timeout_check(ch); + if (!gk20a_channel_check_timedout(ch)) { + gk20a_channel_timeout_check(ch); + } gk20a_channel_put(ch); } } -- cgit v1.2.2