diff --git a/src/dawn_native/d3d12/TextureCopySplitter.cpp b/src/dawn_native/d3d12/TextureCopySplitter.cpp index 50c3f1e7e1..ea3260c951 100644 --- a/src/dawn_native/d3d12/TextureCopySplitter.cpp +++ b/src/dawn_native/d3d12/TextureCopySplitter.cpp @@ -33,12 +33,12 @@ namespace dawn_native { namespace d3d12 { } } // namespace - TextureCopySubresource ComputeTextureCopySubresource(Origin3D origin, - Extent3D copySize, - const TexelBlockInfo& blockInfo, - uint64_t offset, - uint32_t bytesPerRow, - uint32_t rowsPerImage) { + TextureCopySubresource Compute2DTextureCopySubresource(Origin3D origin, + Extent3D copySize, + const TexelBlockInfo& blockInfo, + uint64_t offset, + uint32_t bytesPerRow, + uint32_t rowsPerImage) { TextureCopySubresource copy; ASSERT(bytesPerRow % blockInfo.byteSize == 0); @@ -48,20 +48,15 @@ namespace dawn_native { namespace d3d12 { uint64_t alignedOffset = offset & ~static_cast(D3D12_TEXTURE_DATA_PLACEMENT_ALIGNMENT - 1); - copy.offset = alignedOffset; - // If the provided offset to the data was already 512-aligned, we can simply copy the data // without further translation. if (offset == alignedOffset) { copy.count = 1; + copy.copies[0].alignedOffset = alignedOffset; copy.copies[0].textureOffset = origin; - copy.copies[0].copySize = copySize; - - copy.copies[0].bufferOffset.x = 0; - copy.copies[0].bufferOffset.y = 0; - copy.copies[0].bufferOffset.z = 0; + copy.copies[0].bufferOffset = {0, 0, 0}; copy.copies[0].bufferSize = copySize; return copy; @@ -124,11 +119,11 @@ namespace dawn_native { namespace d3d12 { copy.count = 1; + copy.copies[0].alignedOffset = alignedOffset; copy.copies[0].textureOffset = origin; - copy.copies[0].copySize = copySize; - copy.copies[0].bufferOffset = texelOffset; + copy.copies[0].bufferSize.width = copySize.width + texelOffset.x; copy.copies[0].bufferSize.height = rowsPerImageInTexels + texelOffset.y; copy.copies[0].bufferSize.depthOrArrayLayers = copySize.depthOrArrayLayers; @@ -172,6 +167,7 @@ namespace dawn_native { namespace d3d12 { copy.count = 2; + copy.copies[0].alignedOffset = alignedOffset; copy.copies[0].textureOffset = origin; ASSERT(bytesPerRow > byteOffsetInRowPitch); @@ -185,6 +181,7 @@ namespace dawn_native { namespace d3d12 { copy.copies[0].bufferSize.height = rowsPerImageInTexels + texelOffset.y; copy.copies[0].bufferSize.depthOrArrayLayers = copySize.depthOrArrayLayers; + copy.copies[1].alignedOffset = alignedOffset; copy.copies[1].textureOffset.x = origin.x + copy.copies[0].copySize.width; copy.copies[1].textureOffset.y = origin.y; copy.copies[1].textureOffset.z = origin.z; @@ -204,55 +201,102 @@ namespace dawn_native { namespace d3d12 { return copy; } - TextureCopySplits ComputeTextureCopySplits(Origin3D origin, - Extent3D copySize, - const TexelBlockInfo& blockInfo, - uint64_t offset, - uint32_t bytesPerRow, - uint32_t rowsPerImage, - bool is3DTexture) { + TextureCopySplits Compute2DTextureCopySplits(Origin3D origin, + Extent3D copySize, + const TexelBlockInfo& blockInfo, + uint64_t offset, + uint32_t bytesPerRow, + uint32_t rowsPerImage) { TextureCopySplits copies; - const uint64_t bytesPerSlice = bytesPerRow * rowsPerImage; + const uint64_t bytesPerLayer = bytesPerRow * rowsPerImage; - // The function ComputeTextureCopySubresource() decides how to split the copy based on: + // The function Compute2DTextureCopySubresource() decides how to split the copy based on: // - the alignment of the buffer offset with D3D12_TEXTURE_DATA_PLACEMENT_ALIGNMENT (512) // - the alignment of the buffer offset with D3D12_TEXTURE_DATA_PITCH_ALIGNMENT (256) - // Each slice of a 2D array or 3D copy might need to be split, but because of the WebGPU - // constraint that "bytesPerRow" must be a multiple of 256, all odd (resp. all even) slices + // Each layer of a 2D array might need to be split, but because of the WebGPU + // constraint that "bytesPerRow" must be a multiple of 256, all odd (resp. all even) layers // will be at an offset multiple of 512 of each other, which means they will all result in // the same 2D split. Thus we can just compute the copy splits for the first and second - // slices, and reuse them for the remaining slices by adding the related offset of each - // slice. Moreover, if "rowsPerImage" is even, both the first and second copy layers can + // layers, and reuse them for the remaining layers by adding the related offset of each + // layer. Moreover, if "rowsPerImage" is even, both the first and second copy layers can // share the same copy split, so in this situation we just need to compute copy split once - // and reuse it for all the slices. + // and reuse it for all the layers. Extent3D copyOneLayerSize = copySize; Origin3D copyFirstLayerOrigin = origin; - if (!is3DTexture) { - copyOneLayerSize.depthOrArrayLayers = 1; - copyFirstLayerOrigin.z = 0; - } + copyOneLayerSize.depthOrArrayLayers = 1; + copyFirstLayerOrigin.z = 0; - copies.copySubresources[0] = ComputeTextureCopySubresource( + copies.copySubresources[0] = Compute2DTextureCopySubresource( copyFirstLayerOrigin, copyOneLayerSize, blockInfo, offset, bytesPerRow, rowsPerImage); - // When the copy only refers one texture 2D array layer or a 3D texture, + // When the copy only refers one texture 2D array layer, // copies.copySubresources[1] will never be used so we can safely early return here. - if (copySize.depthOrArrayLayers == 1 || is3DTexture) { + if (copySize.depthOrArrayLayers == 1) { return copies; } - if (bytesPerSlice % D3D12_TEXTURE_DATA_PLACEMENT_ALIGNMENT == 0) { + if (bytesPerLayer % D3D12_TEXTURE_DATA_PLACEMENT_ALIGNMENT == 0) { copies.copySubresources[1] = copies.copySubresources[0]; - copies.copySubresources[1].offset += bytesPerSlice; + copies.copySubresources[1].copies[0].alignedOffset += bytesPerLayer; + copies.copySubresources[1].copies[1].alignedOffset += bytesPerLayer; } else { - const uint64_t bufferOffsetNextLayer = offset + bytesPerSlice; + const uint64_t bufferOffsetNextLayer = offset + bytesPerLayer; copies.copySubresources[1] = - ComputeTextureCopySubresource(copyFirstLayerOrigin, copyOneLayerSize, blockInfo, - bufferOffsetNextLayer, bytesPerRow, rowsPerImage); + Compute2DTextureCopySubresource(copyFirstLayerOrigin, copyOneLayerSize, blockInfo, + bufferOffsetNextLayer, bytesPerRow, rowsPerImage); } return copies; } + TextureCopySubresource Compute3DTextureCopySplits(Origin3D origin, + Extent3D copySize, + const TexelBlockInfo& blockInfo, + uint64_t offset, + uint32_t bytesPerRow, + uint32_t rowsPerImage) { + // To compute the copy region(s) for 3D textures, we call Compute2DTextureCopySubresource + // and get copy region(s) for the first slice of the copy, then extend to all depth slices + // and become a 3D copy. However, this doesn't work as easily as that due to some corner + // cases. + // + // For example, if bufferSize.height is greater than rowsPerImage in the generated copy + // region and we simply extend the 2D copy region to all copied depth slices, copied data + // will be incorrectly offset for each depth slice except the first one. This situation + // can be introduced by 2 special cases: + // - If there is an empty row at the beginning of the copy region due to alignment. + // - If copySize.height is 1 and one row of data straddle two rows. + // + // For these special cases, we need to recompute the copy regions for 3D textures like + // 1) split and modify the incorrect copy region to a few more copy regions, or 2) abandon + // the old copy region and regenerate the copy regions in different approach. + + // Call Compute2DTextureCopySubresource and get copy regions. This function has already + // forwarded "copySize.depthOrArrayLayers" to all depth slices. + TextureCopySubresource copySubresource = Compute2DTextureCopySubresource( + origin, copySize, blockInfo, offset, bytesPerRow, rowsPerImage); + + // If copySize.depth is 1, we can return copySubresource. Because we don't need to extend + // the copy region(s) to other depth slice(s). + if (copySize.depthOrArrayLayers == 1) { + return copySubresource; + } + + bool needRecompute = false; + for (uint32_t i = 0; i < copySubresource.count; ++i) { + if (copySubresource.copies[i].bufferSize.height > rowsPerImage) { + needRecompute = true; + break; + } + } + + if (!needRecompute) { + return copySubresource; + } + + // TODO(yunchao.he@intel.com): recompute copy regions for special cases for 3D textures, + // and return the revised copy regions. + return copySubresource; + } }} // namespace dawn_native::d3d12 diff --git a/src/dawn_native/d3d12/TextureCopySplitter.h b/src/dawn_native/d3d12/TextureCopySplitter.h index 89c31d071a..999a13cf11 100644 --- a/src/dawn_native/d3d12/TextureCopySplitter.h +++ b/src/dawn_native/d3d12/TextureCopySplitter.h @@ -31,6 +31,7 @@ namespace dawn_native { namespace d3d12 { static constexpr unsigned int kMaxTextureCopyRegions = 2; struct CopyInfo { + uint64_t alignedOffset = 0; Origin3D textureOffset; Origin3D bufferOffset; Extent3D bufferSize; @@ -38,7 +39,6 @@ namespace dawn_native { namespace d3d12 { Extent3D copySize; }; - uint64_t offset = 0; uint32_t count = 0; std::array copies; }; @@ -49,20 +49,44 @@ namespace dawn_native { namespace d3d12 { std::array copySubresources; }; - TextureCopySubresource ComputeTextureCopySubresource(Origin3D origin, - Extent3D copySize, - const TexelBlockInfo& blockInfo, - uint64_t offset, - uint32_t bytesPerRow, - uint32_t rowsPerImage); + // This function is shared by 2D and 3D texture copy splitter. But it only knows how to handle + // 2D non-arrayed textures correctly, and just forwards "copySize.depthOrArrayLayers". See + // details in Compute{2D|3D}TextureCopySplits about how we generate copy regions for 2D array + // and 3D textures based on this function. + // The resulting copies triggered by API like CopyTextureRegion are equivalent to the copy + // regions defines by the arguments of TextureCopySubresource returned by this function and its + // counterparts. These arguments should strictly conform to particular invariants. Otherwise, + // D3D12 driver may report validation errors when we call CopyTextureRegion. Some important + // invariants are listed below. For more details + // of these invariants, see src/tests/unittests/d3d12/CopySplitTests.cpp. + // - Inside each copy region, its buffer offset plus copy size should be less than its buffer + // size. + // - each region has an offset (aka alignedOffset) aligned to + // D3D12_TEXTURE_DATA_PLACEMENT_ALIGNMENT + // - If there are multiple copy regions, each copy region should not overlap with the others. + // - Copy region(s) combined should exactly be equivalent to the texture region to be copied. + // - Every pixel accessed by every copy region should not be out of the bound of the copied + // texture and buffer. + TextureCopySubresource Compute2DTextureCopySubresource(Origin3D origin, + Extent3D copySize, + const TexelBlockInfo& blockInfo, + uint64_t offset, + uint32_t bytesPerRow, + uint32_t rowsPerImage); - TextureCopySplits ComputeTextureCopySplits(Origin3D origin, - Extent3D copySize, - const TexelBlockInfo& blockInfo, - uint64_t offset, - uint32_t bytesPerRow, - uint32_t rowsPerImage, - bool is3DTexture = false); + TextureCopySplits Compute2DTextureCopySplits(Origin3D origin, + Extent3D copySize, + const TexelBlockInfo& blockInfo, + uint64_t offset, + uint32_t bytesPerRow, + uint32_t rowsPerImage); + + TextureCopySubresource Compute3DTextureCopySplits(Origin3D origin, + Extent3D copySize, + const TexelBlockInfo& blockInfo, + uint64_t offset, + uint32_t bytesPerRow, + uint32_t rowsPerImage); }} // namespace dawn_native::d3d12 #endif // DAWNNATIVE_D3D12_TEXTURECOPYSPLITTER_H_ diff --git a/src/dawn_native/d3d12/TextureD3D12.cpp b/src/dawn_native/d3d12/TextureD3D12.cpp index ac7c396745..82b5da4c7d 100644 --- a/src/dawn_native/d3d12/TextureD3D12.cpp +++ b/src/dawn_native/d3d12/TextureD3D12.cpp @@ -984,7 +984,7 @@ namespace dawn_native { namespace d3d12 { Extent3D copySize = GetMipLevelPhysicalSize(level); uint32_t rowsPerImage = copySize.height / blockInfo.height; - TextureCopySubresource copySplit = ComputeTextureCopySubresource( + TextureCopySubresource copySplit = Compute2DTextureCopySubresource( {0, 0, 0}, copySize, blockInfo, uploadHandle.startOffset, bytesPerRow, rowsPerImage); diff --git a/src/dawn_native/d3d12/UtilsD3D12.cpp b/src/dawn_native/d3d12/UtilsD3D12.cpp index 98e9785be9..b52dc0ba22 100644 --- a/src/dawn_native/d3d12/UtilsD3D12.cpp +++ b/src/dawn_native/d3d12/UtilsD3D12.cpp @@ -155,13 +155,12 @@ namespace dawn_native { namespace d3d12 { const D3D12_TEXTURE_COPY_LOCATION textureLocation = ComputeTextureCopyLocationForTexture(texture, textureMiplevel, textureLayer, aspect); - const uint64_t offsetBytes = baseCopySplit.offset + baseOffset; - for (uint32_t i = 0; i < baseCopySplit.count; ++i) { const TextureCopySubresource::CopyInfo& info = baseCopySplit.copies[i]; // TODO(jiawei.shao@intel.com): pre-compute bufferLocation and sourceRegion as // members in TextureCopySubresource::CopyInfo. + const uint64_t offsetBytes = info.alignedOffset + baseOffset; const D3D12_TEXTURE_COPY_LOCATION bufferLocation = ComputeBufferLocationForCopyTextureRegion(texture, bufferResource, info.bufferSize, offsetBytes, bufferBytesPerRow, aspect); @@ -184,38 +183,38 @@ namespace dawn_native { namespace d3d12 { Texture* texture, Aspect aspect) { ASSERT(HasOneBit(aspect)); - // See comments in ComputeTextureCopySplits() for more details. + // See comments in Compute2DTextureCopySplits() for more details. const TexelBlockInfo& blockInfo = texture->GetFormat().GetAspectInfo(aspect).block; - const TextureCopySplits copySplits = ComputeTextureCopySplits( + const TextureCopySplits copySplits = Compute2DTextureCopySplits( textureCopy.origin, copySize, blockInfo, offset, bytesPerRow, rowsPerImage); - const uint64_t bytesPerSlice = bytesPerRow * rowsPerImage; + const uint64_t bytesPerLayer = bytesPerRow * rowsPerImage; - // copySplits.copySubresources[1] is always calculated for the second copy slice with - // extra "bytesPerSlice" copy offset compared with the first copy slice. So - // here we use an array bufferOffsetsForNextSlice to record the extra offsets - // for each copy slice: bufferOffsetsForNextSlice[0] is the extra offset for - // the next copy slice that uses copySplits.copySubresources[0], and - // bufferOffsetsForNextSlice[1] is the extra offset for the next copy slice + // copySplits.copySubresources[1] is always calculated for the second copy layer with + // extra "bytesPerLayer" copy offset compared with the first copy layer. So + // here we use an array bufferOffsetsForNextLayer to record the extra offsets + // for each copy layer: bufferOffsetsForNextLayer[0] is the extra offset for + // the next copy layer that uses copySplits.copySubresources[0], and + // bufferOffsetsForNextLayer[1] is the extra offset for the next copy layer // that uses copySplits.copySubresources[1]. std::array - bufferOffsetsForNextSlice = {{0u, 0u}}; + bufferOffsetsForNextLayer = {{0u, 0u}}; for (uint32_t copyLayer = 0; copyLayer < copySize.depthOrArrayLayers; ++copyLayer) { const uint32_t splitIndex = copyLayer % copySplits.copySubresources.size(); const TextureCopySubresource& copySplitPerLayerBase = copySplits.copySubresources[splitIndex]; - const uint64_t bufferOffsetForNextSlice = bufferOffsetsForNextSlice[splitIndex]; + const uint64_t bufferOffsetForNextLayer = bufferOffsetsForNextLayer[splitIndex]; const uint32_t copyTextureLayer = copyLayer + textureCopy.origin.z; RecordCopyBufferToTextureFromTextureCopySplit( commandContext->GetCommandList(), copySplitPerLayerBase, bufferResource, - bufferOffsetForNextSlice, bytesPerRow, texture, textureCopy.mipLevel, + bufferOffsetForNextLayer, bytesPerRow, texture, textureCopy.mipLevel, copyTextureLayer, aspect); - bufferOffsetsForNextSlice[splitIndex] += - bytesPerSlice * copySplits.copySubresources.size(); + bufferOffsetsForNextLayer[splitIndex] += + bytesPerLayer * copySplits.copySubresources.size(); } } @@ -229,14 +228,14 @@ namespace dawn_native { namespace d3d12 { Texture* texture, Aspect aspect) { ASSERT(HasOneBit(aspect)); - // See comments in ComputeTextureCopySplits() for more details. + // See comments in Compute3DTextureCopySplits() for more details. const TexelBlockInfo& blockInfo = texture->GetFormat().GetAspectInfo(aspect).block; - const TextureCopySplits copySplits = ComputeTextureCopySplits( - textureCopy.origin, copySize, blockInfo, offset, bytesPerRow, rowsPerImage, true); + const TextureCopySubresource copyRegions = Compute3DTextureCopySplits( + textureCopy.origin, copySize, blockInfo, offset, bytesPerRow, rowsPerImage); - RecordCopyBufferToTextureFromTextureCopySplit( - commandContext->GetCommandList(), copySplits.copySubresources[0], bufferResource, 0, - bytesPerRow, texture, textureCopy.mipLevel, 0, aspect); + RecordCopyBufferToTextureFromTextureCopySplit(commandContext->GetCommandList(), copyRegions, + bufferResource, 0, bytesPerRow, texture, + textureCopy.mipLevel, 0, aspect); } void RecordCopyBufferToTexture(CommandRecordingContext* commandContext, @@ -274,16 +273,15 @@ namespace dawn_native { namespace d3d12 { const D3D12_TEXTURE_COPY_LOCATION textureLocation = ComputeTextureCopyLocationForTexture(texture, textureMiplevel, textureLayer, aspect); - const uint64_t offset = baseCopySplit.offset + baseOffset; - for (uint32_t i = 0; i < baseCopySplit.count; ++i) { const TextureCopySubresource::CopyInfo& info = baseCopySplit.copies[i]; // TODO(jiawei.shao@intel.com): pre-compute bufferLocation and sourceRegion as // members in TextureCopySubresource::CopyInfo. + const uint64_t offsetBytes = info.alignedOffset + baseOffset; const D3D12_TEXTURE_COPY_LOCATION bufferLocation = ComputeBufferLocationForCopyTextureRegion(texture, buffer->GetD3D12Resource(), - info.bufferSize, offset, + info.bufferSize, offsetBytes, bufferBytesPerRow, aspect); const D3D12_BOX sourceRegion = ComputeD3D12BoxFromOffsetAndSize(info.textureOffset, info.copySize); @@ -304,37 +302,37 @@ namespace dawn_native { namespace d3d12 { const TexelBlockInfo& blockInfo = texture->GetFormat().GetAspectInfo(textureCopy.aspect).block; - // See comments around ComputeTextureCopySplits() for more details. + // See comments around Compute2DTextureCopySplits() for more details. const TextureCopySplits copySplits = - ComputeTextureCopySplits(textureCopy.origin, copySize, blockInfo, bufferCopy.offset, - bufferCopy.bytesPerRow, bufferCopy.rowsPerImage); + Compute2DTextureCopySplits(textureCopy.origin, copySize, blockInfo, bufferCopy.offset, + bufferCopy.bytesPerRow, bufferCopy.rowsPerImage); - const uint64_t bytesPerSlice = bufferCopy.bytesPerRow * bufferCopy.rowsPerImage; + const uint64_t bytesPerLayer = bufferCopy.bytesPerRow * bufferCopy.rowsPerImage; - // copySplits.copySubresources[1] is always calculated for the second copy slice with - // extra "bytesPerSlice" copy offset compared with the first copy slice. So - // here we use an array bufferOffsetsForNextSlice to record the extra offsets - // for each copy slice: bufferOffsetsForNextSlice[0] is the extra offset for - // the next copy slice that uses copySplits.copySubresources[0], and - // bufferOffsetsForNextSlice[1] is the extra offset for the next copy slice + // copySplits.copySubresources[1] is always calculated for the second copy layer with + // extra "bytesPerLayer" copy offset compared with the first copy layer. So + // here we use an array bufferOffsetsForNextLayer to record the extra offsets + // for each copy layer: bufferOffsetsForNextLayer[0] is the extra offset for + // the next copy layer that uses copySplits.copySubresources[0], and + // bufferOffsetsForNextLayer[1] is the extra offset for the next copy layer // that uses copySplits.copySubresources[1]. std::array - bufferOffsetsForNextSlice = {{0u, 0u}}; + bufferOffsetsForNextLayer = {{0u, 0u}}; for (uint32_t copyLayer = 0; copyLayer < copySize.depthOrArrayLayers; ++copyLayer) { const uint32_t splitIndex = copyLayer % copySplits.copySubresources.size(); const TextureCopySubresource& copySplitPerLayerBase = copySplits.copySubresources[splitIndex]; - const uint64_t bufferOffsetForNextSlice = bufferOffsetsForNextSlice[splitIndex]; + const uint64_t bufferOffsetForNextLayer = bufferOffsetsForNextLayer[splitIndex]; const uint32_t copyTextureLayer = copyLayer + textureCopy.origin.z; RecordCopyTextureToBufferFromTextureCopySplit( - commandList, copySplitPerLayerBase, buffer, bufferOffsetForNextSlice, + commandList, copySplitPerLayerBase, buffer, bufferOffsetForNextLayer, bufferCopy.bytesPerRow, texture, textureCopy.mipLevel, copyTextureLayer, textureCopy.aspect); - bufferOffsetsForNextSlice[splitIndex] += - bytesPerSlice * copySplits.copySubresources.size(); + bufferOffsetsForNextLayer[splitIndex] += + bytesPerLayer * copySplits.copySubresources.size(); } } @@ -348,13 +346,13 @@ namespace dawn_native { namespace d3d12 { const TexelBlockInfo& blockInfo = texture->GetFormat().GetAspectInfo(textureCopy.aspect).block; - // See comments around ComputeTextureCopySplits() for more details. - const TextureCopySplits copySplits = - ComputeTextureCopySplits(textureCopy.origin, copySize, blockInfo, bufferCopy.offset, - bufferCopy.bytesPerRow, bufferCopy.rowsPerImage, true); + // See comments around Compute3DTextureCopySplits() for more details. + const TextureCopySubresource copyRegions = + Compute3DTextureCopySplits(textureCopy.origin, copySize, blockInfo, bufferCopy.offset, + bufferCopy.bytesPerRow, bufferCopy.rowsPerImage); - RecordCopyTextureToBufferFromTextureCopySplit(commandList, copySplits.copySubresources[0], - buffer, 0, bufferCopy.bytesPerRow, texture, + RecordCopyTextureToBufferFromTextureCopySplit(commandList, copyRegions, buffer, 0, + bufferCopy.bytesPerRow, texture, textureCopy.mipLevel, 0, textureCopy.aspect); } diff --git a/src/tests/unittests/d3d12/CopySplitTests.cpp b/src/tests/unittests/d3d12/CopySplitTests.cpp index cd71be9127..a1dd2f181f 100644 --- a/src/tests/unittests/d3d12/CopySplitTests.cpp +++ b/src/tests/unittests/d3d12/CopySplitTests.cpp @@ -56,8 +56,11 @@ namespace { // Check that the offset is aligned void ValidateOffset(const TextureCopySubresource& copySplit) { - ASSERT_TRUE(Align(copySplit.offset, D3D12_TEXTURE_DATA_PLACEMENT_ALIGNMENT) == - copySplit.offset); + for (uint32_t i = 0; i < copySplit.count; ++i) { + ASSERT_TRUE( + Align(copySplit.copies[i].alignedOffset, D3D12_TEXTURE_DATA_PLACEMENT_ALIGNMENT) == + copySplit.copies[i].alignedOffset); + } } bool RangesOverlap(uint32_t minA, uint32_t maxA, uint32_t minB, uint32_t maxB) { @@ -142,7 +145,7 @@ namespace { uint32_t slicePitchInTexels = bytesPerRowInTexels * (bufferSpec.rowsPerImage / textureSpec.blockHeight); uint32_t absoluteTexelOffset = - copySplit.offset / textureSpec.texelBlockSizeInBytes * texelsPerBlock + + copy.alignedOffset / textureSpec.texelBlockSizeInBytes * texelsPerBlock + copy.bufferOffset.x / textureSpec.blockWidth * texelsPerBlock + copy.bufferOffset.y / textureSpec.blockHeight * bytesPerRowInTexels; @@ -302,7 +305,7 @@ class CopySplitTest : public testing::Test { blockInfo.width = textureSpec.blockWidth; blockInfo.height = textureSpec.blockHeight; blockInfo.byteSize = textureSpec.texelBlockSizeInBytes; - TextureCopySubresource copySplit = ComputeTextureCopySubresource( + TextureCopySubresource copySplit = Compute2DTextureCopySubresource( {textureSpec.x, textureSpec.y, textureSpec.z}, {textureSpec.width, textureSpec.height, textureSpec.depth}, blockInfo, bufferSpec.offset, bufferSpec.bytesPerRow, bufferSpec.rowsPerImage);