Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

at v5.5-rc6 94 lines 2.0 kB view raw
1// SPDX-License-Identifier: MIT 2 3/* 4 * Copyright © 2019 Intel Corporation 5 */ 6 7#include "i915_sw_fence_work.h" 8 9static void fence_work(struct work_struct *work) 10{ 11 struct dma_fence_work *f = container_of(work, typeof(*f), work); 12 int err; 13 14 err = f->ops->work(f); 15 if (err) 16 dma_fence_set_error(&f->dma, err); 17 dma_fence_signal(&f->dma); 18 dma_fence_put(&f->dma); 19} 20 21static int __i915_sw_fence_call 22fence_notify(struct i915_sw_fence *fence, enum i915_sw_fence_notify state) 23{ 24 struct dma_fence_work *f = container_of(fence, typeof(*f), chain); 25 26 switch (state) { 27 case FENCE_COMPLETE: 28 if (fence->error) 29 dma_fence_set_error(&f->dma, fence->error); 30 31 if (!f->dma.error) { 32 dma_fence_get(&f->dma); 33 queue_work(system_unbound_wq, &f->work); 34 } else { 35 dma_fence_signal(&f->dma); 36 } 37 break; 38 39 case FENCE_FREE: 40 dma_fence_put(&f->dma); 41 break; 42 } 43 44 return NOTIFY_DONE; 45} 46 47static const char *get_driver_name(struct dma_fence *fence) 48{ 49 return "dma-fence"; 50} 51 52static const char *get_timeline_name(struct dma_fence *fence) 53{ 54 struct dma_fence_work *f = container_of(fence, typeof(*f), dma); 55 56 return f->ops->name ?: "work"; 57} 58 59static void fence_release(struct dma_fence *fence) 60{ 61 struct dma_fence_work *f = container_of(fence, typeof(*f), dma); 62 63 if (f->ops->release) 64 f->ops->release(f); 65 66 i915_sw_fence_fini(&f->chain); 67 68 BUILD_BUG_ON(offsetof(typeof(*f), dma)); 69 dma_fence_free(&f->dma); 70} 71 72static const struct dma_fence_ops fence_ops = { 73 .get_driver_name = get_driver_name, 74 .get_timeline_name = get_timeline_name, 75 .release = fence_release, 76}; 77 78void dma_fence_work_init(struct dma_fence_work *f, 79 const struct dma_fence_work_ops *ops) 80{ 81 f->ops = ops; 82 spin_lock_init(&f->lock); 83 dma_fence_init(&f->dma, &fence_ops, &f->lock, 0, 0); 84 i915_sw_fence_init(&f->chain, fence_notify); 85 INIT_WORK(&f->work, fence_work); 86} 87 88int dma_fence_work_chain(struct dma_fence_work *f, struct dma_fence *signal) 89{ 90 if (!signal) 91 return 0; 92 93 return __i915_sw_fence_await_dma_fence(&f->chain, signal, &f->cb); 94}