36 FML_LOG(ERROR) <<
"Couldn't find Vulkan ICD \"" << vulkan_icd
37 <<
"\", trying \"libvulkan.so\" instead.";
38 vulkan_icd =
"libvulkan.so";
41 FML_LOG(INFO) <<
"Using Vulkan ICD: " << vulkan_icd;
43 vk_ = fml::MakeRefCounted<vulkan::VulkanProcTable>(vulkan_icd);
45 FML_LOG(ERROR) <<
"Proc table has not acquired mandatory proc addresses.";
49 application_ = std::make_unique<vulkan::VulkanApplication>(
50 *vk_,
"Flutter Unittests", std::vector<std::string>{},
51 VK_MAKE_VERSION(1, 0, 0), VK_MAKE_VERSION(1, 1, 0),
true);
52 if (!application_->IsValid()) {
53 FML_LOG(ERROR) <<
"Failed to initialize basic Vulkan state.";
57 FML_LOG(ERROR) <<
"Failed to acquire full proc table.";
61 device_ = application_->AcquireFirstCompatibleLogicalDevice();
62 if (!device_ || !device_->IsValid()) {
63 FML_LOG(ERROR) <<
"Failed to create compatible logical device.";
72 VkPhysicalDeviceFeatures features;
73 if (!device_->GetPhysicalDeviceFeatures(&features)) {
74 FML_LOG(ERROR) <<
"Failed to get physical device features.";
80 if (get_proc ==
nullptr) {
81 FML_LOG(ERROR) <<
"Failed to create Vulkan getProc for Skia.";
85 sk_sp<skgpu::VulkanMemoryAllocator> allocator =
87 VK_MAKE_VERSION(1, 1, 0), application_->GetInstance(),
88 device_->GetPhysicalDeviceHandle(), device_->GetHandle(), vk_,
true);
90 skgpu::VulkanExtensions extensions;
92 skgpu::VulkanBackendContext backend_context = {};
93 backend_context.fInstance = application_->GetInstance();
94 backend_context.fPhysicalDevice = device_->GetPhysicalDeviceHandle();
95 backend_context.fDevice = device_->GetHandle();
96 backend_context.fQueue = device_->GetQueueHandle();
97 backend_context.fGraphicsQueueIndex = device_->GetGraphicsQueueIndex();
98 backend_context.fMaxAPIVersion = VK_MAKE_VERSION(1, 1, 0);
99 backend_context.fDeviceFeatures = &features;
100 backend_context.fVkExtensions = &extensions;
101 backend_context.fGetProc = get_proc;
102 backend_context.fMemoryAllocator = allocator;
104 GrContextOptions options =
106 options.fReduceOpsTaskSplitting = GrContextOptions::Enable::kNo;
107 context_ = GrDirectContexts::MakeVulkan(backend_context, options);
120 VkImageCreateInfo info = {
121 .sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
124 .imageType = VK_IMAGE_TYPE_2D,
125 .format = VK_FORMAT_R8G8B8A8_UNORM,
126 .extent = VkExtent3D{
static_cast<uint32_t
>(
size.width),
127 static_cast<uint32_t
>(
size.height), 1},
130 .samples = VK_SAMPLE_COUNT_1_BIT,
131 .tiling = VK_IMAGE_TILING_OPTIMAL,
132 .usage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT |
133 VK_IMAGE_USAGE_TRANSFER_DST_BIT |
134 VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_SAMPLED_BIT,
135 .sharingMode = VK_SHARING_MODE_EXCLUSIVE,
136 .queueFamilyIndexCount = 0,
137 .pQueueFamilyIndices =
nullptr,
138 .initialLayout = VK_IMAGE_LAYOUT_UNDEFINED,
143 vk_->CreateImage(device_->GetHandle(), &info,
nullptr, &
image)))) {
149 vk->DestroyImage(
device->GetHandle(),
image,
nullptr);
152 VkMemoryRequirements mem_req;
153 vk_->GetImageMemoryRequirements(device_->GetHandle(),
image, &mem_req);
154 VkMemoryAllocateInfo alloc_info{};
155 alloc_info.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO;
156 alloc_info.allocationSize = mem_req.size;
157 alloc_info.memoryTypeIndex =
static_cast<uint32_t
>(__builtin_ctz(
158 mem_req.memoryTypeBits & VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT));
160 VkDeviceMemory memory;
162 nullptr, &memory)) != VK_SUCCESS) {
167 memory, [&vk = vk_, &
device = device_](VkDeviceMemory memory) {
168 vk->FreeMemory(
device->GetHandle(), memory,
nullptr);
172 device_->GetHandle(), result.image_, result.memory_, 0)))) {
static sk_sp< VulkanMemoryAllocator > Make(uint32_t vulkan_api_version, VkInstance instance, VkPhysicalDevice physicalDevice, VkDevice device, const fml::RefPtr< vulkan::VulkanProcTable > &vk, bool mustUseCoherentHostVisibleMemory)
sk_sp< GrDirectContext > GetGrDirectContext() const
std::optional< TestVulkanImage > CreateImage(const DlISize &size) const