Skip to content

Commit 552bb94

Browse files
committed
Refactor api/operations/resource_init
Issue #4181 Issue #4178
1 parent 78dc3b8 commit 552bb94

File tree

7 files changed

+83
-64
lines changed

7 files changed

+83
-64
lines changed

src/webgpu/api/operation/resource_init/buffer.spec.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { makeTestGroup } from '../../../../common/framework/test_group.js';
22
import { unreachable } from '../../../../common/util/util.js';
33
import { GPUConst } from '../../../constants.js';
4-
import { GPUTest } from '../../../gpu_test.js';
4+
import { AllFeaturesMaxLimitsGPUTest } from '../../../gpu_test.js';
55
import { getTextureCopyLayout } from '../../../util/texture/layout.js';
66
import { PerTexelComponent } from '../../../util/texture/texel_data.js';
77

@@ -21,7 +21,7 @@ const kBufferUsagesForMappedAtCreationTests = [
2121
GPUConst.BufferUsage.COPY_SRC,
2222
];
2323

24-
class F extends GPUTest {
24+
class F extends AllFeaturesMaxLimitsGPUTest {
2525
GetBufferUsageFromMapMode(mapMode: GPUMapModeFlags): number {
2626
switch (mapMode) {
2727
case GPUMapMode.READ:

src/webgpu/api/operation/resource_init/check_texture/by_copy.ts

+1-4
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
1-
import { assert } from '../../../../../common/util/util.js';
2-
import { kTextureFormatInfo, EncodableTextureFormat } from '../../../../format_info.js';
1+
import { EncodableTextureFormat } from '../../../../format_info.js';
32
import { virtualMipSize } from '../../../../util/texture/base.js';
43

54
import { CheckContents } from './texture_zero_init_test.js';
@@ -12,7 +11,6 @@ export const checkContentsByBufferCopy: CheckContents = (
1211
subresourceRange
1312
) => {
1413
for (const { level: mipLevel, layer } of subresourceRange.each()) {
15-
assert(params.format in kTextureFormatInfo);
1614
const format = params.format as EncodableTextureFormat;
1715

1816
t.expectSingleColor(texture, format, {
@@ -33,7 +31,6 @@ export const checkContentsByTextureCopy: CheckContents = (
3331
subresourceRange
3432
) => {
3533
for (const { level, layer } of subresourceRange.each()) {
36-
assert(params.format in kTextureFormatInfo);
3734
const format = params.format as EncodableTextureFormat;
3835

3936
const [width, height, depth] = virtualMipSize(

src/webgpu/api/operation/resource_init/check_texture/by_ds_test.ts

+5-7
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import { assert } from '../../../../../common/util/util.js';
2-
import { kTextureFormatInfo } from '../../../../format_info.js';
2+
import { isDepthTextureFormat, isStencilTextureFormat } from '../../../../format_info.js';
33
import { GPUTest } from '../../../../gpu_test.js';
44
import { virtualMipSize } from '../../../../util/texture/base.js';
55

@@ -106,8 +106,6 @@ const checkContents: (type: 'depth' | 'stencil', ...args: Parameters<CheckConten
106106
state,
107107
subresourceRange
108108
) => {
109-
const formatInfo = kTextureFormatInfo[params.format];
110-
111109
assert(params.dimension === '2d');
112110
for (const viewDescriptor of t.generateTextureViewDescriptorsForRendering(
113111
'all',
@@ -153,10 +151,10 @@ const checkContents: (type: 'depth' | 'stencil', ...args: Parameters<CheckConten
153151
],
154152
depthStencilAttachment: {
155153
view: texture.createView(viewDescriptor),
156-
depthLoadOp: formatInfo.depth ? 'load' : undefined,
157-
depthStoreOp: formatInfo.depth ? 'store' : undefined,
158-
stencilLoadOp: formatInfo.stencil ? 'load' : undefined,
159-
stencilStoreOp: formatInfo.stencil ? 'store' : undefined,
154+
depthLoadOp: isDepthTextureFormat(params.format) ? 'load' : undefined,
155+
depthStoreOp: isDepthTextureFormat(params.format) ? 'store' : undefined,
156+
stencilLoadOp: isStencilTextureFormat(params.format) ? 'load' : undefined,
157+
stencilStoreOp: isStencilTextureFormat(params.format) ? 'store' : undefined,
160158
},
161159
});
162160

src/webgpu/api/operation/resource_init/check_texture/by_sampling.ts

+1-2
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import { assert, unreachable } from '../../../../../common/util/util.js';
2-
import { kTextureFormatInfo, EncodableTextureFormat } from '../../../../format_info.js';
2+
import { EncodableTextureFormat } from '../../../../format_info.js';
33
import { virtualMipSize } from '../../../../util/texture/base.js';
44
import {
55
kTexelRepresentationInfo,
@@ -16,7 +16,6 @@ export const checkContentsBySampling: CheckContents = (
1616
state,
1717
subresourceRange
1818
) => {
19-
assert(params.format in kTextureFormatInfo);
2019
const format = params.format as EncodableTextureFormat;
2120
const rep = kTexelRepresentationInfo[format];
2221

src/webgpu/api/operation/resource_init/check_texture/texture_zero_init_test.ts

+60-40
Original file line numberDiff line numberDiff line change
@@ -7,13 +7,22 @@ import { assert, unreachable } from '../../../../../common/util/util.js';
77
import { kTextureAspects, kTextureDimensions } from '../../../../capability_info.js';
88
import { GPUConst } from '../../../../constants.js';
99
import {
10-
kTextureFormatInfo,
1110
kUncompressedTextureFormats,
1211
textureDimensionAndFormatCompatible,
1312
UncompressedTextureFormat,
1413
EncodableTextureFormat,
14+
isColorTextureFormat,
15+
isDepthTextureFormat,
16+
isStencilTextureFormat,
17+
isDepthOrStencilTextureFormat,
18+
isTextureFormatPossiblyUsableAsRenderAttachment,
19+
isTextureFormatPossiblyStorageReadable,
20+
isTextureFormatPossiblyMultisampled,
21+
canCopyAllAspectsOfTextureFormat,
22+
isTextureFormatColorRenderable,
23+
isTextureFormatPossiblyUsableAsColorRenderAttachment,
1524
} from '../../../../format_info.js';
16-
import { GPUTest, GPUTestSubcaseBatchState } from '../../../../gpu_test.js';
25+
import { AllFeaturesMaxLimitsGPUTest, GPUTestSubcaseBatchState } from '../../../../gpu_test.js';
1726
import { virtualMipSize } from '../../../../util/texture/base.js';
1827
import { createTextureUploadBuffer } from '../../../../util/texture/layout.js';
1928
import { BeginEndRange, SubresourceRange } from '../../../../util/texture/subresource.js';
@@ -115,14 +124,6 @@ const initializedStateAsStencil = {
115124
[InitializedState.Canary]: 42,
116125
};
117126

118-
function allAspectsCopyDst(info: (typeof kTextureFormatInfo)[UncompressedTextureFormat]) {
119-
return (
120-
(!info.color || info.color.copyDst) &&
121-
(!info.depth || info.depth.copyDst) &&
122-
(!info.stencil || info.stencil.copyDst)
123-
);
124-
}
125-
126127
export function getRequiredTextureUsage(
127128
format: UncompressedTextureFormat,
128129
sampleCount: number,
@@ -167,18 +168,22 @@ export function getRequiredTextureUsage(
167168
usage |= GPUConst.TextureUsage.RENDER_ATTACHMENT;
168169
}
169170

170-
const info = kTextureFormatInfo[format];
171-
if (!allAspectsCopyDst(info)) {
171+
if (!canCopyAllAspectsOfTextureFormat(format)) {
172172
// Copies are not possible. We need OutputAttachment to initialize
173173
// canary data.
174-
if (info.color) assert(!!info.colorRender, 'not implemented for non-renderable color');
174+
if (isColorTextureFormat(format)) {
175+
assert(
176+
isTextureFormatPossiblyUsableAsColorRenderAttachment(format),
177+
'not implemented for non-renderable color'
178+
);
179+
}
175180
usage |= GPUConst.TextureUsage.RENDER_ATTACHMENT;
176181
}
177182

178183
return usage;
179184
}
180185

181-
export class TextureZeroInitTest extends GPUTest {
186+
export class TextureZeroInitTest extends AllFeaturesMaxLimitsGPUTest {
182187
readonly stateToTexelComponents: { [k in InitializedState]: PerTexelComponent<number> };
183188

184189
private p: TextureZeroParams;
@@ -302,7 +307,7 @@ export class TextureZeroInitTest extends GPUTest {
302307
'all',
303308
subresourceRange
304309
)) {
305-
if (kTextureFormatInfo[this.p.format].color) {
310+
if (isColorTextureFormat(this.p.format)) {
306311
commandEncoder
307312
.beginRenderPass({
308313
colorAttachments: [
@@ -319,12 +324,12 @@ export class TextureZeroInitTest extends GPUTest {
319324
const depthStencilAttachment: GPURenderPassDepthStencilAttachment = {
320325
view: texture.createView(viewDescriptor),
321326
};
322-
if (kTextureFormatInfo[this.p.format].depth) {
327+
if (isDepthTextureFormat(this.p.format)) {
323328
depthStencilAttachment.depthClearValue = initializedStateAsDepth[state];
324329
depthStencilAttachment.depthLoadOp = 'clear';
325330
depthStencilAttachment.depthStoreOp = 'store';
326331
}
327-
if (kTextureFormatInfo[this.p.format].stencil) {
332+
if (isStencilTextureFormat(this.p.format)) {
328333
depthStencilAttachment.stencilClearValue = initializedStateAsStencil[state];
329334
depthStencilAttachment.stencilLoadOp = 'clear';
330335
depthStencilAttachment.stencilStoreOp = 'store';
@@ -347,7 +352,6 @@ export class TextureZeroInitTest extends GPUTest {
347352
state: InitializedState,
348353
subresourceRange: SubresourceRange
349354
): void {
350-
assert(this.p.format in kTextureFormatInfo);
351355
const format = this.p.format as EncodableTextureFormat;
352356

353357
const firstSubresource = subresourceRange.each().next().value;
@@ -394,11 +398,15 @@ export class TextureZeroInitTest extends GPUTest {
394398
state: InitializedState,
395399
subresourceRange: SubresourceRange
396400
): void {
397-
const info = kTextureFormatInfo[this.p.format];
398-
if (this.p.sampleCount > 1 || !allAspectsCopyDst(info)) {
401+
if (this.p.sampleCount > 1 || !canCopyAllAspectsOfTextureFormat(this.p.format)) {
399402
// Copies to multisampled textures not yet specified.
400403
// Use a storeOp for now.
401-
if (info.color) assert(!!info.colorRender, 'not implemented for non-renderable color');
404+
if (isColorTextureFormat(this.p.format)) {
405+
assert(
406+
isTextureFormatColorRenderable(this.device, this.p.format),
407+
'not implemented for non-renderable color'
408+
);
409+
}
402410
this.initializeWithStoreOp(state, texture, subresourceRange);
403411
} else {
404412
this.initializeWithCopy(texture, state, subresourceRange);
@@ -410,7 +418,7 @@ export class TextureZeroInitTest extends GPUTest {
410418
commandEncoder.pushDebugGroup('discardTexture');
411419

412420
for (const desc of this.generateTextureViewDescriptorsForRendering('all', subresourceRange)) {
413-
if (kTextureFormatInfo[this.p.format].color) {
421+
if (isColorTextureFormat(this.p.format)) {
414422
commandEncoder
415423
.beginRenderPass({
416424
colorAttachments: [
@@ -426,11 +434,11 @@ export class TextureZeroInitTest extends GPUTest {
426434
const depthStencilAttachment: GPURenderPassDepthStencilAttachment = {
427435
view: texture.createView(desc),
428436
};
429-
if (kTextureFormatInfo[this.p.format].depth) {
437+
if (isDepthTextureFormat(this.p.format)) {
430438
depthStencilAttachment.depthLoadOp = 'load';
431439
depthStencilAttachment.depthStoreOp = 'discard';
432440
}
433-
if (kTextureFormatInfo[this.p.format].stencil) {
441+
if (isStencilTextureFormat(this.p.format)) {
434442
depthStencilAttachment.stencilLoadOp = 'load';
435443
depthStencilAttachment.stencilStoreOp = 'discard';
436444
}
@@ -446,6 +454,19 @@ export class TextureZeroInitTest extends GPUTest {
446454
commandEncoder.popDebugGroup();
447455
this.queue.submit([commandEncoder.finish()]);
448456
}
457+
458+
skipIfTextureFormatNotSupportedForTest(params: TextureZeroParams) {
459+
const { format, sampleCount, uninitializeMethod, readMethod } = params;
460+
this.skipIfTextureFormatNotSupported(format);
461+
462+
const usage = getRequiredTextureUsage(format, sampleCount, uninitializeMethod, readMethod);
463+
464+
this.skipIfTextureFormatDoesNotSupportUsage(usage, format);
465+
466+
if (sampleCount > 1) {
467+
this.skipIfTextureFormatNotMultisampled(format);
468+
}
469+
}
449470
}
450471

451472
export const kTestParams = kUnitCaseParamsBuilder
@@ -463,16 +484,18 @@ export const kTestParams = kUnitCaseParamsBuilder
463484
.beginSubcases()
464485
.combine('aspect', kTextureAspects)
465486
.unless(({ readMethod, format, aspect }) => {
466-
const info = kTextureFormatInfo[format];
487+
const hasColor = isColorTextureFormat(format);
488+
const hasDepth = isDepthTextureFormat(format);
489+
const hasStencil = isStencilTextureFormat(format);
467490
return (
468-
(readMethod === ReadMethod.DepthTest && (!info.depth || aspect === 'stencil-only')) ||
469-
(readMethod === ReadMethod.StencilTest && (!info.stencil || aspect === 'depth-only')) ||
470-
(readMethod === ReadMethod.ColorBlending && !info.color) ||
491+
(readMethod === ReadMethod.DepthTest && (!hasDepth || aspect === 'stencil-only')) ||
492+
(readMethod === ReadMethod.StencilTest && (!hasStencil || aspect === 'depth-only')) ||
493+
(readMethod === ReadMethod.ColorBlending && !hasColor) ||
471494
// [1]: Test with depth/stencil sampling
472-
(readMethod === ReadMethod.Sample && (!!info.depth || !!info.stencil)) ||
473-
(aspect === 'depth-only' && !info.depth) ||
474-
(aspect === 'stencil-only' && !info.stencil) ||
475-
(aspect === 'all' && !!info.depth && !!info.stencil) ||
495+
(readMethod === ReadMethod.Sample && (hasDepth || hasStencil)) ||
496+
(aspect === 'depth-only' && !hasDepth) ||
497+
(aspect === 'stencil-only' && !hasStencil) ||
498+
(aspect === 'all' && !!hasDepth && !!hasStencil) ||
476499
// Cannot copy from a packed depth format.
477500
// [2]: Test copying out of the stencil aspect.
478501
((readMethod === ReadMethod.CopyToBuffer || readMethod === ReadMethod.CopyToTexture) &&
@@ -493,12 +516,10 @@ export const kTestParams = kUnitCaseParamsBuilder
493516
.unless(({ sampleCount, mipLevelCount }) => sampleCount > 1 && mipLevelCount > 1)
494517
.combine('uninitializeMethod', kUninitializeMethods)
495518
.unless(({ dimension, readMethod, uninitializeMethod, format, sampleCount }) => {
496-
const formatInfo = kTextureFormatInfo[format];
497519
return (
498520
dimension !== '2d' &&
499521
(sampleCount > 1 ||
500-
!!formatInfo.depth ||
501-
!!formatInfo.stencil ||
522+
isDepthOrStencilTextureFormat(format) ||
502523
readMethod === ReadMethod.DepthTest ||
503524
readMethod === ReadMethod.StencilTest ||
504525
readMethod === ReadMethod.ColorBlending ||
@@ -521,14 +542,13 @@ export const kTestParams = kUnitCaseParamsBuilder
521542
.unless(({ sampleCount, layerCount }) => sampleCount > 1 && layerCount > 1)
522543
.unless(({ format, sampleCount, uninitializeMethod, readMethod }) => {
523544
const usage = getRequiredTextureUsage(format, sampleCount, uninitializeMethod, readMethod);
524-
const info = kTextureFormatInfo[format];
525545

526546
return (
527547
((usage & GPUConst.TextureUsage.RENDER_ATTACHMENT) !== 0 &&
528-
info.color &&
529-
!info.colorRender) ||
530-
((usage & GPUConst.TextureUsage.STORAGE_BINDING) !== 0 && !info.color?.storage) ||
531-
(sampleCount > 1 && !info.multisample)
548+
!isTextureFormatPossiblyUsableAsRenderAttachment(format)) ||
549+
((usage & GPUConst.TextureUsage.STORAGE_BINDING) !== 0 &&
550+
!isTextureFormatPossiblyStorageReadable(format)) ||
551+
(sampleCount > 1 && !isTextureFormatPossiblyMultisampled(format))
532552
);
533553
})
534554
.combine('nonPowerOfTwo', [false, true])

src/webgpu/api/operation/resource_init/texture_zero.spec.ts

+1-9
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@ TODO:
99

1010
import { makeTestGroup } from '../../../../common/framework/test_group.js';
1111
import { unreachable } from '../../../../common/util/util.js';
12-
import { isMultisampledTextureFormatDeprecated, kTextureFormatInfo } from '../../../format_info.js';
1312

1413
import { checkContentsByBufferCopy, checkContentsByTextureCopy } from './check_texture/by_copy.js';
1514
import {
@@ -41,15 +40,8 @@ export const g = makeTestGroup(TextureZeroInitTest);
4140

4241
g.test('uninitialized_texture_is_zero')
4342
.params(kTestParams)
44-
.beforeAllSubcases(t => {
45-
t.skipIfTextureFormatNotSupportedDeprecated(t.params.format);
46-
t.selectDeviceOrSkipTestCase(kTextureFormatInfo[t.params.format].feature);
47-
})
4843
.fn(t => {
49-
t.skipIf(
50-
t.params.sampleCount > 1 &&
51-
!isMultisampledTextureFormatDeprecated(t.params.format, t.isCompatibility)
52-
);
44+
t.skipIfTextureFormatNotSupportedForTest(t.params);
5345

5446
const usage = getRequiredTextureUsage(
5547
t.params.format,

src/webgpu/format_info.ts

+13
Original file line numberDiff line numberDiff line change
@@ -1895,10 +1895,23 @@ export function filterFormatsByFeature<T>(
18951895
return formats.filter(f => f === undefined || kTextureFormatInfo[f].feature === feature);
18961896
}
18971897

1898+
export function canCopyAllAspectsOfTextureFormat(format: GPUTextureFormat) {
1899+
const info = kTextureFormatInfo[format];
1900+
return (
1901+
(!info.color || info.color.copyDst) &&
1902+
(!info.depth || info.depth.copyDst) &&
1903+
(!info.stencil || info.stencil.copyDst)
1904+
);
1905+
}
1906+
18981907
export function isCompressedTextureFormat(format: GPUTextureFormat) {
18991908
return format in kCompressedTextureFormatInfo;
19001909
}
19011910

1911+
export function isColorTextureFormat(format: GPUTextureFormat) {
1912+
return !!kTextureFormatInfo[format].color;
1913+
}
1914+
19021915
export function isDepthTextureFormat(format: GPUTextureFormat) {
19031916
return !!kTextureFormatInfo[format].depth;
19041917
}

0 commit comments

Comments
 (0)