summaryrefslogtreecommitdiff
path: root/src/protocols/DRMSyncobj.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/protocols/DRMSyncobj.cpp')
-rw-r--r--src/protocols/DRMSyncobj.cpp103
1 files changed, 23 insertions, 80 deletions
diff --git a/src/protocols/DRMSyncobj.cpp b/src/protocols/DRMSyncobj.cpp
index 0a4ca439..c2960746 100644
--- a/src/protocols/DRMSyncobj.cpp
+++ b/src/protocols/DRMSyncobj.cpp
@@ -75,100 +75,43 @@ CDRMSyncobjSurfaceResource::CDRMSyncobjSurfaceResource(UP<CWpLinuxDrmSyncobjSurf
});
listeners.surfacePrecommit = surface->events.precommit.registerListener([this](std::any d) {
- const bool PENDING_HAS_NEW_BUFFER = surface->pending.updated & SSurfaceState::eUpdatedProperties::SURFACE_UPDATED_BUFFER;
-
- if (!surface->pending.buffer && PENDING_HAS_NEW_BUFFER && !surface->pending.texture) {
- removeAllWaiters();
- surface->commitPendingState(surface->pending);
- return; // null buffer attached.
+ if (!surface->pending.updated.buffer || !surface->pending.buffer) {
+ if (pendingAcquire.timeline() || pendingRelease.timeline()) {
+ resource->error(WP_LINUX_DRM_SYNCOBJ_SURFACE_V1_ERROR_NO_BUFFER, "Missing buffer");
+ surface->pending.rejected = true;
+ }
+ return;
}
- if (!surface->pending.buffer && !PENDING_HAS_NEW_BUFFER && surface->current.buffer) {
- surface->current.bufferDamage.clear();
- surface->current.damage.clear();
- surface->commitPendingState(surface->current);
- return; // no new buffer, but we still have current around and a commit happend, commit current again.
+ if (!pendingAcquire.timeline()) {
+ resource->error(WP_LINUX_DRM_SYNCOBJ_SURFACE_V1_ERROR_NO_ACQUIRE_POINT, "Missing acquire timeline");
+ surface->pending.rejected = true;
+ return;
}
- if (!surface->pending.buffer && !PENDING_HAS_NEW_BUFFER && !surface->current.buffer) {
- surface->commitPendingState(surface->pending); // no pending buffer, no current buffer. probably first commit
+ if (!pendingRelease.timeline()) {
+ resource->error(WP_LINUX_DRM_SYNCOBJ_SURFACE_V1_ERROR_NO_RELEASE_POINT, "Missing release timeline");
+ surface->pending.rejected = true;
return;
}
- if (pendingAcquire.timeline()) {
- surface->pending.buffer->acquire = makeUnique<CDRMSyncPointState>(std::move(pendingAcquire));
- pendingAcquire = {};
+ if (pendingAcquire.timeline() == pendingRelease.timeline() && pendingAcquire.point() >= pendingRelease.point()) {
+ resource->error(WP_LINUX_DRM_SYNCOBJ_SURFACE_V1_ERROR_CONFLICTING_POINTS, "Acquire and release points are on the same timeline, and acquire >= release");
+ surface->pending.rejected = true;
+ return;
}
- if (pendingRelease.timeline()) {
- surface->pending.buffer->release = makeUnique<CDRMSyncPointState>(std::move(pendingRelease));
- pendingRelease = {};
- }
+ surface->pending.updated.acquire = true;
+ surface->pending.acquire = pendingAcquire;
+ pendingAcquire = {};
- if (protocolError())
- return;
+ surface->pending.buffer.release = pendingRelease;
+ pendingRelease = {};
- const auto& state = pendingStates.emplace_back(makeShared<SSurfaceState>(surface->pending));
- surface->pending.damage.clear();
- surface->pending.bufferDamage.clear();
- surface->pending.updated &= ~SSurfaceState::eUpdatedProperties::SURFACE_UPDATED_BUFFER;
- surface->pending.updated &= ~SSurfaceState::eUpdatedProperties::SURFACE_UPDATED_DAMAGE;
- surface->pending.buffer.reset();
-
- state->buffer->buffer->syncReleaser = state->buffer->release->createSyncRelease();
- state->buffer->acquire->addWaiter([this, surf = surface, wp = CWeakPointer<SSurfaceState>(*std::prev(pendingStates.end()))] {
- if (!surf)
- return;
-
- surf->commitPendingState(*wp.lock());
- std::erase(pendingStates, wp);
- });
+ surface->pending.buffer->syncReleaser = surface->pending.buffer.release.createSyncRelease();
});
}
-void CDRMSyncobjSurfaceResource::removeAllWaiters() {
- for (auto& s : pendingStates) {
- if (s && s->buffer && s->buffer->acquire)
- s->buffer->acquire->timeline()->removeAllWaiters();
- }
-
- pendingStates.clear();
-}
-
-CDRMSyncobjSurfaceResource::~CDRMSyncobjSurfaceResource() {
- removeAllWaiters();
-}
-
-bool CDRMSyncobjSurfaceResource::protocolError() {
- if (!surface->pending.buffer) {
- resource->error(WP_LINUX_DRM_SYNCOBJ_SURFACE_V1_ERROR_NO_BUFFER, "Missing buffer");
- surface->pending.rejected = true;
- return true;
- }
-
- if (!surface->pending.buffer->acquire || !surface->pending.buffer->acquire->timeline()) {
- resource->error(WP_LINUX_DRM_SYNCOBJ_SURFACE_V1_ERROR_NO_ACQUIRE_POINT, "Missing acquire timeline");
- surface->pending.rejected = true;
- return true;
- }
-
- if (!surface->pending.buffer->release || !surface->pending.buffer->release->timeline()) {
- resource->error(WP_LINUX_DRM_SYNCOBJ_SURFACE_V1_ERROR_NO_RELEASE_POINT, "Missing release timeline");
- surface->pending.rejected = true;
- return true;
- }
-
- if (surface->pending.buffer->acquire->timeline() == surface->pending.buffer->release->timeline()) {
- if (surface->pending.buffer->acquire->point() >= surface->pending.buffer->release->point()) {
- resource->error(WP_LINUX_DRM_SYNCOBJ_SURFACE_V1_ERROR_CONFLICTING_POINTS, "Acquire and release points are on the same timeline, and acquire >= release");
- surface->pending.rejected = true;
- return true;
- }
- }
-
- return false;
-}
-
bool CDRMSyncobjSurfaceResource::good() {
return resource->resource();
}