mirror of
https://github.com/encounter/dawn-cmake.git
synced 2025-05-15 03:41:34 +00:00
Add support for Tint's HLSL writer as a Toggle
This commit adds a Toggle that switches SPIRV-cross's HLSL generator for Tint's HLSL writer. New Toggle currently defaults to false. Bug: dawn:548 Change-Id: I37e238c6ba887efd65727809c8a6919df515a35e Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/31640 Reviewed-by: Bryan Bernhart <bryan.bernhart@intel.com> Reviewed-by: Corentin Wallez <cwallez@chromium.org> Reviewed-by: Ryan Harrison <rharrison@chromium.org> Commit-Queue: Enrico Galli <enrico.galli@intel.com>
This commit is contained in:
parent
c1dbb2625b
commit
2b6b0f45ff
@ -138,7 +138,10 @@ namespace dawn_native {
|
|||||||
{"disallow_unsafe_apis",
|
{"disallow_unsafe_apis",
|
||||||
"Produces validation errors on API entry points or parameter combinations that "
|
"Produces validation errors on API entry points or parameter combinations that "
|
||||||
"aren't considered secure yet.",
|
"aren't considered secure yet.",
|
||||||
"http://crbug.com/1138528"}}
|
"http://crbug.com/1138528"}},
|
||||||
|
{Toggle::UseTintGenerator,
|
||||||
|
{"use_tint_generator", "Use Tint instead of SPRIV-cross to generate shaders.",
|
||||||
|
"https://crbug.com/dawn/548"}},
|
||||||
// Dummy comment to separate the }} so it is clearer what to copy-paste to add a toggle.
|
// Dummy comment to separate the }} so it is clearer what to copy-paste to add a toggle.
|
||||||
}};
|
}};
|
||||||
|
|
||||||
|
@ -44,6 +44,7 @@ namespace dawn_native {
|
|||||||
DisableRobustness,
|
DisableRobustness,
|
||||||
MetalEnableVertexPulling,
|
MetalEnableVertexPulling,
|
||||||
DisallowUnsafeAPIs,
|
DisallowUnsafeAPIs,
|
||||||
|
UseTintGenerator,
|
||||||
|
|
||||||
EnumCount,
|
EnumCount,
|
||||||
InvalidEnum = EnumCount,
|
InvalidEnum = EnumCount,
|
||||||
|
@ -43,27 +43,37 @@ namespace dawn_native { namespace d3d12 {
|
|||||||
|
|
||||||
ShaderModule* module = ToBackend(descriptor->computeStage.module);
|
ShaderModule* module = ToBackend(descriptor->computeStage.module);
|
||||||
|
|
||||||
// Note that the HLSL will always use entryPoint "main".
|
const char* entryPoint = descriptor->computeStage.entryPoint;
|
||||||
std::string hlslSource;
|
std::string hlslSource;
|
||||||
DAWN_TRY_ASSIGN(hlslSource, module->TranslateToHLSL(descriptor->computeStage.entryPoint,
|
if (device->IsToggleEnabled(Toggle::UseTintGenerator)) {
|
||||||
SingleShaderStage::Compute,
|
DAWN_TRY_ASSIGN(hlslSource,
|
||||||
|
module->TranslateToHLSLWithTint(entryPoint, SingleShaderStage::Compute,
|
||||||
ToBackend(GetLayout())));
|
ToBackend(GetLayout())));
|
||||||
|
} else {
|
||||||
|
DAWN_TRY_ASSIGN(hlslSource,
|
||||||
|
module->TranslateToHLSLWithSPIRVCross(
|
||||||
|
entryPoint, SingleShaderStage::Compute, ToBackend(GetLayout())));
|
||||||
|
|
||||||
|
// Note that the HLSL will always use entryPoint "main" under SPIRV-cross.
|
||||||
|
entryPoint = "main";
|
||||||
|
}
|
||||||
|
|
||||||
D3D12_COMPUTE_PIPELINE_STATE_DESC d3dDesc = {};
|
D3D12_COMPUTE_PIPELINE_STATE_DESC d3dDesc = {};
|
||||||
d3dDesc.pRootSignature = ToBackend(GetLayout())->GetRootSignature();
|
d3dDesc.pRootSignature = ToBackend(GetLayout())->GetRootSignature();
|
||||||
|
|
||||||
ComPtr<IDxcBlob> compiledDXCShader;
|
ComPtr<IDxcBlob> compiledDXCShader;
|
||||||
ComPtr<ID3DBlob> compiledFXCShader;
|
ComPtr<ID3DBlob> compiledFXCShader;
|
||||||
|
|
||||||
if (device->IsToggleEnabled(Toggle::UseDXC)) {
|
if (device->IsToggleEnabled(Toggle::UseDXC)) {
|
||||||
DAWN_TRY_ASSIGN(compiledDXCShader, CompileShaderDXC(device, SingleShaderStage::Compute,
|
DAWN_TRY_ASSIGN(compiledDXCShader,
|
||||||
hlslSource, "main", compileFlags));
|
CompileShaderDXC(device, SingleShaderStage::Compute, hlslSource,
|
||||||
|
entryPoint, compileFlags));
|
||||||
|
|
||||||
d3dDesc.CS.pShaderBytecode = compiledDXCShader->GetBufferPointer();
|
d3dDesc.CS.pShaderBytecode = compiledDXCShader->GetBufferPointer();
|
||||||
d3dDesc.CS.BytecodeLength = compiledDXCShader->GetBufferSize();
|
d3dDesc.CS.BytecodeLength = compiledDXCShader->GetBufferSize();
|
||||||
} else {
|
} else {
|
||||||
DAWN_TRY_ASSIGN(compiledFXCShader, CompileShaderFXC(device, SingleShaderStage::Compute,
|
DAWN_TRY_ASSIGN(compiledFXCShader,
|
||||||
hlslSource, "main", compileFlags));
|
CompileShaderFXC(device, SingleShaderStage::Compute, hlslSource,
|
||||||
|
entryPoint, compileFlags));
|
||||||
d3dDesc.CS.pShaderBytecode = compiledFXCShader->GetBufferPointer();
|
d3dDesc.CS.pShaderBytecode = compiledFXCShader->GetBufferPointer();
|
||||||
d3dDesc.CS.BytecodeLength = compiledFXCShader->GetBufferSize();
|
d3dDesc.CS.BytecodeLength = compiledFXCShader->GetBufferSize();
|
||||||
}
|
}
|
||||||
|
@ -499,6 +499,7 @@ namespace dawn_native { namespace d3d12 {
|
|||||||
SetToggle(Toggle::UseD3D12RenderPass, GetDeviceInfo().supportsRenderPass);
|
SetToggle(Toggle::UseD3D12RenderPass, GetDeviceInfo().supportsRenderPass);
|
||||||
SetToggle(Toggle::UseD3D12ResidencyManagement, true);
|
SetToggle(Toggle::UseD3D12ResidencyManagement, true);
|
||||||
SetToggle(Toggle::UseDXC, false);
|
SetToggle(Toggle::UseDXC, false);
|
||||||
|
SetToggle(Toggle::UseTintGenerator, false);
|
||||||
|
|
||||||
// By default use the maximum shader-visible heap size allowed.
|
// By default use the maximum shader-visible heap size allowed.
|
||||||
SetToggle(Toggle::UseD3D12SmallShaderVisibleHeapForTesting, false);
|
SetToggle(Toggle::UseD3D12SmallShaderVisibleHeapForTesting, false);
|
||||||
|
@ -311,21 +311,32 @@ namespace dawn_native { namespace d3d12 {
|
|||||||
|
|
||||||
wgpu::ShaderStage renderStages = wgpu::ShaderStage::Vertex | wgpu::ShaderStage::Fragment;
|
wgpu::ShaderStage renderStages = wgpu::ShaderStage::Vertex | wgpu::ShaderStage::Fragment;
|
||||||
for (auto stage : IterateStages(renderStages)) {
|
for (auto stage : IterateStages(renderStages)) {
|
||||||
// Note that the HLSL entryPoint will always be "main".
|
|
||||||
std::string hlslSource;
|
std::string hlslSource;
|
||||||
DAWN_TRY_ASSIGN(hlslSource,
|
const char* entryPoint = GetStage(stage).entryPoint.c_str();
|
||||||
modules[stage]->TranslateToHLSL(GetStage(stage).entryPoint.c_str(),
|
|
||||||
stage, ToBackend(GetLayout())));
|
if (device->IsToggleEnabled(Toggle::UseTintGenerator)) {
|
||||||
|
DAWN_TRY_ASSIGN(hlslSource, modules[stage]->TranslateToHLSLWithTint(
|
||||||
|
entryPoint, stage, ToBackend(GetLayout())));
|
||||||
|
|
||||||
|
} else {
|
||||||
|
DAWN_TRY_ASSIGN(hlslSource, modules[stage]->TranslateToHLSLWithSPIRVCross(
|
||||||
|
entryPoint, stage, ToBackend(GetLayout())));
|
||||||
|
|
||||||
|
// Note that the HLSL will always use entryPoint "main" under SPIRV-cross.
|
||||||
|
entryPoint = "main";
|
||||||
|
}
|
||||||
|
|
||||||
if (device->IsToggleEnabled(Toggle::UseDXC)) {
|
if (device->IsToggleEnabled(Toggle::UseDXC)) {
|
||||||
DAWN_TRY_ASSIGN(compiledDXCShader[stage],
|
DAWN_TRY_ASSIGN(
|
||||||
CompileShaderDXC(device, stage, hlslSource, "main", compileFlags));
|
compiledDXCShader[stage],
|
||||||
|
CompileShaderDXC(device, stage, hlslSource, entryPoint, compileFlags));
|
||||||
|
|
||||||
shaders[stage]->pShaderBytecode = compiledDXCShader[stage]->GetBufferPointer();
|
shaders[stage]->pShaderBytecode = compiledDXCShader[stage]->GetBufferPointer();
|
||||||
shaders[stage]->BytecodeLength = compiledDXCShader[stage]->GetBufferSize();
|
shaders[stage]->BytecodeLength = compiledDXCShader[stage]->GetBufferSize();
|
||||||
} else {
|
} else {
|
||||||
DAWN_TRY_ASSIGN(compiledFXCShader[stage],
|
DAWN_TRY_ASSIGN(
|
||||||
CompileShaderFXC(device, stage, hlslSource, "main", compileFlags));
|
compiledFXCShader[stage],
|
||||||
|
CompileShaderFXC(device, stage, hlslSource, entryPoint, compileFlags));
|
||||||
|
|
||||||
shaders[stage]->pShaderBytecode = compiledFXCShader[stage]->GetBufferPointer();
|
shaders[stage]->pShaderBytecode = compiledFXCShader[stage]->GetBufferPointer();
|
||||||
shaders[stage]->BytecodeLength = compiledFXCShader[stage]->GetBufferSize();
|
shaders[stage]->BytecodeLength = compiledFXCShader[stage]->GetBufferSize();
|
||||||
|
@ -29,6 +29,10 @@
|
|||||||
|
|
||||||
#include <spirv_hlsl.hpp>
|
#include <spirv_hlsl.hpp>
|
||||||
|
|
||||||
|
#ifdef DAWN_ENABLE_WGSL
|
||||||
|
# include <tint/tint.h>
|
||||||
|
#endif // DAWN_ENABLE_WGSL
|
||||||
|
|
||||||
namespace dawn_native { namespace d3d12 {
|
namespace dawn_native { namespace d3d12 {
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
@ -176,10 +180,68 @@ namespace dawn_native { namespace d3d12 {
|
|||||||
: ShaderModuleBase(device, descriptor) {
|
: ShaderModuleBase(device, descriptor) {
|
||||||
}
|
}
|
||||||
|
|
||||||
ResultOrError<std::string> ShaderModule::TranslateToHLSL(const char* entryPointName,
|
ResultOrError<std::string> ShaderModule::TranslateToHLSLWithTint(const char* entryPointName,
|
||||||
SingleShaderStage stage,
|
SingleShaderStage stage,
|
||||||
PipelineLayout* layout) const {
|
PipelineLayout* layout) const {
|
||||||
ASSERT(!IsError());
|
ASSERT(!IsError());
|
||||||
|
|
||||||
|
#ifdef DAWN_ENABLE_WGSL
|
||||||
|
std::ostringstream errorStream;
|
||||||
|
errorStream << "Tint HLSL failure:" << std::endl;
|
||||||
|
|
||||||
|
// TODO: Remove redundant SPIRV step between WGSL and HLSL.
|
||||||
|
tint::Context context;
|
||||||
|
tint::reader::spirv::Parser parser(&context, GetSpirv());
|
||||||
|
|
||||||
|
if (!parser.Parse()) {
|
||||||
|
errorStream << "Parser: " << parser.error() << std::endl;
|
||||||
|
return DAWN_VALIDATION_ERROR(errorStream.str().c_str());
|
||||||
|
}
|
||||||
|
|
||||||
|
tint::ast::Module module = parser.module();
|
||||||
|
if (!module.IsValid()) {
|
||||||
|
errorStream << "Invalid module generated..." << std::endl;
|
||||||
|
return DAWN_VALIDATION_ERROR(errorStream.str().c_str());
|
||||||
|
}
|
||||||
|
|
||||||
|
tint::TypeDeterminer typeDeterminer(&context, &module);
|
||||||
|
if (!typeDeterminer.Determine()) {
|
||||||
|
errorStream << "Type Determination: " << typeDeterminer.error();
|
||||||
|
return DAWN_VALIDATION_ERROR(errorStream.str().c_str());
|
||||||
|
}
|
||||||
|
|
||||||
|
tint::Validator validator;
|
||||||
|
if (!validator.Validate(&module)) {
|
||||||
|
errorStream << "Validation: " << validator.error() << std::endl;
|
||||||
|
return DAWN_VALIDATION_ERROR(errorStream.str().c_str());
|
||||||
|
}
|
||||||
|
|
||||||
|
tint::transform::BoundArrayAccessorsTransform boundArrayTransformer(&context, &module);
|
||||||
|
if (!boundArrayTransformer.Run()) {
|
||||||
|
errorStream << "Bound Array Accessors Transform: " << boundArrayTransformer.error()
|
||||||
|
<< std::endl;
|
||||||
|
return DAWN_VALIDATION_ERROR(errorStream.str().c_str());
|
||||||
|
}
|
||||||
|
|
||||||
|
tint::writer::hlsl::Generator generator(std::move(module));
|
||||||
|
// TODO: Switch to GenerateEntryPoint once HLSL writer supports it.
|
||||||
|
if (!generator.Generate()) {
|
||||||
|
errorStream << "Generator: " << generator.error() << std::endl;
|
||||||
|
return DAWN_VALIDATION_ERROR(errorStream.str().c_str());
|
||||||
|
}
|
||||||
|
|
||||||
|
return generator.result();
|
||||||
|
#else
|
||||||
|
return DAWN_VALIDATION_ERROR("Using Tint to generate HLSL is not supported.");
|
||||||
|
#endif // DAWN_ENABLE_WGSL
|
||||||
|
}
|
||||||
|
|
||||||
|
ResultOrError<std::string> ShaderModule::TranslateToHLSLWithSPIRVCross(
|
||||||
|
const char* entryPointName,
|
||||||
|
SingleShaderStage stage,
|
||||||
|
PipelineLayout* layout) const {
|
||||||
|
ASSERT(!IsError());
|
||||||
|
|
||||||
// If these options are changed, the values in DawnSPIRVCrossHLSLFastFuzzer.cpp need to
|
// If these options are changed, the values in DawnSPIRVCrossHLSLFastFuzzer.cpp need to
|
||||||
// be updated.
|
// be updated.
|
||||||
spirv_cross::CompilerGLSL::Options options_glsl;
|
spirv_cross::CompilerGLSL::Options options_glsl;
|
||||||
|
@ -40,9 +40,13 @@ namespace dawn_native { namespace d3d12 {
|
|||||||
static ResultOrError<ShaderModule*> Create(Device* device,
|
static ResultOrError<ShaderModule*> Create(Device* device,
|
||||||
const ShaderModuleDescriptor* descriptor);
|
const ShaderModuleDescriptor* descriptor);
|
||||||
|
|
||||||
ResultOrError<std::string> TranslateToHLSL(const char* entryPointName,
|
ResultOrError<std::string> TranslateToHLSLWithTint(const char* entryPointName,
|
||||||
SingleShaderStage stage,
|
SingleShaderStage stage,
|
||||||
PipelineLayout* layout) const;
|
PipelineLayout* layout) const;
|
||||||
|
|
||||||
|
ResultOrError<std::string> TranslateToHLSLWithSPIRVCross(const char* entryPointName,
|
||||||
|
SingleShaderStage stage,
|
||||||
|
PipelineLayout* layout) const;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
ShaderModule(Device* device, const ShaderModuleDescriptor* descriptor);
|
ShaderModule(Device* device, const ShaderModuleDescriptor* descriptor);
|
||||||
|
@ -637,6 +637,15 @@ bool DawnTestBase::IsAsan() const {
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool DawnTestBase::HasToggleEnabled(const char* toggle) const {
|
||||||
|
for (const char* toggleEnabled : mParam.forceEnabledWorkarounds) {
|
||||||
|
if (strcmp(toggle, toggleEnabled) == 0) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
bool DawnTestBase::HasVendorIdFilter() const {
|
bool DawnTestBase::HasVendorIdFilter() const {
|
||||||
return gTestEnv->HasVendorIdFilter();
|
return gTestEnv->HasVendorIdFilter();
|
||||||
}
|
}
|
||||||
|
@ -254,6 +254,8 @@ class DawnTestBase {
|
|||||||
|
|
||||||
bool IsAsan() const;
|
bool IsAsan() const;
|
||||||
|
|
||||||
|
bool HasToggleEnabled(const char* workaround) const;
|
||||||
|
|
||||||
void StartExpectDeviceError();
|
void StartExpectDeviceError();
|
||||||
bool EndExpectDeviceError();
|
bool EndExpectDeviceError();
|
||||||
|
|
||||||
|
@ -72,6 +72,10 @@ TEST_P(EntryPointTests, TwoComputeInModule) {
|
|||||||
// TODO: Reenable once Tint is able to produce Vulkan 1.0 / 1.1 SPIR-V.
|
// TODO: Reenable once Tint is able to produce Vulkan 1.0 / 1.1 SPIR-V.
|
||||||
DAWN_SKIP_TEST_IF(IsVulkan());
|
DAWN_SKIP_TEST_IF(IsVulkan());
|
||||||
|
|
||||||
|
// TODO: Reenable once Tint's HLSL writer supports multiple entryPoints on a single stage.
|
||||||
|
// https://crbug.com/tint/297
|
||||||
|
DAWN_SKIP_TEST_IF(IsD3D12() && HasToggleEnabled("use_tint_generator"));
|
||||||
|
|
||||||
wgpu::ShaderModule module = utils::CreateShaderModuleFromWGSL(device, R"(
|
wgpu::ShaderModule module = utils::CreateShaderModuleFromWGSL(device, R"(
|
||||||
[[block]] struct Data {
|
[[block]] struct Data {
|
||||||
[[offset(0)]] data : u32;
|
[[offset(0)]] data : u32;
|
||||||
@ -141,6 +145,7 @@ TEST_P(EntryPointTests, TwoComputeInModule) {
|
|||||||
|
|
||||||
DAWN_INSTANTIATE_TEST(EntryPointTests,
|
DAWN_INSTANTIATE_TEST(EntryPointTests,
|
||||||
D3D12Backend(),
|
D3D12Backend(),
|
||||||
|
D3D12Backend({"use_tint_generator"}),
|
||||||
MetalBackend(),
|
MetalBackend(),
|
||||||
OpenGLBackend(),
|
OpenGLBackend(),
|
||||||
VulkanBackend());
|
VulkanBackend());
|
||||||
|
Loading…
x
Reference in New Issue
Block a user