Commit ea13e5ab authored by Ben Skeggs's avatar Ben Skeggs

drm/nouveau: signal pending fences when channel has been killed

Signed-off-by: default avatarBen Skeggs <bskeggs@redhat.com>
parent 0181f4bf
...@@ -55,6 +55,8 @@ nouveau_channel_killed(struct nvif_notify *ntfy) ...@@ -55,6 +55,8 @@ nouveau_channel_killed(struct nvif_notify *ntfy)
struct nouveau_cli *cli = (void *)chan->user.client; struct nouveau_cli *cli = (void *)chan->user.client;
NV_PRINTK(warn, cli, "channel %d killed!\n", chan->chid); NV_PRINTK(warn, cli, "channel %d killed!\n", chan->chid);
atomic_set(&chan->killed, 1); atomic_set(&chan->killed, 1);
if (chan->fence)
nouveau_fence_context_kill(chan->fence, -ENODEV);
return NVIF_NOTIFY_DROP; return NVIF_NOTIFY_DROP;
} }
......
...@@ -87,7 +87,7 @@ nouveau_local_fence(struct dma_fence *fence, struct nouveau_drm *drm) ...@@ -87,7 +87,7 @@ nouveau_local_fence(struct dma_fence *fence, struct nouveau_drm *drm)
} }
void void
nouveau_fence_context_del(struct nouveau_fence_chan *fctx) nouveau_fence_context_kill(struct nouveau_fence_chan *fctx, int error)
{ {
struct nouveau_fence *fence; struct nouveau_fence *fence;
...@@ -95,11 +95,19 @@ nouveau_fence_context_del(struct nouveau_fence_chan *fctx) ...@@ -95,11 +95,19 @@ nouveau_fence_context_del(struct nouveau_fence_chan *fctx)
while (!list_empty(&fctx->pending)) { while (!list_empty(&fctx->pending)) {
fence = list_entry(fctx->pending.next, typeof(*fence), head); fence = list_entry(fctx->pending.next, typeof(*fence), head);
if (error)
dma_fence_set_error(&fence->base, error);
if (nouveau_fence_signal(fence)) if (nouveau_fence_signal(fence))
nvif_notify_put(&fctx->notify); nvif_notify_put(&fctx->notify);
} }
spin_unlock_irq(&fctx->lock); spin_unlock_irq(&fctx->lock);
}
void
nouveau_fence_context_del(struct nouveau_fence_chan *fctx)
{
nouveau_fence_context_kill(fctx, 0);
nvif_notify_fini(&fctx->notify); nvif_notify_fini(&fctx->notify);
fctx->dead = 1; fctx->dead = 1;
......
...@@ -63,6 +63,7 @@ struct nouveau_fence_priv { ...@@ -63,6 +63,7 @@ struct nouveau_fence_priv {
void nouveau_fence_context_new(struct nouveau_channel *, struct nouveau_fence_chan *); void nouveau_fence_context_new(struct nouveau_channel *, struct nouveau_fence_chan *);
void nouveau_fence_context_del(struct nouveau_fence_chan *); void nouveau_fence_context_del(struct nouveau_fence_chan *);
void nouveau_fence_context_free(struct nouveau_fence_chan *); void nouveau_fence_context_free(struct nouveau_fence_chan *);
void nouveau_fence_context_kill(struct nouveau_fence_chan *, int error);
int nv04_fence_create(struct nouveau_drm *); int nv04_fence_create(struct nouveau_drm *);
int nv04_fence_mthd(struct nouveau_channel *, u32, u32, u32); int nv04_fence_mthd(struct nouveau_channel *, u32, u32, u32);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment