Reduce memory used by MVKPixelFormats lookups.

- Add MVKInflectionMap collection to manage lookups based on enums
  that have a large set of consecutive elements, plus additional enum
  values that are more sparsely assigned.
- Recognize every MTLPixelFormat value can be held in uint16_t.
- Reduce inflection-map sizes by calling shrink_to_fit().
- runcts script log completion time (unrelated).
This commit is contained in:
Bill Hollings 2024-01-03 12:43:00 -05:00
commit a836e18050
10 changed files with 127 additions and 69 deletions

View File

@ -314,6 +314,8 @@ In addition to core *Vulkan* functionality, **MoltenVK** also supports the foll
- `VK_KHR_bind_memory2` - `VK_KHR_bind_memory2`
- `VK_KHR_buffer_device_address` - `VK_KHR_buffer_device_address`
- *Requires GPU Tier 2 argument buffers support.* - *Requires GPU Tier 2 argument buffers support.*
- `VK_KHR_calibrated_timestamp`
- *Requires Metal 2.2.*
- `VK_KHR_copy_commands2` - `VK_KHR_copy_commands2`
- `VK_KHR_create_renderpass2` - `VK_KHR_create_renderpass2`
- `VK_KHR_dedicated_allocation` - `VK_KHR_dedicated_allocation`
@ -323,6 +325,7 @@ In addition to core *Vulkan* functionality, **MoltenVK** also supports the foll
- `VK_KHR_device_group_creation` - `VK_KHR_device_group_creation`
- `VK_KHR_driver_properties` - `VK_KHR_driver_properties`
- `VK_KHR_dynamic_rendering` - `VK_KHR_dynamic_rendering`
- `VK_KHR_format_feature_flags2`
- `VK_KHR_fragment_shader_barycentric` - `VK_KHR_fragment_shader_barycentric`
- *Requires Metal 2.2 on Mac or Metal 2.3 on iOS.* - *Requires Metal 2.2 on Mac or Metal 2.3 on iOS.*
- `VK_KHR_get_memory_requirements2` - `VK_KHR_get_memory_requirements2`
@ -358,6 +361,7 @@ In addition to core *Vulkan* functionality, **MoltenVK** also supports the foll
- `VK_KHR_timeline_semaphore` - `VK_KHR_timeline_semaphore`
- `VK_KHR_uniform_buffer_standard_layout` - `VK_KHR_uniform_buffer_standard_layout`
- `VK_KHR_variable_pointers` - `VK_KHR_variable_pointers`
- `VK_KHR_vertex_attribute_divisor`
- `VK_EXT_4444_formats` - `VK_EXT_4444_formats`
- *Requires 16-bit formats and either native texture swizzling or manual swizzling to be enabled.* - *Requires 16-bit formats and either native texture swizzling or manual swizzling to be enabled.*
- `VK_EXT_buffer_device_address` - `VK_EXT_buffer_device_address`

View File

@ -1 +1 @@
19a863ccce773ff393b186329478b1eb1a519fd3 41263fc5aa994b8eafaca946583bfcceca8ca419

View File

@ -762,6 +762,12 @@ void MVKPhysicalDevice::getProperties(VkPhysicalDeviceProperties2* properties) {
portabilityProps->minVertexInputBindingStrideAlignment = (uint32_t)_metalFeatures.vertexStrideAlignment; portabilityProps->minVertexInputBindingStrideAlignment = (uint32_t)_metalFeatures.vertexStrideAlignment;
break; break;
} }
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VERTEX_ATTRIBUTE_DIVISOR_PROPERTIES_KHR: {
auto* divisorProps = (VkPhysicalDeviceVertexAttributeDivisorPropertiesKHR*)next;
divisorProps->maxVertexAttribDivisor = kMVKUndefinedLargeUInt32;
divisorProps->supportsNonZeroFirstInstance = VK_TRUE;
break;
}
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_PROPERTIES_EXT: { case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_PROPERTIES_EXT: {
auto* extDynState3Props = (VkPhysicalDeviceExtendedDynamicState3PropertiesEXT*)next; auto* extDynState3Props = (VkPhysicalDeviceExtendedDynamicState3PropertiesEXT*)next;
extDynState3Props->dynamicPrimitiveTopologyUnrestricted = false; extDynState3Props->dynamicPrimitiveTopologyUnrestricted = false;
@ -888,6 +894,22 @@ void MVKPhysicalDevice::getFormatProperties(VkFormat format, VkFormatProperties*
void MVKPhysicalDevice::getFormatProperties(VkFormat format, VkFormatProperties2KHR* pFormatProperties) { void MVKPhysicalDevice::getFormatProperties(VkFormat format, VkFormatProperties2KHR* pFormatProperties) {
pFormatProperties->sType = VK_STRUCTURE_TYPE_FORMAT_PROPERTIES_2_KHR; pFormatProperties->sType = VK_STRUCTURE_TYPE_FORMAT_PROPERTIES_2_KHR;
for (auto* next = (VkBaseOutStructure*)pFormatProperties->pNext; next; next = next->pNext) {
switch (next->sType) {
case VK_STRUCTURE_TYPE_FORMAT_PROPERTIES_3_KHR: {
auto* properties3 = (VkFormatProperties3*)next;
auto& properties = _pixelFormats.getVkFormatProperties3(format);
properties3->linearTilingFeatures = properties.linearTilingFeatures;
properties3->optimalTilingFeatures = properties.optimalTilingFeatures;
properties3->bufferFeatures = properties.bufferFeatures;
break;
}
default:
break;
}
}
getFormatProperties(format, &pFormatProperties->formatProperties); getFormatProperties(format, &pFormatProperties->formatProperties);
} }
@ -999,15 +1021,14 @@ VkResult MVKPhysicalDevice::getImageFormatProperties(VkFormat format,
maxLayers = 1; maxLayers = 1;
sampleCounts = VK_SAMPLE_COUNT_1_BIT; sampleCounts = VK_SAMPLE_COUNT_1_BIT;
} else { } else {
VkFormatProperties fmtProps; VkFormatProperties3& fmtProps = _pixelFormats.getVkFormatProperties3(format);
getFormatProperties(format, &fmtProps);
// Compressed multisampled textures aren't supported. // Compressed multisampled textures aren't supported.
// Chroma-subsampled multisampled textures aren't supported. // Chroma-subsampled multisampled textures aren't supported.
// Multisampled cube textures aren't supported. // Multisampled cube textures aren't supported.
// Non-renderable multisampled textures aren't supported. // Non-renderable multisampled textures aren't supported.
if (mvkFmt == kMVKFormatCompressed || isChromaSubsampled || if (mvkFmt == kMVKFormatCompressed || isChromaSubsampled ||
mvkIsAnyFlagEnabled(flags, VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT) || mvkIsAnyFlagEnabled(flags, VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT) ||
!mvkIsAnyFlagEnabled(fmtProps.optimalTilingFeatures, VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT|VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT) ) { !mvkIsAnyFlagEnabled(fmtProps.optimalTilingFeatures, VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BIT | VK_FORMAT_FEATURE_2_DEPTH_STENCIL_ATTACHMENT_BIT) ) {
sampleCounts = VK_SAMPLE_COUNT_1_BIT; sampleCounts = VK_SAMPLE_COUNT_1_BIT;
} }
// BGRG and GBGR images may only have one mip level and one layer. // BGRG and GBGR images may only have one mip level and one layer.
@ -2520,7 +2541,11 @@ void MVKPhysicalDevice::initLimits() {
// to fill out the VkPhysicalDeviceTexelBufferAlignmentPropertiesEXT struct. // to fill out the VkPhysicalDeviceTexelBufferAlignmentPropertiesEXT struct.
uint32_t maxStorage = 0, maxUniform = 0; uint32_t maxStorage = 0, maxUniform = 0;
bool singleTexelStorage = true, singleTexelUniform = true; bool singleTexelStorage = true, singleTexelUniform = true;
_pixelFormats.enumerateSupportedFormats({0, 0, VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT | VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_BIT}, true, [&](VkFormat vk) {
VkFormatProperties3 fmtProps = {}; // We don't initialize sType as enumerateSupportedFormats doesn't care.
fmtProps.bufferFeatures = VK_FORMAT_FEATURE_2_UNIFORM_TEXEL_BUFFER_BIT | VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_BIT;
_pixelFormats.enumerateSupportedFormats(fmtProps, true, [&](VkFormat vk) {
MTLPixelFormat mtlFmt = _pixelFormats.getMTLPixelFormat(vk); MTLPixelFormat mtlFmt = _pixelFormats.getMTLPixelFormat(vk);
if ( !mtlFmt ) { return false; } // If format is invalid, avoid validation errors on MTLDevice format alignment calls if ( !mtlFmt ) { return false; } // If format is invalid, avoid validation errors on MTLDevice format alignment calls
@ -2530,7 +2555,7 @@ void MVKPhysicalDevice::initLimits() {
} else { } else {
alignment = [_mtlDevice minimumLinearTextureAlignmentForPixelFormat: mtlFmt]; alignment = [_mtlDevice minimumLinearTextureAlignmentForPixelFormat: mtlFmt];
} }
VkFormatProperties& props = _pixelFormats.getVkFormatProperties(vk); VkFormatProperties3& props = _pixelFormats.getVkFormatProperties3(vk);
// For uncompressed formats, this is the size of a single texel. // For uncompressed formats, this is the size of a single texel.
// Note that no implementations of Metal support compressed formats // Note that no implementations of Metal support compressed formats
// in a linear texture (including texture buffers). It's likely that even // in a linear texture (including texture buffers). It's likely that even
@ -2558,11 +2583,11 @@ void MVKPhysicalDevice::initLimits() {
break; break;
} }
} }
if (mvkAreAllFlagsEnabled(props.bufferFeatures, VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT)) { if (mvkAreAllFlagsEnabled(props.bufferFeatures, VK_FORMAT_FEATURE_2_UNIFORM_TEXEL_BUFFER_BIT)) {
maxUniform = max(maxUniform, uint32_t(alignment)); maxUniform = max(maxUniform, uint32_t(alignment));
if (alignment > texelSize) { singleTexelUniform = false; } if (alignment > texelSize) { singleTexelUniform = false; }
} }
if (mvkAreAllFlagsEnabled(props.bufferFeatures, VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_BIT)) { if (mvkAreAllFlagsEnabled(props.bufferFeatures, VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_BIT)) {
maxStorage = max(maxStorage, uint32_t(alignment)); maxStorage = max(maxStorage, uint32_t(alignment));
if (alignment > texelSize) { singleTexelStorage = false; } if (alignment > texelSize) { singleTexelStorage = false; }
} }

View File

@ -931,7 +931,7 @@ MVKImage::MVKImage(MVKDevice* device, const VkImageCreateInfo* pCreateInfo) : MV
_is3DCompressed = (getImageType() == VK_IMAGE_TYPE_3D) && (pixFmts->getFormatType(pCreateInfo->format) == kMVKFormatCompressed) && !_device->_pMetalFeatures->native3DCompressedTextures; _is3DCompressed = (getImageType() == VK_IMAGE_TYPE_3D) && (pixFmts->getFormatType(pCreateInfo->format) == kMVKFormatCompressed) && !_device->_pMetalFeatures->native3DCompressedTextures;
_isDepthStencilAttachment = (mvkAreAllFlagsEnabled(pCreateInfo->usage, VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT) || _isDepthStencilAttachment = (mvkAreAllFlagsEnabled(pCreateInfo->usage, VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT) ||
mvkAreAllFlagsEnabled(pixFmts->getVkFormatProperties(pCreateInfo->format).optimalTilingFeatures, VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT)); mvkAreAllFlagsEnabled(pixFmts->getVkFormatProperties3(pCreateInfo->format).optimalTilingFeatures, VK_FORMAT_FEATURE_2_DEPTH_STENCIL_ATTACHMENT_BIT));
_canSupportMTLTextureView = !_isDepthStencilAttachment || _device->_pMetalFeatures->stencilViews; _canSupportMTLTextureView = !_isDepthStencilAttachment || _device->_pMetalFeatures->stencilViews;
_rowByteAlignment = _isLinear || _isLinearForAtomics ? _device->getVkFormatTexelBufferAlignment(pCreateInfo->format, this) : mvkEnsurePowerOfTwo(pixFmts->getBytesPerBlock(pCreateInfo->format)); _rowByteAlignment = _isLinear || _isLinearForAtomics ? _device->getVkFormatTexelBufferAlignment(pCreateInfo->format, this) : mvkEnsurePowerOfTwo(pixFmts->getBytesPerBlock(pCreateInfo->format));

View File

@ -705,6 +705,8 @@ void MVKInstance::initProcAddrs() {
ADD_DVC_1_3_PROMOTED_ENTRY_POINT(vkSetPrivateData, EXT, EXT_PRIVATE_DATA); ADD_DVC_1_3_PROMOTED_ENTRY_POINT(vkSetPrivateData, EXT, EXT_PRIVATE_DATA);
// Device extension functions. // Device extension functions.
ADD_DVC_EXT_ENTRY_POINT(vkGetCalibratedTimestampsKHR, KHR_CALIBRATED_TIMESTAMPS);
ADD_DVC_EXT_ENTRY_POINT(vkGetPhysicalDeviceCalibrateableTimeDomainsKHR, KHR_CALIBRATED_TIMESTAMPS);
ADD_DVC_EXT_ENTRY_POINT(vkCreateDeferredOperationKHR, KHR_DEFERRED_HOST_OPERATIONS); ADD_DVC_EXT_ENTRY_POINT(vkCreateDeferredOperationKHR, KHR_DEFERRED_HOST_OPERATIONS);
ADD_DVC_EXT_ENTRY_POINT(vkDeferredOperationJoinKHR, KHR_DEFERRED_HOST_OPERATIONS); ADD_DVC_EXT_ENTRY_POINT(vkDeferredOperationJoinKHR, KHR_DEFERRED_HOST_OPERATIONS);
ADD_DVC_EXT_ENTRY_POINT(vkDestroyDeferredOperationKHR, KHR_DEFERRED_HOST_OPERATIONS); ADD_DVC_EXT_ENTRY_POINT(vkDestroyDeferredOperationKHR, KHR_DEFERRED_HOST_OPERATIONS);

View File

@ -140,7 +140,7 @@ typedef struct MVKVkFormatDesc {
VkExtent2D blockTexelSize; VkExtent2D blockTexelSize;
uint32_t bytesPerBlock; uint32_t bytesPerBlock;
MVKFormatType formatType; MVKFormatType formatType;
VkFormatProperties properties; VkFormatProperties3 properties;
VkComponentMapping componentMapping; VkComponentMapping componentMapping;
const char* name; const char* name;
bool hasReportedSubstitution; bool hasReportedSubstitution;
@ -337,7 +337,8 @@ public:
MTLTextureSwizzleChannels getMTLTextureSwizzleChannels(VkFormat vkFormat); MTLTextureSwizzleChannels getMTLTextureSwizzleChannels(VkFormat vkFormat);
/** Returns the default properties for the specified Vulkan format. */ /** Returns the default properties for the specified Vulkan format. */
VkFormatProperties& getVkFormatProperties(VkFormat vkFormat); VkFormatProperties getVkFormatProperties(VkFormat format);
VkFormatProperties3& getVkFormatProperties3(VkFormat vkFormat);
/** Returns the Metal format capabilities supported by the specified Vulkan format, without substitution. */ /** Returns the Metal format capabilities supported by the specified Vulkan format, without substitution. */
MVKMTLFmtCaps getCapabilities(VkFormat vkFormat, bool isExtended = false); MVKMTLFmtCaps getCapabilities(VkFormat vkFormat, bool isExtended = false);
@ -390,15 +391,15 @@ public:
bool isExtended = false); bool isExtended = false);
/** Enumerates all formats that support the given features, calling a specified function for each one. */ /** Enumerates all formats that support the given features, calling a specified function for each one. */
void enumerateSupportedFormats(VkFormatProperties properties, bool any, std::function<bool(VkFormat)> func); void enumerateSupportedFormats(const VkFormatProperties3& properties, bool any, std::function<bool(VkFormat)> func);
/** /**
* Returns the Metal MTLVertexFormat corresponding to the specified * Returns the Metal MTLVertexFormat corresponding to the specified
* Vulkan VkFormat as used as a vertex attribute format. * Vulkan VkFormat as used as a vertex attribute format.
*/ */
MTLVertexFormat getMTLVertexFormat(VkFormat vkFormat); MTLVertexFormat getMTLVertexFormat(VkFormat vkFormat);
static VkFormatFeatureFlags convertFormatPropertiesFlagBits(VkFormatFeatureFlags2 flags);
#pragma mark Construction #pragma mark Construction
MVKPixelFormats(MVKPhysicalDevice* physicalDevice = nullptr); MVKPixelFormats(MVKPhysicalDevice* physicalDevice = nullptr);

View File

@ -420,10 +420,19 @@ MTLTextureSwizzleChannels MVKPixelFormats::getMTLTextureSwizzleChannels(VkFormat
return mvkMTLTextureSwizzleChannelsFromVkComponentMapping(getVkComponentMapping(vkFormat)); return mvkMTLTextureSwizzleChannelsFromVkComponentMapping(getVkComponentMapping(vkFormat));
} }
VkFormatProperties& MVKPixelFormats::getVkFormatProperties(VkFormat vkFormat) { VkFormatProperties3& MVKPixelFormats::getVkFormatProperties3(VkFormat vkFormat) {
return getVkFormatDesc(vkFormat).properties; return getVkFormatDesc(vkFormat).properties;
} }
VkFormatProperties MVKPixelFormats::getVkFormatProperties(VkFormat vkFormat) {
auto& properties = getVkFormatProperties3(vkFormat);
VkFormatProperties ret;
ret.linearTilingFeatures = MVKPixelFormats::convertFormatPropertiesFlagBits(properties.linearTilingFeatures);
ret.optimalTilingFeatures = MVKPixelFormats::convertFormatPropertiesFlagBits(properties.optimalTilingFeatures);
ret.bufferFeatures = MVKPixelFormats::convertFormatPropertiesFlagBits(properties.bufferFeatures);
return ret;
}
MVKMTLFmtCaps MVKPixelFormats::getCapabilities(VkFormat vkFormat, bool isExtended) { MVKMTLFmtCaps MVKPixelFormats::getCapabilities(VkFormat vkFormat, bool isExtended) {
return getCapabilities(getVkFormatDesc(vkFormat).mtlPixelFormat, isExtended); return getCapabilities(getVkFormatDesc(vkFormat).mtlPixelFormat, isExtended);
} }
@ -459,8 +468,8 @@ const char* MVKPixelFormats::getName(MTLVertexFormat mtlFormat) {
return getMTLVertexFormatDesc(mtlFormat).name; return getMTLVertexFormatDesc(mtlFormat).name;
} }
void MVKPixelFormats::enumerateSupportedFormats(VkFormatProperties properties, bool any, std::function<bool(VkFormat)> func) { void MVKPixelFormats::enumerateSupportedFormats(const VkFormatProperties3& properties, bool any, std::function<bool(VkFormat)> func) {
static const auto areFeaturesSupported = [any](uint32_t a, uint32_t b) { static const auto areFeaturesSupported = [any](VkFlags64 a, VkFlags64 b) {
if (b == 0) return true; if (b == 0) return true;
if (any) if (any)
return mvkIsAnyFlagEnabled(a, b); return mvkIsAnyFlagEnabled(a, b);
@ -785,6 +794,11 @@ MVKMTLFormatDesc& MVKPixelFormats::getMTLVertexFormatDesc(MTLVertexFormat mtlFor
return _mtlVertexFormatDescriptions[mtlFormat]; return _mtlVertexFormatDescriptions[mtlFormat];
} }
VkFormatFeatureFlags MVKPixelFormats::convertFormatPropertiesFlagBits(VkFormatFeatureFlags2 flags) {
// Truncate to 32-bits and just return. All current values are identical.
return static_cast<VkFormatFeatureFlags>(flags);
}
#pragma mark Construction #pragma mark Construction
@ -803,7 +817,7 @@ MVKPixelFormats::MVKPixelFormats(MVKPhysicalDevice* physicalDevice) : _physicalD
#define addVkFormatDescFull(VK_FMT, MTL_FMT, MTL_FMT_ALT, MTL_VTX_FMT, MTL_VTX_FMT_ALT, CSPC, CSCB, BLK_W, BLK_H, BLK_BYTE_CNT, MVK_FMT_TYPE, SWIZ_R, SWIZ_G, SWIZ_B, SWIZ_A) \ #define addVkFormatDescFull(VK_FMT, MTL_FMT, MTL_FMT_ALT, MTL_VTX_FMT, MTL_VTX_FMT_ALT, CSPC, CSCB, BLK_W, BLK_H, BLK_BYTE_CNT, MVK_FMT_TYPE, SWIZ_R, SWIZ_G, SWIZ_B, SWIZ_A) \
vkFmt = VK_FORMAT_ ##VK_FMT; \ vkFmt = VK_FORMAT_ ##VK_FMT; \
_vkFormatDescriptions[vkFmt] = { vkFmt, MTLPixelFormat ##MTL_FMT, MTLPixelFormat ##MTL_FMT_ALT, MTLVertexFormat ##MTL_VTX_FMT, MTLVertexFormat ##MTL_VTX_FMT_ALT, \ _vkFormatDescriptions[vkFmt] = { vkFmt, MTLPixelFormat ##MTL_FMT, MTLPixelFormat ##MTL_FMT_ALT, MTLVertexFormat ##MTL_VTX_FMT, MTLVertexFormat ##MTL_VTX_FMT_ALT, \
CSPC, CSCB, { BLK_W, BLK_H }, BLK_BYTE_CNT, kMVKFormat ##MVK_FMT_TYPE, { 0, 0, 0 }, \ CSPC, CSCB, { BLK_W, BLK_H }, BLK_BYTE_CNT, kMVKFormat ##MVK_FMT_TYPE, { VK_STRUCTURE_TYPE_FORMAT_PROPERTIES_3, nullptr, 0, 0, 0 }, \
{ VK_COMPONENT_SWIZZLE_ ##SWIZ_R, VK_COMPONENT_SWIZZLE_ ##SWIZ_G, VK_COMPONENT_SWIZZLE_ ##SWIZ_B, VK_COMPONENT_SWIZZLE_ ##SWIZ_A }, \ { VK_COMPONENT_SWIZZLE_ ##SWIZ_R, VK_COMPONENT_SWIZZLE_ ##SWIZ_G, VK_COMPONENT_SWIZZLE_ ##SWIZ_B, VK_COMPONENT_SWIZZLE_ ##SWIZ_A }, \
"VK_FORMAT_" #VK_FMT, false } "VK_FORMAT_" #VK_FMT, false }
@ -818,6 +832,7 @@ MVKPixelFormats::MVKPixelFormats(MVKPhysicalDevice* physicalDevice) : _physicalD
void MVKPixelFormats::initVkFormatCapabilities() { void MVKPixelFormats::initVkFormatCapabilities() {
VkFormat vkFmt; VkFormat vkFmt;
_vkFormatDescriptions.reserve(512); // High estimate to future-proof against allocations as elements are added. shrink_to_fit() below will collapse.
// UNDEFINED must come first. // UNDEFINED must come first.
addVkFormatDesc( UNDEFINED, Invalid, Invalid, Invalid, Invalid, 1, 1, 0, None ); addVkFormatDesc( UNDEFINED, Invalid, Invalid, Invalid, Invalid, 1, 1, 0, None );
@ -1126,6 +1141,7 @@ void MVKPixelFormats::initVkFormatCapabilities() {
void MVKPixelFormats::initMTLPixelFormatCapabilities() { void MVKPixelFormats::initMTLPixelFormatCapabilities() {
MTLPixelFormat mtlPixFmt; MTLPixelFormat mtlPixFmt;
_mtlPixelFormatDescriptions.reserve(512); // High estimate to future-proof against allocations as elements are added. shrink_to_fit() below will collapse.
// MTLPixelFormatInvalid must come first. // MTLPixelFormatInvalid must come first.
addMTLPixelFormatDesc ( Invalid, None, None, None ); addMTLPixelFormatDesc ( Invalid, None, None, None );
@ -1307,7 +1323,6 @@ void MVKPixelFormats::initMTLPixelFormatCapabilities() {
void MVKPixelFormats::initMTLVertexFormatCapabilities() { void MVKPixelFormats::initMTLVertexFormatCapabilities() {
MTLVertexFormat mtlVtxFmt; MTLVertexFormat mtlVtxFmt;
_mtlVertexFormatDescriptions.resize(MTLVertexFormatHalf + 3, {}); _mtlVertexFormatDescriptions.resize(MTLVertexFormatHalf + 3, {});
addMTLVertexFormatDesc( Invalid, None, None ); // MTLVertexFormatInvalid must come first. addMTLVertexFormatDesc( Invalid, None, None ); // MTLVertexFormatInvalid must come first.
@ -2026,33 +2041,33 @@ void MVKPixelFormats::buildVkFormatMaps() {
} }
// Enumeration of Vulkan format features aligned to the MVKMTLFmtCaps enumeration. // Enumeration of Vulkan format features aligned to the MVKMTLFmtCaps enumeration.
typedef enum : VkFormatFeatureFlags { typedef enum : VkFormatFeatureFlags2 {
kMVKVkFormatFeatureFlagsTexNone = 0, kMVKVkFormatFeatureFlagsTexNone = 0,
kMVKVkFormatFeatureFlagsTexRead = (VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT | kMVKVkFormatFeatureFlagsTexRead = (VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_BIT |
VK_FORMAT_FEATURE_TRANSFER_SRC_BIT | VK_FORMAT_FEATURE_2_TRANSFER_SRC_BIT |
VK_FORMAT_FEATURE_TRANSFER_DST_BIT | VK_FORMAT_FEATURE_2_TRANSFER_DST_BIT |
VK_FORMAT_FEATURE_BLIT_SRC_BIT), VK_FORMAT_FEATURE_2_BLIT_SRC_BIT),
kMVKVkFormatFeatureFlagsTexFilter = (VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_LINEAR_BIT), kMVKVkFormatFeatureFlagsTexFilter = (VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_FILTER_LINEAR_BIT),
kMVKVkFormatFeatureFlagsTexWrite = (VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT), kMVKVkFormatFeatureFlagsTexWrite = (VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT),
kMVKVkFormatFeatureFlagsTexAtomic = (VK_FORMAT_FEATURE_STORAGE_IMAGE_ATOMIC_BIT), kMVKVkFormatFeatureFlagsTexAtomic = (VK_FORMAT_FEATURE_2_STORAGE_IMAGE_ATOMIC_BIT),
kMVKVkFormatFeatureFlagsTexColorAtt = (VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT | kMVKVkFormatFeatureFlagsTexColorAtt = (VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BIT |
VK_FORMAT_FEATURE_BLIT_DST_BIT), VK_FORMAT_FEATURE_2_BLIT_DST_BIT),
kMVKVkFormatFeatureFlagsTexDSAtt = (VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT | kMVKVkFormatFeatureFlagsTexDSAtt = (VK_FORMAT_FEATURE_2_DEPTH_STENCIL_ATTACHMENT_BIT |
VK_FORMAT_FEATURE_BLIT_DST_BIT), VK_FORMAT_FEATURE_2_BLIT_DST_BIT),
kMVKVkFormatFeatureFlagsTexBlend = (VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BLEND_BIT), kMVKVkFormatFeatureFlagsTexBlend = (VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BLEND_BIT),
kMVKVkFormatFeatureFlagsTexTransfer = (VK_FORMAT_FEATURE_TRANSFER_SRC_BIT | kMVKVkFormatFeatureFlagsTexTransfer = (VK_FORMAT_FEATURE_2_TRANSFER_SRC_BIT |
VK_FORMAT_FEATURE_TRANSFER_DST_BIT), VK_FORMAT_FEATURE_2_TRANSFER_DST_BIT),
kMVKVkFormatFeatureFlagsTexChromaSubsampling = (VK_FORMAT_FEATURE_MIDPOINT_CHROMA_SAMPLES_BIT_KHR | kMVKVkFormatFeatureFlagsTexChromaSubsampling = (VK_FORMAT_FEATURE_2_MIDPOINT_CHROMA_SAMPLES_BIT_KHR |
VK_FORMAT_FEATURE_SAMPLED_IMAGE_YCBCR_CONVERSION_LINEAR_FILTER_BIT_KHR), VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_YCBCR_CONVERSION_LINEAR_FILTER_BIT_KHR),
kMVKVkFormatFeatureFlagsTexMultiPlanar = (VK_FORMAT_FEATURE_COSITED_CHROMA_SAMPLES_BIT_KHR | kMVKVkFormatFeatureFlagsTexMultiPlanar = (VK_FORMAT_FEATURE_2_COSITED_CHROMA_SAMPLES_BIT_KHR |
VK_FORMAT_FEATURE_SAMPLED_IMAGE_YCBCR_CONVERSION_SEPARATE_RECONSTRUCTION_FILTER_BIT_KHR | VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_YCBCR_CONVERSION_SEPARATE_RECONSTRUCTION_FILTER_BIT_KHR |
VK_FORMAT_FEATURE_SAMPLED_IMAGE_YCBCR_CONVERSION_CHROMA_RECONSTRUCTION_EXPLICIT_BIT_KHR | VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_YCBCR_CONVERSION_CHROMA_RECONSTRUCTION_EXPLICIT_BIT_KHR |
VK_FORMAT_FEATURE_SAMPLED_IMAGE_YCBCR_CONVERSION_CHROMA_RECONSTRUCTION_EXPLICIT_FORCEABLE_BIT_KHR | VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_YCBCR_CONVERSION_CHROMA_RECONSTRUCTION_EXPLICIT_FORCEABLE_BIT_KHR |
VK_FORMAT_FEATURE_DISJOINT_BIT_KHR), VK_FORMAT_FEATURE_2_DISJOINT_BIT_KHR),
kMVKVkFormatFeatureFlagsBufRead = (VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT), kMVKVkFormatFeatureFlagsBufRead = (VK_FORMAT_FEATURE_2_UNIFORM_TEXEL_BUFFER_BIT),
kMVKVkFormatFeatureFlagsBufWrite = (VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_BIT), kMVKVkFormatFeatureFlagsBufWrite = (VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_BIT),
kMVKVkFormatFeatureFlagsBufAtomic = (VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_ATOMIC_BIT), kMVKVkFormatFeatureFlagsBufAtomic = (VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_ATOMIC_BIT),
kMVKVkFormatFeatureFlagsBufVertex = (VK_FORMAT_FEATURE_VERTEX_BUFFER_BIT), kMVKVkFormatFeatureFlagsBufVertex = (VK_FORMAT_FEATURE_2_VERTEX_BUFFER_BIT),
} MVKVkFormatFeatureFlags; } MVKVkFormatFeatureFlags;
// Sets the VkFormatProperties (optimal/linear/buffer) for the Vulkan format. // Sets the VkFormatProperties (optimal/linear/buffer) for the Vulkan format.
@ -2063,7 +2078,7 @@ void MVKPixelFormats::setFormatProperties(MVKVkFormatDesc& vkDesc) {
mvkEnableFlags(VK_FEATS, kMVKVkFormatFeatureFlags ##TYPE ##CAP); \ mvkEnableFlags(VK_FEATS, kMVKVkFormatFeatureFlags ##TYPE ##CAP); \
} }
VkFormatProperties& vkProps = vkDesc.properties; VkFormatProperties3& vkProps = vkDesc.properties;
MVKMTLFmtCaps mtlPixFmtCaps = getMTLPixelFormatDesc(vkDesc.mtlPixelFormat).mtlFmtCaps; MVKMTLFmtCaps mtlPixFmtCaps = getMTLPixelFormatDesc(vkDesc.mtlPixelFormat).mtlFmtCaps;
vkProps.optimalTilingFeatures = kMVKVkFormatFeatureFlagsTexNone; vkProps.optimalTilingFeatures = kMVKVkFormatFeatureFlagsTexNone;
vkProps.linearTilingFeatures = kMVKVkFormatFeatureFlagsTexNone; vkProps.linearTilingFeatures = kMVKVkFormatFeatureFlagsTexNone;
@ -2110,7 +2125,7 @@ void MVKPixelFormats::setFormatProperties(MVKVkFormatDesc& vkDesc) {
// Vulkan forbids blits between chroma-subsampled formats. // Vulkan forbids blits between chroma-subsampled formats.
// If we can't write the stencil reference from the shader, we can't blit stencil. // If we can't write the stencil reference from the shader, we can't blit stencil.
if (chromaSubsamplingComponentBits > 0 || (isStencilFormat(vkDesc.mtlPixelFormat) && !supportsStencilFeedback)) { if (chromaSubsamplingComponentBits > 0 || (isStencilFormat(vkDesc.mtlPixelFormat) && !supportsStencilFeedback)) {
mvkDisableFlags(vkProps.optimalTilingFeatures, (VK_FORMAT_FEATURE_BLIT_SRC_BIT | VK_FORMAT_FEATURE_BLIT_DST_BIT)); mvkDisableFlags(vkProps.optimalTilingFeatures, (VK_FORMAT_FEATURE_2_BLIT_SRC_BIT | VK_FORMAT_FEATURE_2_BLIT_DST_BIT));
} }
// These formats require swizzling. In order to support rendering, we'll have to swizzle // These formats require swizzling. In order to support rendering, we'll have to swizzle

View File

@ -45,6 +45,7 @@ MVK_EXTENSION(KHR_16bit_storage, KHR_16BIT_STORAGE,
MVK_EXTENSION(KHR_8bit_storage, KHR_8BIT_STORAGE, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_8bit_storage, KHR_8BIT_STORAGE, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_bind_memory2, KHR_BIND_MEMORY_2, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_bind_memory2, KHR_BIND_MEMORY_2, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_buffer_device_address, KHR_BUFFER_DEVICE_ADDRESS, DEVICE, 13.0, 16.0, 1.0) MVK_EXTENSION(KHR_buffer_device_address, KHR_BUFFER_DEVICE_ADDRESS, DEVICE, 13.0, 16.0, 1.0)
MVK_EXTENSION(KHR_calibrated_timestamps, KHR_CALIBRATED_TIMESTAMPS, DEVICE, 10.15, 14.0, 1.0)
MVK_EXTENSION(KHR_copy_commands2, KHR_COPY_COMMANDS_2, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_copy_commands2, KHR_COPY_COMMANDS_2, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_create_renderpass2, KHR_CREATE_RENDERPASS_2, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_create_renderpass2, KHR_CREATE_RENDERPASS_2, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_dedicated_allocation, KHR_DEDICATED_ALLOCATION, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_dedicated_allocation, KHR_DEDICATED_ALLOCATION, DEVICE, 10.11, 8.0, 1.0)
@ -63,6 +64,7 @@ MVK_EXTENSION(KHR_external_memory_capabilities, KHR_EXTERNAL_MEMORY_CAPABI
MVK_EXTENSION(KHR_external_semaphore, KHR_EXTERNAL_SEMAPHORE, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_external_semaphore, KHR_EXTERNAL_SEMAPHORE, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_external_semaphore_capabilities, KHR_EXTERNAL_SEMAPHORE_CAPABILITIES, INSTANCE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_external_semaphore_capabilities, KHR_EXTERNAL_SEMAPHORE_CAPABILITIES, INSTANCE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_fragment_shader_barycentric, KHR_FRAGMENT_SHADER_BARYCENTRIC, DEVICE, 10.15, 14.0, 1.0) MVK_EXTENSION(KHR_fragment_shader_barycentric, KHR_FRAGMENT_SHADER_BARYCENTRIC, DEVICE, 10.15, 14.0, 1.0)
MVK_EXTENSION(KHR_format_feature_flags2, KHR_FORMAT_FEATURE_FLAGS_2, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_get_memory_requirements2, KHR_GET_MEMORY_REQUIREMENTS_2, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_get_memory_requirements2, KHR_GET_MEMORY_REQUIREMENTS_2, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_get_physical_device_properties2, KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2, INSTANCE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_get_physical_device_properties2, KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2, INSTANCE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_get_surface_capabilities2, KHR_GET_SURFACE_CAPABILITIES_2, INSTANCE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_get_surface_capabilities2, KHR_GET_SURFACE_CAPABILITIES_2, INSTANCE, 10.11, 8.0, 1.0)
@ -95,6 +97,7 @@ MVK_EXTENSION(KHR_synchronization2, KHR_SYNCHRONIZATION_2,
MVK_EXTENSION(KHR_timeline_semaphore, KHR_TIMELINE_SEMAPHORE, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_timeline_semaphore, KHR_TIMELINE_SEMAPHORE, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_uniform_buffer_standard_layout, KHR_UNIFORM_BUFFER_STANDARD_LAYOUT, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_uniform_buffer_standard_layout, KHR_UNIFORM_BUFFER_STANDARD_LAYOUT, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_variable_pointers, KHR_VARIABLE_POINTERS, DEVICE, 10.11, 8.0, 1.0) MVK_EXTENSION(KHR_variable_pointers, KHR_VARIABLE_POINTERS, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_vertex_attribute_divisor, KHR_VERTEX_ATTRIBUTE_DIVISOR, DEVICE, 10.11, 8.0, 1.0)
MVK_EXTENSION(KHR_vulkan_memory_model, KHR_VULKAN_MEMORY_MODEL, DEVICE, MVK_NA, MVK_NA, MVK_NA) MVK_EXTENSION(KHR_vulkan_memory_model, KHR_VULKAN_MEMORY_MODEL, DEVICE, MVK_NA, MVK_NA, MVK_NA)
MVK_EXTENSION(EXT_4444_formats, EXT_4444_FORMATS, DEVICE, 11.0, 13.0, 1.0) MVK_EXTENSION(EXT_4444_formats, EXT_4444_FORMATS, DEVICE, 11.0, 13.0, 1.0)
MVK_EXTENSION(EXT_buffer_device_address, EXT_BUFFER_DEVICE_ADDRESS, DEVICE, 13.0, 16.0, 1.0) MVK_EXTENSION(EXT_buffer_device_address, EXT_BUFFER_DEVICE_ADDRESS, DEVICE, 13.0, 16.0, 1.0)

View File

@ -81,6 +81,7 @@ public:
bool empty() { return _values.size() == 0; } bool empty() { return _values.size() == 0; }
size_t size() { return _values.size(); } size_t size() { return _values.size(); }
void reserve(const size_t new_cap) { _values.reserve(new_cap); }
void shrink_to_fit() { _values.shrink_to_fit(); } void shrink_to_fit() { _values.shrink_to_fit(); }
protected: protected:

View File

@ -2875,6 +2875,33 @@ MVK_PUBLIC_VULKAN_CORE_ALIAS(vkGetBufferOpaqueCaptureAddress, KHR);
MVK_PUBLIC_VULKAN_CORE_ALIAS(vkGetDeviceMemoryOpaqueCaptureAddress, KHR); MVK_PUBLIC_VULKAN_CORE_ALIAS(vkGetDeviceMemoryOpaqueCaptureAddress, KHR);
#pragma mark -
#pragma mark VK_KHR_calibrated_timestamps
MVK_PUBLIC_VULKAN_SYMBOL VkResult vkGetPhysicalDeviceCalibrateableTimeDomainsKHR(
VkPhysicalDevice physicalDevice,
uint32_t* pTimeDomainCount,
VkTimeDomainEXT* pTimeDomains) {
MVKTraceVulkanCallStart();
MVKPhysicalDevice* mvkPD = MVKPhysicalDevice::getMVKPhysicalDevice(physicalDevice);
mvkPD->getCalibrateableTimeDomains(pTimeDomainCount, pTimeDomains);
MVKTraceVulkanCallEnd();
return VK_SUCCESS;
}
MVK_PUBLIC_VULKAN_SYMBOL VkResult vkGetCalibratedTimestampsKHR(
VkDevice device,
uint32_t timestampCount,
const VkCalibratedTimestampInfoEXT* pTimestampInfos,
uint64_t* pTimestamps,
uint64_t* pMaxDeviation) {
MVKTraceVulkanCallStart();
MVKDevice* mvkDev = MVKDevice::getMVKDevice(device);
mvkDev->getCalibratedTimestamps(timestampCount, pTimestampInfos, pTimestamps, pMaxDeviation);
MVKTraceVulkanCallEnd();
return VK_SUCCESS;
}
#pragma mark - #pragma mark -
#pragma mark VK_KHR_copy_commands2 extension #pragma mark VK_KHR_copy_commands2 extension
@ -3371,29 +3398,9 @@ MVK_PUBLIC_VULKAN_CORE_ALIAS(vkGetBufferDeviceAddress, EXT);
#pragma mark - #pragma mark -
#pragma mark VK_EXT_calibrated_timestamps extension #pragma mark VK_EXT_calibrated_timestamps extension
MVK_PUBLIC_VULKAN_SYMBOL VkResult vkGetPhysicalDeviceCalibrateableTimeDomainsEXT(
VkPhysicalDevice physicalDevice,
uint32_t* pTimeDomainCount,
VkTimeDomainEXT* pTimeDomains) {
MVKTraceVulkanCallStart();
MVKPhysicalDevice* mvkPD = MVKPhysicalDevice::getMVKPhysicalDevice(physicalDevice);
mvkPD->getCalibrateableTimeDomains(pTimeDomainCount, pTimeDomains);
MVKTraceVulkanCallEnd();
return VK_SUCCESS;
}
MVK_PUBLIC_VULKAN_SYMBOL VkResult vkGetCalibratedTimestampsEXT( MVK_PUBLIC_VULKAN_ALIAS(vkGetCalibratedTimestampsEXT, vkGetCalibratedTimestampsKHR);
VkDevice device, MVK_PUBLIC_VULKAN_ALIAS(vkGetPhysicalDeviceCalibrateableTimeDomainsEXT, vkGetPhysicalDeviceCalibrateableTimeDomainsKHR);
uint32_t timestampCount,
const VkCalibratedTimestampInfoEXT* pTimestampInfos,
uint64_t* pTimestamps,
uint64_t* pMaxDeviation) {
MVKTraceVulkanCallStart();
MVKDevice* mvkDev = MVKDevice::getMVKDevice(device);
mvkDev->getCalibratedTimestamps(timestampCount, pTimestampInfos, pTimestamps, pMaxDeviation);
MVKTraceVulkanCallEnd();
return VK_SUCCESS;
}
#pragma mark - #pragma mark -