Fix image subresource sizing calculations for heap-based textures.
Add MVKImage::_rowByteAlignment separate from _byteAlignment.
diff --git a/Docs/Whats_New.md b/Docs/Whats_New.md
index 0712726..6d5d4e0 100644
--- a/Docs/Whats_New.md
+++ b/Docs/Whats_New.md
@@ -22,6 +22,7 @@
- Support linear filtering when using `vkCmdBlitImage()`.
- Clamp image copy extents to image extent.
- Fix crash in `fetchDependencies` on build paths containing spaces.
+- Fix image subresource sizing calculations for heap-based textures.
- Support *Xcode 11.2*.
diff --git a/MoltenVK/MoltenVK/GPUObjects/MVKImage.h b/MoltenVK/MoltenVK/GPUObjects/MVKImage.h
index bc05360..80c9dcc 100644
--- a/MoltenVK/MoltenVK/GPUObjects/MVKImage.h
+++ b/MoltenVK/MoltenVK/GPUObjects/MVKImage.h
@@ -273,6 +273,7 @@
id<MTLTexture> _mtlTexture;
std::mutex _lock;
IOSurfaceRef _ioSurface;
+ VkDeviceSize _rowByteAlignment;
bool _isDepthStencilAttachment;
bool _canSupportMTLTextureView;
bool _hasExpectedTexelSize;
diff --git a/MoltenVK/MoltenVK/GPUObjects/MVKImage.mm b/MoltenVK/MoltenVK/GPUObjects/MVKImage.mm
index b4ffc6a..1e8ac3b 100644
--- a/MoltenVK/MoltenVK/GPUObjects/MVKImage.mm
+++ b/MoltenVK/MoltenVK/GPUObjects/MVKImage.mm
@@ -66,7 +66,7 @@
VkDeviceSize MVKImage::getBytesPerRow(uint32_t mipLevel) {
size_t bytesPerRow = mvkMTLPixelFormatBytesPerRow(_mtlPixelFormat, getExtent3D(mipLevel).width);
- return (uint32_t)mvkAlignByteOffset(bytesPerRow, _byteAlignment);
+ return mvkAlignByteOffset(bytesPerRow, _rowByteAlignment);
}
VkDeviceSize MVKImage::getBytesPerLayer(uint32_t mipLevel) {
@@ -634,6 +634,7 @@
_canSupportMTLTextureView = !_isDepthStencilAttachment || _device->_pMetalFeatures->stencilViews;
_hasExpectedTexelSize = (mvkMTLPixelFormatBytesPerBlock(_mtlPixelFormat) == mvkVkFormatBytesPerBlock(pCreateInfo->format));
+ _rowByteAlignment = _isLinear ? _device->getVkFormatTexelBufferAlignment(pCreateInfo->format, this) : mvkEnsurePowerOfTwo(mvkVkFormatBytesPerBlock(pCreateInfo->format));
if (!_isLinear && _device->_pMetalFeatures->placementHeaps) {
MTLTextureDescriptor *mtlTexDesc = newMTLTextureDescriptor(); // temp retain
MTLSizeAndAlign sizeAndAlign = [_device->getMTLDevice() heapTextureSizeAndAlignWithDescriptor: mtlTexDesc];
@@ -642,8 +643,8 @@
_byteAlignment = sizeAndAlign.align;
_isAliasable = mvkIsAnyFlagEnabled(pCreateInfo->flags, VK_IMAGE_CREATE_ALIAS_BIT);
} else {
- // Calc _byteCount after _byteAlignment
- _byteAlignment = _isLinear ? _device->getVkFormatTexelBufferAlignment(pCreateInfo->format, this) : mvkEnsurePowerOfTwo(mvkVkFormatBytesPerBlock(pCreateInfo->format));
+ // Calc _byteCount after _rowByteAlignment
+ _byteAlignment = _rowByteAlignment;
for (uint32_t mipLvl = 0; mipLvl < _mipLevels; mipLvl++) {
_byteCount += getBytesPerLayer(mipLvl) * _extent.depth * _arrayLayers;
}