| 399 | } |
| 400 | |
| 401 | std::shared_ptr<decoder::mapped_hardware_buffer> decoder::map_hardware_buffer(AImage * image) |
| 402 | { |
| 403 | AHardwareBuffer * hardware_buffer; |
| 404 | check(AImage_getHardwareBuffer(image, &hardware_buffer), "AImage_getHardwareBuffer"); |
| 405 | |
| 406 | std::unique_lock lock(hbm_mutex); |
| 407 | |
| 408 | AHardwareBuffer_Desc buffer_desc{}; |
| 409 | AHardwareBuffer_describe(hardware_buffer, &buffer_desc); |
| 410 | |
| 411 | auto [properties, format_properties] = device.getAndroidHardwareBufferPropertiesANDROID<vk::AndroidHardwareBufferPropertiesANDROID, vk::AndroidHardwareBufferFormatPropertiesANDROID>(*hardware_buffer); |
| 412 | |
| 413 | if (!*ycbcr_sampler || memcmp(&ahb_format, &format_properties, sizeof(format_properties))) |
| 414 | { |
| 415 | memcpy(&ahb_format, &format_properties, sizeof(format_properties)); |
| 416 | spdlog::info("decoded image size: {}x{}", buffer_desc.width, buffer_desc.height); |
| 417 | create_sampler(buffer_desc, ahb_format); |
| 418 | hardware_buffer_map.clear(); |
| 419 | // TODO tell the reprojector to recreate the pipeline |
| 420 | } |
| 421 | |
| 422 | auto it = hardware_buffer_map.find(hardware_buffer); |
| 423 | if (it != hardware_buffer_map.end()) |
| 424 | return it->second; |
| 425 | |
| 426 | vk::StructureChain img_info{ |
| 427 | vk::ImageCreateInfo{ |
| 428 | .flags = {}, |
| 429 | .imageType = vk::ImageType::e2D, |
| 430 | .format = vk::Format::eUndefined, |
| 431 | .extent = {buffer_desc.width, buffer_desc.height, 1}, |
| 432 | .mipLevels = 1, |
| 433 | .arrayLayers = 1, |
| 434 | .samples = vk::SampleCountFlagBits::e1, |
| 435 | .tiling = vk::ImageTiling::eOptimal, |
| 436 | .usage = vk::ImageUsageFlagBits::eSampled, |
| 437 | .sharingMode = vk::SharingMode::eExclusive, |
| 438 | .initialLayout = vk::ImageLayout::eUndefined, |
| 439 | }, |
| 440 | vk::ExternalMemoryImageCreateInfo{ |
| 441 | .handleTypes = vk::ExternalMemoryHandleTypeFlagBits::eAndroidHardwareBufferANDROID, |
| 442 | }, |
| 443 | vk::ExternalFormatANDROID{ |
| 444 | .externalFormat = format_properties.externalFormat, |
| 445 | }, |
| 446 | }; |
| 447 | |
| 448 | vk::raii::Image vimage(device, img_info.get()); |
| 449 | |
| 450 | assert(properties.memoryTypeBits != 0); |
| 451 | vk::StructureChain mem_info{ |
| 452 | vk::MemoryAllocateInfo{ |
| 453 | .allocationSize = properties.allocationSize, |
| 454 | .memoryTypeIndex = (uint32_t)(ffs(properties.memoryTypeBits) - 1), |
| 455 | }, |
| 456 | vk::MemoryDedicatedAllocateInfo{ |
| 457 | .image = *vimage, |
| 458 | }, |