sync.txt 3.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576
  1. Motivation:
  2. In complicated DMA pipelines such as graphics (multimedia, camera, gpu, display)
  3. a consumer of a buffer needs to know when the producer has finished producing
  4. it. Likewise the producer needs to know when the consumer is finished with the
  5. buffer so it can reuse it. A particular buffer may be consumed by multiple
  6. consumers which will retain the buffer for different amounts of time. In
  7. addition, a consumer may consume multiple buffers atomically.
  8. The sync framework adds an API which allows synchronization between the
  9. producers and consumers in a generic way while also allowing platforms which
  10. have shared hardware synchronization primitives to exploit them.
  11. Goals:
  12. * provide a generic API for expressing synchronization dependencies
  13. * allow drivers to exploit hardware synchronization between hardware
  14. blocks
  15. * provide a userspace API that allows a compositor to manage
  16. dependencies.
  17. * provide rich telemetry data to allow debugging slowdowns and stalls of
  18. the graphics pipeline.
  19. Objects:
  20. * sync_timeline
  21. * sync_pt
  22. * sync_fence
  23. sync_timeline:
  24. A sync_timeline is an abstract monotonically increasing counter. In general,
  25. each driver/hardware block context will have one of these. They can be backed
  26. by the appropriate hardware or rely on the generic sw_sync implementation.
  27. Timelines are only ever created through their specific implementations
  28. (i.e. sw_sync.)
  29. sync_pt:
  30. A sync_pt is an abstract value which marks a point on a sync_timeline. Sync_pts
  31. have a single timeline parent. They have 3 states: active, signaled, and error.
  32. They start in active state and transition, once, to either signaled (when the
  33. timeline counter advances beyond the sync_pt’s value) or error state.
  34. sync_fence:
  35. Sync_fences are the primary primitives used by drivers to coordinate
  36. synchronization of their buffers. They are a collection of sync_pts which may
  37. or may not have the same timeline parent. A sync_pt can only exist in one fence
  38. and the fence's list of sync_pts is immutable once created. Fences can be
  39. waited on synchronously or asynchronously. Two fences can also be merged to
  40. create a third fence containing a copy of the two fences’ sync_pts. Fences are
  41. backed by file descriptors to allow userspace to coordinate the display pipeline
  42. dependencies.
  43. Use:
  44. A driver implementing sync support should have a work submission function which:
  45. * takes a fence argument specifying when to begin work
  46. * asynchronously queues that work to kick off when the fence is signaled
  47. * returns a fence to indicate when its work will be done.
  48. * signals the returned fence once the work is completed.
  49. Consider an imaginary display driver that has the following API:
  50. /*
  51. * assumes buf is ready to be displayed.
  52. * blocks until the buffer is on screen.
  53. */
  54. void display_buffer(struct dma_buf *buf);
  55. The new API will become:
  56. /*
  57. * will display buf when fence is signaled.
  58. * returns immediately with a fence that will signal when buf
  59. * is no longer displayed.
  60. */
  61. struct sync_fence* display_buffer(struct dma_buf *buf,
  62. struct sync_fence *fence);