diff --git a/include/aquamarine/allocator/GBM.hpp b/include/aquamarine/allocator/GBM.hpp index f4d18ee..5033187 100644 --- a/include/aquamarine/allocator/GBM.hpp +++ b/include/aquamarine/allocator/GBM.hpp @@ -14,12 +14,14 @@ namespace Aquamarine { public: virtual ~CGBMBuffer(); - virtual eBufferCapability caps(); - virtual eBufferType type(); - virtual void update(const Hyprutils::Math::CRegion& damage); - virtual bool isSynchronous(); - virtual bool good(); - virtual SDMABUFAttrs dmabuf(); + virtual eBufferCapability caps(); + virtual eBufferType type(); + virtual void update(const Hyprutils::Math::CRegion& damage); + virtual bool isSynchronous(); + virtual bool good(); + virtual SDMABUFAttrs dmabuf(); + virtual std::tuple beginDataPtr(uint32_t flags); + virtual void endDataPtr(); private: CGBMBuffer(const SAllocatorBufferParams& params, Hyprutils::Memory::CWeakPointer allocator_, Hyprutils::Memory::CSharedPointer swapchain); @@ -27,7 +29,9 @@ namespace Aquamarine { Hyprutils::Memory::CWeakPointer allocator; // gbm stuff - gbm_bo* bo = nullptr; + gbm_bo* bo = nullptr; + void* boBuffer = nullptr; + void* gboMapping = nullptr; SDMABUFAttrs attrs{.success = false}; friend class CGBMAllocator; diff --git a/src/allocator/GBM.cpp b/src/allocator/GBM.cpp index 49f75e4..a78a243 100644 --- a/src/allocator/GBM.cpp +++ b/src/allocator/GBM.cpp @@ -53,7 +53,8 @@ static SDRMFormat guessFormatFrom(std::vector formats, bool cursor) } Aquamarine::CGBMBuffer::CGBMBuffer(const SAllocatorBufferParams& params, Hyprutils::Memory::CWeakPointer allocator_, - Hyprutils::Memory::CSharedPointer swapchain) : allocator(allocator_) { + Hyprutils::Memory::CSharedPointer swapchain) : + allocator(allocator_) { if (!allocator) return; @@ -158,8 +159,11 @@ Aquamarine::CGBMBuffer::CGBMBuffer(const SAllocatorBufferParams& params, Hypruti Aquamarine::CGBMBuffer::~CGBMBuffer() { events.destroy.emit(); - if (bo) + if (bo) { + if (gboMapping) + gbm_bo_unmap(bo, gboMapping); // FIXME: is it needed before destroy? gbm_bo_destroy(bo); + } for (size_t i = 0; i < (size_t)attrs.planes; i++) close(attrs.fds.at(i)); } @@ -188,6 +192,24 @@ SDMABUFAttrs Aquamarine::CGBMBuffer::dmabuf() { return attrs; } +std::tuple Aquamarine::CGBMBuffer::beginDataPtr(uint32_t flags) { + uint32_t dst_stride = 0; + if (boBuffer) + allocator->backend->log(AQ_LOG_ERROR, "beginDataPtr is called a second time without calling endDataPtr first. Returning old mapping"); + else + boBuffer = gbm_bo_map(bo, 0, 0, attrs.size.x, attrs.size.y, flags, &dst_stride, &gboMapping); + // FIXME: assumes a 32-bit pixel format + return {(uint8_t*)boBuffer, attrs.format, attrs.size.x * attrs.size.y * 4}; +} + +void Aquamarine::CGBMBuffer::endDataPtr() { + if (gboMapping) { + gbm_bo_unmap(bo, gboMapping); + gboMapping = nullptr; + boBuffer = nullptr; + } +} + CGBMAllocator::~CGBMAllocator() { if (gbmDevice) gbm_device_destroy(gbmDevice);