| /* |
| * Copyright 2022 Google LLC. |
| * |
| * Use of this source code is governed by a BSD-style license that can be |
| * found in the LICENSE file. |
| */ |
| |
| #ifndef skgpu_VulkanTypes_DEFINED |
| #define skgpu_VulkanTypes_DEFINED |
| |
| #include "include/core/SkTypes.h" |
| #include "include/private/base/SkTo.h" |
| #include "include/private/gpu/vk/SkiaVulkan.h" |
| |
| #include <cstddef> |
| #include <cstdint> |
| #include <functional> |
| #include <optional> |
| #include <string> |
| #include <vector> |
| |
| #ifndef VK_VERSION_1_1 |
| #error Skia requires the use of Vulkan 1.1 headers |
| #endif |
| |
| namespace skgpu { |
| |
| namespace graphite { |
| class VulkanYcbcrConversion; |
| } |
| |
| using VulkanGetProc = std::function<PFN_vkVoidFunction( |
| const char*, // function name |
| VkInstance, // instance or VK_NULL_HANDLE |
| VkDevice // device or VK_NULL_HANDLE |
| )>; |
| |
| typedef intptr_t VulkanBackendMemory; |
| |
| /** |
| * Types for interacting with Vulkan resources created externally to Skia. |
| */ |
| struct VulkanAlloc { |
| // can be VK_NULL_HANDLE iff is an RT and is borrowed |
| VkDeviceMemory fMemory = VK_NULL_HANDLE; |
| VkDeviceSize fOffset = 0; |
| VkDeviceSize fSize = 0; // this can be indeterminate iff Tex uses borrow semantics |
| uint32_t fFlags = 0; |
| // handle to memory allocated via skgpu::VulkanMemoryAllocator. |
| VulkanBackendMemory fBackendMemory = 0; |
| |
| enum Flag { |
| kNoncoherent_Flag = 0x1, // memory must be flushed to device after mapping |
| kMappable_Flag = 0x2, // memory is able to be mapped. |
| kLazilyAllocated_Flag = 0x4, // memory was created with lazy allocation |
| }; |
| |
| bool operator==(const VulkanAlloc& that) const { |
| return fMemory == that.fMemory && fOffset == that.fOffset && fSize == that.fSize && |
| fFlags == that.fFlags && fUsesSystemHeap == that.fUsesSystemHeap; |
| } |
| |
| private: |
| bool fUsesSystemHeap = false; |
| }; |
| |
| // Used to pass in the necessary information to create a VkSamplerYcbcrConversion object for an |
| // VkExternalFormatANDROID. |
| struct SK_API VulkanYcbcrConversionInfo { |
| public: |
| // Makes an invalid VulkanYcbcrConversionInfo |
| VulkanYcbcrConversionInfo() = default; |
| |
| // For external images format features here should be those returned by a call to |
| // vkAndroidHardwareBufferFormatPropertiesANDROID |
| VulkanYcbcrConversionInfo(uint64_t externalFormat, |
| VkSamplerYcbcrModelConversion ycbcrModel, |
| VkSamplerYcbcrRange ycbcrRange, |
| VkChromaLocation xChromaOffset, |
| VkChromaLocation yChromaOffset, |
| VkFilter chromaFilter, |
| VkBool32 forceExplicitReconstruction, |
| VkComponentMapping components, |
| VkFormatFeatureFlags formatFeatures) |
| : VulkanYcbcrConversionInfo(VK_FORMAT_UNDEFINED, |
| externalFormat, |
| ycbcrModel, |
| ycbcrRange, |
| xChromaOffset, |
| yChromaOffset, |
| chromaFilter, |
| forceExplicitReconstruction, |
| components, |
| formatFeatures) {} |
| |
| VulkanYcbcrConversionInfo(VkFormat format, |
| VkSamplerYcbcrModelConversion ycbcrModel, |
| VkSamplerYcbcrRange ycbcrRange, |
| VkChromaLocation xChromaOffset, |
| VkChromaLocation yChromaOffset, |
| VkFilter chromaFilter, |
| VkBool32 forceExplicitReconstruction, |
| VkComponentMapping components, |
| VkFormatFeatureFlags formatFeatures) |
| : VulkanYcbcrConversionInfo(format, |
| 0, |
| ycbcrModel, |
| ycbcrRange, |
| xChromaOffset, |
| yChromaOffset, |
| chromaFilter, |
| forceExplicitReconstruction, |
| components, |
| formatFeatures) {} |
| |
| bool operator==(const VulkanYcbcrConversionInfo& that) const { |
| // Invalid objects are not required to have all other fields initialized or matching. |
| if (!this->isValid() && !that.isValid()) { |
| return true; |
| } |
| |
| // Note that we do not need to check for fSamplerFilterMustMatchChromaFilter equality. This |
| // is because the Vulkan spec dictates that Android hardware buffers with the same external |
| // format must have the same support for key features. See |
| // https://docs.vulkan.org/spec/latest/chapters/memory.html#_android_hardware_buffer_external_memory |
| // for more details. |
| return this->fFormat == that.fFormat && |
| this->fExternalFormat == that.fExternalFormat && |
| this->fYcbcrModel == that.fYcbcrModel && |
| this->fYcbcrRange == that.fYcbcrRange && |
| this->fXChromaOffset == that.fXChromaOffset && |
| this->fYChromaOffset == that.fYChromaOffset && |
| this->fChromaFilter == that.fChromaFilter && |
| this->fForceExplicitReconstruction == that.fForceExplicitReconstruction && |
| this->fComponents.r == that.fComponents.r && |
| this->fComponents.g == that.fComponents.g && |
| this->fComponents.b == that.fComponents.b && |
| this->fComponents.a == that.fComponents.a; |
| } |
| bool operator!=(const VulkanYcbcrConversionInfo& that) const { return !(*this == that); } |
| |
| bool isValid() const { |
| return fYcbcrModel != VK_SAMPLER_YCBCR_MODEL_CONVERSION_RGB_IDENTITY || |
| this->hasExternalFormat(); |
| } |
| |
| VkFormat format() const { return fFormat; } |
| |
| bool hasExternalFormat() const { return fExternalFormat != 0; } |
| uint64_t externalFormat() const { return fExternalFormat; } |
| |
| VkSamplerYcbcrModelConversion model() const { return fYcbcrModel; } |
| VkSamplerYcbcrRange range() const { return fYcbcrRange; } |
| VkChromaLocation xChromaOffset() const { return fXChromaOffset; } |
| VkChromaLocation yChromaOffset() const { return fYChromaOffset; } |
| VkFilter chromaFilter() const { return fChromaFilter; } |
| VkBool32 forceExplicitReconstruction() const { return fForceExplicitReconstruction; } |
| VkComponentMapping components() const { return fComponents; } |
| |
| bool samplerFilterMustMatchChromaFilter() const { return fSamplerFilterMustMatchChromaFilter; } |
| bool supportsLinearFilter() const { return fSupportsLinearFilter; } |
| |
| // Returns a populated VkSamplerYcbcrConversionCreateInfo object based on |
| // VulkanYcbcrConversionInfo |
| void toVkSamplerYcbcrConversionCreateInfo(VkSamplerYcbcrConversionCreateInfo* outInfo, |
| std::optional<VkFilter>* requiredSamplerFilter) const; |
| |
| private: |
| VulkanYcbcrConversionInfo(VkFormat format, |
| uint64_t externalFormat, |
| VkSamplerYcbcrModelConversion ycbcrModel, |
| VkSamplerYcbcrRange ycbcrRange, |
| VkChromaLocation xChromaOffset, |
| VkChromaLocation yChromaOffset, |
| VkFilter chromaFilter, |
| VkBool32 forceExplicitReconstruction, |
| VkComponentMapping components, |
| VkFormatFeatureFlags formatFeatures); |
| |
| |
| // For use internally to recreate from an ImmutableSamplerInfo. We don't have feature flags |
| // and assume we've updated all the fields as required by the feature flags previously. |
| friend class graphite::VulkanYcbcrConversion; |
| |
| VulkanYcbcrConversionInfo(VkFormat format, |
| uint64_t externalFormat, |
| VkSamplerYcbcrModelConversion ycbcrModel, |
| VkSamplerYcbcrRange ycbcrRange, |
| VkChromaLocation xChromaOffset, |
| VkChromaLocation yChromaOffset, |
| VkFilter chromaFilter, |
| VkBool32 forceExplicitReconstruction, |
| VkComponentMapping components, |
| bool mustMatchChromaFilter, |
| bool supportsLinearFilter) |
| : fFormat(format) |
| , fExternalFormat(externalFormat) |
| , fYcbcrModel(ycbcrModel) |
| , fYcbcrRange(ycbcrRange) |
| , fXChromaOffset(xChromaOffset) |
| , fYChromaOffset(yChromaOffset) |
| , fChromaFilter(chromaFilter) |
| , fForceExplicitReconstruction(forceExplicitReconstruction) |
| , fComponents(components) |
| , fSamplerFilterMustMatchChromaFilter(mustMatchChromaFilter) |
| , fSupportsLinearFilter(supportsLinearFilter) {} |
| |
| // Format of the source image. Must be set to VK_FORMAT_UNDEFINED for external images or |
| // a valid image format otherwise. |
| VkFormat fFormat = VK_FORMAT_UNDEFINED; |
| |
| // The external format. Must be non-zero for external images, zero otherwise. |
| // Should be compatible to be used in a VkExternalFormatANDROID struct. |
| uint64_t fExternalFormat = 0; |
| |
| VkSamplerYcbcrModelConversion fYcbcrModel = VK_SAMPLER_YCBCR_MODEL_CONVERSION_RGB_IDENTITY; |
| VkSamplerYcbcrRange fYcbcrRange = VK_SAMPLER_YCBCR_RANGE_ITU_FULL; |
| VkChromaLocation fXChromaOffset = VK_CHROMA_LOCATION_COSITED_EVEN; |
| VkChromaLocation fYChromaOffset = VK_CHROMA_LOCATION_COSITED_EVEN; |
| VkFilter fChromaFilter = VK_FILTER_NEAREST; |
| VkBool32 fForceExplicitReconstruction = false; |
| |
| // This is ignored when fExternalFormat is non-zero. |
| VkComponentMapping fComponents = {VK_COMPONENT_SWIZZLE_IDENTITY, |
| VK_COMPONENT_SWIZZLE_IDENTITY, |
| VK_COMPONENT_SWIZZLE_IDENTITY, |
| VK_COMPONENT_SWIZZLE_IDENTITY}; |
| |
| // Default these values to the most restrictive. These defaults only really matter until |
| // we force all clients to go through our constructors. At that point these will be set to the |
| // correct values. |
| bool fSamplerFilterMustMatchChromaFilter = true; |
| bool fSupportsLinearFilter = false; |
| }; |
| |
| typedef void* VulkanDeviceLostContext; |
| typedef void (*VulkanDeviceLostProc)(VulkanDeviceLostContext faultContext, |
| const std::string& description, |
| const std::vector<VkDeviceFaultAddressInfoEXT>& addressInfos, |
| const std::vector<VkDeviceFaultVendorInfoEXT>& vendorInfos, |
| const std::vector<std::byte>& vendorBinaryData); |
| |
| } // namespace skgpu |
| |
| #endif // skgpu_VulkanTypes_DEFINED |