D3D12: Replace dst-alpha with one for formats without alpha

This patch replaces D3D12_BLEND_DEST_ALPHA with D3D12_BLEND_ONE
when the color target formats have no alpha-channel.

Using D3D12_BLEND_ONE is an optimization over
D3D12_BLEND_DEST_ALPHA as it means the GPU hardware doesn't
need to get destination pixel at all. As D3D SPED requires the
default value for missing components in an element format is
"0" for any component except A, which gets "1", using
D3D12_BLEND_DEST_ALPHA takes same effect with
D3D12_BLEND_ONE when the color target formats have no alpha
channel.

In addition, replacing D3D12_BLEND_DEST_ALPHA with
D3D12_BLEND_ONE also serves as a workaround against an Intel
driver issue about alpha blending.

Bug: dawn:1579
Change-Id: If79e4c8007b68dd35e142ba9cf8a4921e611890a
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/120120
Kokoro: Kokoro <noreply+kokoro@google.com>
Commit-Queue: Jiawei Shao <jiawei.shao@intel.com>
Reviewed-by: Austin Eng <enga@chromium.org>
This commit is contained in:
Jiawei Shao 2023-02-20 03:10:32 +00:00 committed by Dawn LUCI CQ
parent b5af23d588
commit e4f947637a
2 changed files with 15 additions and 3 deletions

View File

@ -234,11 +234,24 @@ uint8_t D3D12RenderTargetWriteMask(wgpu::ColorWriteMask writeMask) {
return static_cast<uint8_t>(writeMask);
}
D3D12_RENDER_TARGET_BLEND_DESC ComputeColorDesc(const ColorTargetState* state) {
D3D12_RENDER_TARGET_BLEND_DESC ComputeColorDesc(const DeviceBase* device,
const ColorTargetState* state) {
D3D12_RENDER_TARGET_BLEND_DESC blendDesc = {};
blendDesc.BlendEnable = state->blend != nullptr;
if (blendDesc.BlendEnable) {
blendDesc.SrcBlend = D3D12Blend(state->blend->color.srcFactor);
if (device->GetValidInternalFormat(state->format).componentCount < 4 &&
blendDesc.SrcBlend == D3D12_BLEND_DEST_ALPHA) {
// According to the D3D SPEC, the default value for missing components in an element
// format is "0" for any component except A, which gets "1". So here
// D3D12_BLEND_DEST_ALPHA should have same effect as D3D12_BLEND_ONE.
// Note that this replacement can be an optimization as using D3D12_BLEND_ONE means the
// GPU hardware no longer needs to get pixels from the destination texture. It can also
// be served as a workaround against an Intel driver issue about alpha blending (see
// http://crbug.com/dawn/1579 for more details).
blendDesc.SrcBlend = D3D12_BLEND_ONE;
}
blendDesc.DestBlend = D3D12Blend(state->blend->color.dstFactor);
blendDesc.BlendOp = D3D12BlendOperation(state->blend->color.operation);
blendDesc.SrcBlendAlpha = D3D12AlphaBlend(state->blend->alpha.srcFactor);
@ -419,7 +432,7 @@ MaybeError RenderPipeline::Initialize() {
descriptorD3D12.RTVFormats[static_cast<uint8_t>(i)] =
D3D12TextureFormat(GetColorAttachmentFormat(i));
descriptorD3D12.BlendState.RenderTarget[static_cast<uint8_t>(i)] =
ComputeColorDesc(GetColorTargetState(i));
ComputeColorDesc(device, GetColorTargetState(i));
}
ASSERT(highestColorAttachmentIndexPlusOne <= kMaxColorAttachmentsTyped);
descriptorD3D12.NumRenderTargets = static_cast<uint8_t>(highestColorAttachmentIndexPlusOne);

View File

@ -293,7 +293,6 @@ crbug.com/tint/1810 webgpu:shader,validation,parse,identifiers:* [ Failure ]
# untriaged failures
################################################################################
crbug.com/dawn/0000 [ dawn-backend-validation win10 ] webgpu:api,operation,render_pass,resolve:* [ Failure ]
crbug.com/dawn/0000 [ intel-gen-9 win10 ] webgpu:api,operation,render_pipeline,pipeline_output_targets:color,component_count,blend:format="rg8unorm" [ Failure ]
crbug.com/dawn/0000 [ monterey ] webgpu:web_platform,canvas,readbackFromWebGPUCanvas:drawTo2DCanvas:format="rgba8unorm";alphaMode="opaque";colorSpace="display-p3";webgpuCanvasType="offscreen";canvas2DType="offscreen" [ Failure ]
crbug.com/dawn/0000 [ monterey ] webgpu:web_platform,canvas,readbackFromWebGPUCanvas:drawTo2DCanvas:format="rgba8unorm";alphaMode="opaque";colorSpace="display-p3";webgpuCanvasType="offscreen";canvas2DType="onscreen" [ Failure ]
crbug.com/dawn/0000 [ monterey ] webgpu:web_platform,canvas,readbackFromWebGPUCanvas:drawTo2DCanvas:format="rgba8unorm";alphaMode="opaque";colorSpace="display-p3";webgpuCanvasType="onscreen";canvas2DType="offscreen" [ Failure ]