Change SubresourceRange to be hierarchical.

Initializing SubresourceRange with {x, y, z} type of constructor
was error prone because it was going from the smallest concept
to the larger one instead of being hierarchical.

This CL changes the order of the structure and more importantly
adds a constructor that's in hierarchical order and groups related
members together. For example:

  SubresourceRange range(Aspect::Color, {layerStart, layerCount}, {0, mipCount});

It also adds a rename of SingleMipAndLayer in hierarchical order as
SubresourceRange::Single and a helper that gives a full range as
SubresourceRange::Full (it will be used in follow-up CLs).

Bug: dawn:441

Change-Id: I8e71bae1129a96222f7779014575b24b31f5ef7a
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/35000
Reviewed-by: Corentin Wallez <cwallez@chromium.org>
Commit-Queue: Corentin Wallez <cwallez@chromium.org>
diff --git a/src/dawn_native/CommandBuffer.cpp b/src/dawn_native/CommandBuffer.cpp
index b9c4705..bde0c63 100644
--- a/src/dawn_native/CommandBuffer.cpp
+++ b/src/dawn_native/CommandBuffer.cpp
@@ -77,10 +77,9 @@
                                                    const Extent3D& copySize) {
         switch (copy.texture->GetDimension()) {
             case wgpu::TextureDimension::e2D:
-                return {copy.mipLevel, 1, copy.origin.z, copySize.depth, copy.aspect};
+                return {copy.aspect, {copy.origin.z, copySize.depth}, {copy.mipLevel, 1}};
             default:
                 UNREACHABLE();
-                return {};
         }
     }
 
diff --git a/src/dawn_native/DawnNative.cpp b/src/dawn_native/DawnNative.cpp
index 21343e6..35ed9be 100644
--- a/src/dawn_native/DawnNative.cpp
+++ b/src/dawn_native/DawnNative.cpp
@@ -180,18 +180,18 @@
         return deviceBase->GetDeprecationWarningCountForTesting();
     }
 
-    bool IsTextureSubresourceInitialized(WGPUTexture texture,
+    bool IsTextureSubresourceInitialized(WGPUTexture cTexture,
                                          uint32_t baseMipLevel,
                                          uint32_t levelCount,
                                          uint32_t baseArrayLayer,
                                          uint32_t layerCount,
-                                         WGPUTextureAspect aspect) {
-        dawn_native::TextureBase* textureBase =
-            reinterpret_cast<dawn_native::TextureBase*>(texture);
-        SubresourceRange range = {
-            baseMipLevel, levelCount, baseArrayLayer, layerCount,
-            ConvertAspect(textureBase->GetFormat(), static_cast<wgpu::TextureAspect>(aspect))};
-        return textureBase->IsSubresourceContentInitialized(range);
+                                         WGPUTextureAspect cAspect) {
+        dawn_native::TextureBase* texture = reinterpret_cast<dawn_native::TextureBase*>(cTexture);
+
+        Aspect aspect =
+            ConvertAspect(texture->GetFormat(), static_cast<wgpu::TextureAspect>(cAspect));
+        SubresourceRange range(aspect, {baseArrayLayer, layerCount}, {baseMipLevel, levelCount});
+        return texture->IsSubresourceContentInitialized(range);
     }
 
     std::vector<const char*> GetProcMapNamesForTestingInternal();
diff --git a/src/dawn_native/Subresource.cpp b/src/dawn_native/Subresource.cpp
index f3581e9..766cb1d 100644
--- a/src/dawn_native/Subresource.cpp
+++ b/src/dawn_native/Subresource.cpp
@@ -68,11 +68,40 @@
         }
     }
 
+    SubresourceRange::SubresourceRange(Aspect aspects,
+                                       FirstAndCountRange<uint32_t> arrayLayerParam,
+                                       FirstAndCountRange<uint32_t> mipLevelParams)
+        : aspects(aspects),
+          baseArrayLayer(arrayLayerParam.first),
+          layerCount(arrayLayerParam.count),
+          baseMipLevel(mipLevelParams.first),
+          levelCount(mipLevelParams.count) {
+    }
+
+    SubresourceRange::SubresourceRange()
+        : aspects(Aspect::None), baseArrayLayer(0), layerCount(0), baseMipLevel(0), levelCount(0) {
+    }
+
     // static
     SubresourceRange SubresourceRange::SingleMipAndLayer(uint32_t baseMipLevel,
                                                          uint32_t baseArrayLayer,
                                                          Aspect aspects) {
-        return {baseMipLevel, 1, baseArrayLayer, 1, aspects};
+        return {aspects, {baseArrayLayer, 1}, {baseMipLevel, 1}};
+    }
+
+    // static
+    SubresourceRange SubresourceRange::MakeSingle(Aspect aspect,
+                                                  uint32_t baseArrayLayer,
+                                                  uint32_t baseMipLevel) {
+        ASSERT(HasOneBit(aspect));
+        return {aspect, {baseArrayLayer, 1}, {baseMipLevel, 1}};
+    }
+
+    // static
+    SubresourceRange SubresourceRange::MakeFull(Aspect aspects,
+                                                uint32_t layerCount,
+                                                uint32_t levelCount) {
+        return {aspects, {0, layerCount}, {0, levelCount}};
     }
 
 }  // namespace dawn_native
diff --git a/src/dawn_native/Subresource.h b/src/dawn_native/Subresource.h
index b2f7d40..927f665 100644
--- a/src/dawn_native/Subresource.h
+++ b/src/dawn_native/Subresource.h
@@ -48,16 +48,33 @@
     // Aspect::None.
     Aspect TryConvertAspect(const Format& format, wgpu::TextureAspect aspect);
 
+    // Helper struct to make it clear that what the parameters of a range mean.
+    template <typename T>
+    struct FirstAndCountRange {
+        T first;
+        T count;
+    };
+
     struct SubresourceRange {
-        uint32_t baseMipLevel;
-        uint32_t levelCount;
+        SubresourceRange(Aspect aspects,
+                         FirstAndCountRange<uint32_t> arrayLayerParam,
+                         FirstAndCountRange<uint32_t> mipLevelParams);
+        SubresourceRange();
+
+        Aspect aspects;
         uint32_t baseArrayLayer;
         uint32_t layerCount;
-        Aspect aspects;
+        uint32_t baseMipLevel;
+        uint32_t levelCount;
 
         static SubresourceRange SingleMipAndLayer(uint32_t baseMipLevel,
                                                   uint32_t baseArrayLayer,
                                                   Aspect aspects);
+        static SubresourceRange MakeSingle(Aspect aspect,
+                                           uint32_t baseArrayLayer,
+                                           uint32_t baseMipLevel);
+
+        static SubresourceRange MakeFull(Aspect aspects, uint32_t layerCount, uint32_t levelCount);
     };
 
     // Helper function to use aspects as linear indices in arrays.
diff --git a/src/dawn_native/Texture.cpp b/src/dawn_native/Texture.cpp
index 7e62d73..cc345e3 100644
--- a/src/dawn_native/Texture.cpp
+++ b/src/dawn_native/Texture.cpp
@@ -421,7 +421,7 @@
     }
     SubresourceRange TextureBase::GetAllSubresources() const {
         ASSERT(!IsError());
-        return {0, mMipLevelCount, 0, GetArrayLayers(), mFormat.aspects};
+        return {mFormat.aspects, {0, GetArrayLayers()}, {0, mMipLevelCount}};
     }
     uint32_t TextureBase::GetSampleCount() const {
         ASSERT(!IsError());
@@ -577,8 +577,9 @@
           mTexture(texture),
           mFormat(GetDevice()->GetValidInternalFormat(descriptor->format)),
           mDimension(descriptor->dimension),
-          mRange({descriptor->baseMipLevel, descriptor->mipLevelCount, descriptor->baseArrayLayer,
-                  descriptor->arrayLayerCount, ConvertAspect(mFormat, descriptor->aspect)}) {
+          mRange({ConvertAspect(mFormat, descriptor->aspect),
+                  {descriptor->baseArrayLayer, descriptor->arrayLayerCount},
+                  {descriptor->baseMipLevel, descriptor->mipLevelCount}}) {
     }
 
     TextureViewBase::TextureViewBase(DeviceBase* device, ObjectBase::ErrorTag tag)