Handle suballocated AHB buffers

VkBuffers backed by AHBs do not require dedicated allocations. As such, update SupportsAllocateInfo() to report supported as long as a VkImportAndroidHardwareBufferInfoANDROID or a VkExportMemoryAllocateInfo with AHB bit was found. Updates allocateAndroidHardwareBuffer() to treat the lack of a dedicated buffer or image as a request to allocate a blob AHB. Bug: b/147316305 Bug: b/169796031 Test: cts -m CtsNativeHardwareTestCases Test: cts -m CtsDeqpTestCases -t dEQP-VK.api.external.memory.android_hardware_buffer.* Change-Id: Ica2782b4570bd4d4c1e5585b696b40314a267b2f Reviewed-on: https://swiftshader-review.googlesource.com/c/SwiftShader/+/51248 Presubmit-Ready: Jason Macnak <natsu@google.com> Kokoro-Result: kokoro <noreply+kokoro@google.com> Tested-by: 's avatarJason Macnak <natsu@google.com> Commit-Queue: Jason Macnak <natsu@google.com> Reviewed-by: 's avatarNicolas Capens <nicolascapens@google.com>
parent 236d75a2
...@@ -194,16 +194,16 @@ AHardwareBufferExternalMemory::AllocateInfo::AllocateInfo(const VkMemoryAllocate ...@@ -194,16 +194,16 @@ AHardwareBufferExternalMemory::AllocateInfo::AllocateInfo(const VkMemoryAllocate
break; break;
case VK_STRUCTURE_TYPE_MEMORY_DEDICATED_ALLOCATE_INFO: case VK_STRUCTURE_TYPE_MEMORY_DEDICATED_ALLOCATE_INFO:
{ {
// AHB requires dedicated allocation -- for images, the gralloc gets to decide the image layout,
// not us.
const auto *dedicatedAllocateInfo = reinterpret_cast<const VkMemoryDedicatedAllocateInfo *>(createInfo); const auto *dedicatedAllocateInfo = reinterpret_cast<const VkMemoryDedicatedAllocateInfo *>(createInfo);
imageHandle = vk::Cast(dedicatedAllocateInfo->image); dedicatedImageHandle = vk::Cast(dedicatedAllocateInfo->image);
bufferHandle = vk::Cast(dedicatedAllocateInfo->buffer); dedicatedBufferHandle = vk::Cast(dedicatedAllocateInfo->buffer);
} }
break; break;
default: default:
WARN("VkMemoryAllocateInfo->pNext sType = %s", vk::Stringify(createInfo->sType).c_str()); {
LOG_TRAP("VkMemoryAllocateInfo->pNext sType = %s", vk::Stringify(createInfo->sType).c_str());
}
break;
} }
createInfo = createInfo->pNext; createInfo = createInfo->pNext;
} }
...@@ -221,7 +221,7 @@ AHardwareBufferExternalMemory::~AHardwareBufferExternalMemory() ...@@ -221,7 +221,7 @@ AHardwareBufferExternalMemory::~AHardwareBufferExternalMemory()
} }
// VkAllocateMemory // VkAllocateMemory
VkResult AHardwareBufferExternalMemory::allocate(size_t /*size*/, void **pBuffer) VkResult AHardwareBufferExternalMemory::allocate(size_t size, void **pBuffer)
{ {
if(allocateInfo.importAhb) if(allocateInfo.importAhb)
{ {
...@@ -230,7 +230,7 @@ VkResult AHardwareBufferExternalMemory::allocate(size_t /*size*/, void **pBuffer ...@@ -230,7 +230,7 @@ VkResult AHardwareBufferExternalMemory::allocate(size_t /*size*/, void **pBuffer
else else
{ {
ASSERT(allocateInfo.exportAhb); ASSERT(allocateInfo.exportAhb);
return allocateAndroidHardwareBuffer(pBuffer); return allocateAndroidHardwareBuffer(size, pBuffer);
} }
} }
...@@ -255,12 +255,11 @@ VkResult AHardwareBufferExternalMemory::importAndroidHardwareBuffer(AHardwareBuf ...@@ -255,12 +255,11 @@ VkResult AHardwareBufferExternalMemory::importAndroidHardwareBuffer(AHardwareBuf
return lockAndroidHardwareBuffer(pBuffer); return lockAndroidHardwareBuffer(pBuffer);
} }
VkResult AHardwareBufferExternalMemory::allocateAndroidHardwareBuffer(void **pBuffer) VkResult AHardwareBufferExternalMemory::allocateAndroidHardwareBuffer(size_t size, void **pBuffer)
{ {
if(allocateInfo.imageHandle) if(allocateInfo.dedicatedImageHandle)
{ {
vk::Image *image = allocateInfo.imageHandle; vk::Image *image = allocateInfo.dedicatedImageHandle;
ASSERT(image != nullptr);
ASSERT(image->getArrayLayers() == 1); ASSERT(image->getArrayLayers() == 1);
VkExtent3D extent = image->getExtent(); VkExtent3D extent = image->getExtent();
...@@ -271,10 +270,9 @@ VkResult AHardwareBufferExternalMemory::allocateAndroidHardwareBuffer(void **pBu ...@@ -271,10 +270,9 @@ VkResult AHardwareBufferExternalMemory::allocateAndroidHardwareBuffer(void **pBu
ahbDesc.format = GetAHBFormatFromVkFormat(image->getFormat()); ahbDesc.format = GetAHBFormatFromVkFormat(image->getFormat());
ahbDesc.usage = GetAHBUsageFromVkImageFlags(image->getFlags(), image->getUsage()); ahbDesc.usage = GetAHBUsageFromVkImageFlags(image->getFlags(), image->getUsage());
} }
else else if(allocateInfo.dedicatedBufferHandle)
{ {
vk::Buffer *buffer = allocateInfo.bufferHandle; vk::Buffer *buffer = allocateInfo.dedicatedBufferHandle;
ASSERT(buffer != nullptr);
ahbDesc.width = static_cast<uint32_t>(buffer->getSize()); ahbDesc.width = static_cast<uint32_t>(buffer->getSize());
ahbDesc.height = 1; ahbDesc.height = 1;
...@@ -282,6 +280,18 @@ VkResult AHardwareBufferExternalMemory::allocateAndroidHardwareBuffer(void **pBu ...@@ -282,6 +280,18 @@ VkResult AHardwareBufferExternalMemory::allocateAndroidHardwareBuffer(void **pBu
ahbDesc.format = AHARDWAREBUFFER_FORMAT_BLOB; ahbDesc.format = AHARDWAREBUFFER_FORMAT_BLOB;
ahbDesc.usage = GetAHBUsageFromVkBufferFlags(buffer->getFlags(), buffer->getUsage()); ahbDesc.usage = GetAHBUsageFromVkBufferFlags(buffer->getFlags(), buffer->getUsage());
} }
else
{
// Android Hardware Buffer Buffer Resources: "Android hardware buffers with a format of
// AHARDWAREBUFFER_FORMAT_BLOB and usage that includes AHARDWAREBUFFER_USAGE_GPU_DATA_BUFFER can
// be used as the backing store for VkBuffer objects. Such Android hardware buffers have a size
// in bytes specified by their width; height and layers are both 1."
ahbDesc.width = static_cast<uint32_t>(size);
ahbDesc.height = 1;
ahbDesc.layers = 1;
ahbDesc.format = AHARDWAREBUFFER_FORMAT_BLOB;
ahbDesc.usage = AHARDWAREBUFFER_USAGE_GPU_DATA_BUFFER | AHARDWAREBUFFER_USAGE_CPU_READ_OFTEN | AHARDWAREBUFFER_USAGE_CPU_WRITE_OFTEN;
}
int ret = AHardwareBuffer_allocate(&ahbDesc, &ahb); int ret = AHardwareBuffer_allocate(&ahbDesc, &ahb);
if(ret != 0) if(ret != 0)
...@@ -297,13 +307,17 @@ VkResult AHardwareBufferExternalMemory::allocateAndroidHardwareBuffer(void **pBu ...@@ -297,13 +307,17 @@ VkResult AHardwareBufferExternalMemory::allocateAndroidHardwareBuffer(void **pBu
VkResult AHardwareBufferExternalMemory::lockAndroidHardwareBuffer(void **pBuffer) VkResult AHardwareBufferExternalMemory::lockAndroidHardwareBuffer(void **pBuffer)
{ {
uint64_t usage = 0; uint64_t usage = 0;
if(allocateInfo.imageHandle) if(allocateInfo.dedicatedImageHandle)
{ {
usage = GetAHBLockUsageFromVkImageUsageFlags(allocateInfo.imageHandle->getUsage()); usage = GetAHBLockUsageFromVkImageUsageFlags(allocateInfo.dedicatedImageHandle->getUsage());
}
else if(allocateInfo.dedicatedBufferHandle)
{
usage = GetAHBLockUsageFromVkBufferUsageFlags(allocateInfo.dedicatedBufferHandle->getUsage());
} }
else else
{ {
usage = GetAHBLockUsageFromVkBufferUsageFlags(allocateInfo.bufferHandle->getUsage()); usage = AHARDWAREBUFFER_USAGE_CPU_READ_OFTEN | AHARDWAREBUFFER_USAGE_CPU_WRITE_OFTEN;
} }
// Empty fence, lock immedietly. // Empty fence, lock immedietly.
...@@ -465,6 +479,8 @@ VkResult AHardwareBufferExternalMemory::GetAndroidHardwareBufferProperties(VkDev ...@@ -465,6 +479,8 @@ VkResult AHardwareBufferExternalMemory::GetAndroidHardwareBufferProperties(VkDev
int AHardwareBufferExternalMemory::externalImageRowPitchBytes(VkImageAspectFlagBits aspect) const int AHardwareBufferExternalMemory::externalImageRowPitchBytes(VkImageAspectFlagBits aspect) const
{ {
ASSERT(allocateInfo.dedicatedImageHandle != nullptr);
switch(ahbDesc.format) switch(ahbDesc.format)
{ {
case AHARDWAREBUFFER_FORMAT_Y8Cb8Cr8_420: case AHARDWAREBUFFER_FORMAT_Y8Cb8Cr8_420:
...@@ -490,6 +506,8 @@ int AHardwareBufferExternalMemory::externalImageRowPitchBytes(VkImageAspectFlagB ...@@ -490,6 +506,8 @@ int AHardwareBufferExternalMemory::externalImageRowPitchBytes(VkImageAspectFlagB
VkDeviceSize AHardwareBufferExternalMemory::externalImageMemoryOffset(VkImageAspectFlagBits aspect) const VkDeviceSize AHardwareBufferExternalMemory::externalImageMemoryOffset(VkImageAspectFlagBits aspect) const
{ {
ASSERT(allocateInfo.dedicatedImageHandle != nullptr);
switch(ahbDesc.format) switch(ahbDesc.format)
{ {
case AHARDWAREBUFFER_FORMAT_Y8Cb8Cr8_420: case AHARDWAREBUFFER_FORMAT_Y8Cb8Cr8_420:
......
...@@ -34,8 +34,8 @@ public: ...@@ -34,8 +34,8 @@ public:
bool importAhb = false; bool importAhb = false;
bool exportAhb = false; bool exportAhb = false;
AHardwareBuffer *ahb = nullptr; AHardwareBuffer *ahb = nullptr;
vk::Image *imageHandle = nullptr; vk::Image *dedicatedImageHandle = nullptr;
vk::Buffer *bufferHandle = nullptr; vk::Buffer *dedicatedBufferHandle = nullptr;
AllocateInfo() = default; AllocateInfo() = default;
...@@ -48,7 +48,7 @@ public: ...@@ -48,7 +48,7 @@ public:
static bool SupportsAllocateInfo(const VkMemoryAllocateInfo *pAllocateInfo) static bool SupportsAllocateInfo(const VkMemoryAllocateInfo *pAllocateInfo)
{ {
AllocateInfo info(pAllocateInfo); AllocateInfo info(pAllocateInfo);
return (info.importAhb || info.exportAhb) && (info.bufferHandle || info.imageHandle); return info.importAhb || info.exportAhb;
} }
explicit AHardwareBufferExternalMemory(const VkMemoryAllocateInfo *pAllocateInfo); explicit AHardwareBufferExternalMemory(const VkMemoryAllocateInfo *pAllocateInfo);
...@@ -81,7 +81,7 @@ public: ...@@ -81,7 +81,7 @@ public:
private: private:
VkResult importAndroidHardwareBuffer(AHardwareBuffer *buffer, void **pBuffer); VkResult importAndroidHardwareBuffer(AHardwareBuffer *buffer, void **pBuffer);
VkResult allocateAndroidHardwareBuffer(void **pBuffer); VkResult allocateAndroidHardwareBuffer(size_t size, void **pBuffer);
VkResult lockAndroidHardwareBuffer(void **pBuffer); VkResult lockAndroidHardwareBuffer(void **pBuffer);
VkResult unlockAndroidHardwareBuffer(); VkResult unlockAndroidHardwareBuffer();
......
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