summaryrefslogtreecommitdiffstats
path: root/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu/nvgpu/gk20a/fifo_gk20a.c')
-rw-r--r--drivers/gpu/nvgpu/gk20a/fifo_gk20a.c40
1 files changed, 19 insertions, 21 deletions
diff --git a/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c b/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c
index 617245b8..28efade5 100644
--- a/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c
+++ b/drivers/gpu/nvgpu/gk20a/fifo_gk20a.c
@@ -339,7 +339,6 @@ static int init_runlist(struct gk20a *g, struct fifo_gk20a *f)
339 runlist->mem[i].size = runlist_size; 339 runlist->mem[i].size = runlist_size;
340 } 340 }
341 mutex_init(&runlist->mutex); 341 mutex_init(&runlist->mutex);
342 init_waitqueue_head(&runlist->runlist_wq);
343 342
344 /* None of buffers is pinned if this value doesn't change. 343 /* None of buffers is pinned if this value doesn't change.
345 Otherwise, one of them (cur_buffer) must have been pinned. */ 344 Otherwise, one of them (cur_buffer) must have been pinned. */
@@ -632,19 +631,12 @@ clean_up:
632 631
633static void gk20a_fifo_handle_runlist_event(struct gk20a *g) 632static void gk20a_fifo_handle_runlist_event(struct gk20a *g)
634{ 633{
635 struct fifo_gk20a *f = &g->fifo; 634 u32 runlist_event = gk20a_readl(g, fifo_intr_runlist_r());
636 struct fifo_runlist_info_gk20a *runlist;
637 unsigned long runlist_event;
638 u32 runlist_id;
639
640 runlist_event = gk20a_readl(g, fifo_intr_runlist_r());
641 gk20a_writel(g, fifo_intr_runlist_r(), runlist_event);
642 635
643 for_each_set_bit(runlist_id, &runlist_event, f->max_runlists) { 636 gk20a_dbg(gpu_dbg_intr, "runlist event %08x\n",
644 runlist = &f->runlist_info[runlist_id]; 637 runlist_event);
645 wake_up(&runlist->runlist_wq);
646 }
647 638
639 gk20a_writel(g, fifo_intr_runlist_r(), runlist_event);
648} 640}
649 641
650static int gk20a_init_fifo_setup_hw(struct gk20a *g) 642static int gk20a_init_fifo_setup_hw(struct gk20a *g)
@@ -1853,19 +1845,25 @@ static void gk20a_fifo_runlist_reset_engines(struct gk20a *g, u32 runlist_id)
1853static int gk20a_fifo_runlist_wait_pending(struct gk20a *g, u32 runlist_id) 1845static int gk20a_fifo_runlist_wait_pending(struct gk20a *g, u32 runlist_id)
1854{ 1846{
1855 struct fifo_runlist_info_gk20a *runlist; 1847 struct fifo_runlist_info_gk20a *runlist;
1856 u32 remain; 1848 unsigned long end_jiffies = jiffies +
1857 bool pending; 1849 msecs_to_jiffies(gk20a_get_gr_idle_timeout(g));
1850 unsigned long delay = GR_IDLE_CHECK_DEFAULT;
1851 int ret = -ETIMEDOUT;
1858 1852
1859 runlist = &g->fifo.runlist_info[runlist_id]; 1853 runlist = &g->fifo.runlist_info[runlist_id];
1860 remain = wait_event_timeout(runlist->runlist_wq, 1854 do {
1861 ((pending = gk20a_readl(g, fifo_eng_runlist_r(runlist_id)) & 1855 if ((gk20a_readl(g, fifo_eng_runlist_r(runlist_id)) &
1862 fifo_eng_runlist_pending_true_f()) == 0), 1856 fifo_eng_runlist_pending_true_f()) == 0) {
1863 msecs_to_jiffies(gk20a_get_gr_idle_timeout(g))); 1857 ret = 0;
1858 break;
1859 }
1864 1860
1865 if (remain == 0 && pending != 0) 1861 usleep_range(delay, delay * 2);
1866 return -ETIMEDOUT; 1862 delay = min_t(u32, delay << 1, GR_IDLE_CHECK_MAX);
1863 } while (time_before(jiffies, end_jiffies) ||
1864 !tegra_platform_is_silicon());
1867 1865
1868 return 0; 1866 return ret;
1869} 1867}
1870 1868
1871static int gk20a_fifo_update_runlist_locked(struct gk20a *g, u32 runlist_id, 1869static int gk20a_fifo_update_runlist_locked(struct gk20a *g, u32 runlist_id,