[ir] Move use of IR decision higher in the stack.
This CL changes the tint writers to no longer except the `tint_use_ir`
flag. Instead, there is a version of `Generate` which accepts the IR and
one which accepts a Program. The caller is now responsible for passing
the correct params.
This decouples the WGSL reader from the IR writers which was required in
order to use the program to IR functionality.
Bug: tint:1718
Change-Id: If70a3f6c92a80adeee3094e485132ca33803817f
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/161742
Reviewed-by: Ben Clayton <bclayton@google.com>
Commit-Queue: dan sinclair <dsinclair@chromium.org>
Kokoro: Kokoro <noreply+kokoro@google.com>
diff --git a/src/dawn/native/vulkan/ShaderModuleVk.cpp b/src/dawn/native/vulkan/ShaderModuleVk.cpp
index 302533a..f9e5b34 100644
--- a/src/dawn/native/vulkan/ShaderModuleVk.cpp
+++ b/src/dawn/native/vulkan/ShaderModuleVk.cpp
@@ -190,6 +190,7 @@
X(std::string_view, entryPointName) \
X(bool, disableSymbolRenaming) \
X(tint::spirv::writer::Options, tintOptions) \
+ X(bool, use_tint_ir) \
X(CacheKey::UnsafeUnkeyedValue<dawn::platform::Platform*>, platform)
DAWN_MAKE_CACHE_REQUEST(SpirvCompilationRequest, SPIRV_COMPILATION_REQUEST_MEMBERS);
@@ -324,7 +325,7 @@
// transform as unsized arrays can only be declared on storage address space.
req.tintOptions.disable_runtime_sized_array_index_clamping =
GetDevice()->IsToggleEnabled(Toggle::VulkanUseBufferRobustAccess2);
- req.tintOptions.use_tint_ir = GetDevice()->IsToggleEnabled(Toggle::UseTintIR);
+ req.use_tint_ir = GetDevice()->IsToggleEnabled(Toggle::UseTintIR);
// Set subgroup uniform control flow flag for subgroup experiment, if device has
// Chromium-experimental-subgroup-uniform-control-flow feature. (dawn:464)
@@ -400,7 +401,17 @@
}
TRACE_EVENT0(r.platform.UnsafeGetValue(), General, "tint::spirv::writer::Generate()");
- auto tintResult = tint::spirv::writer::Generate(program, r.tintOptions);
+ tint::Result<tint::spirv::writer::Output> tintResult;
+ if (r.use_tint_ir) {
+ // Convert the AST program to an IR module.
+ auto ir = tint::wgsl::reader::ProgramToLoweredIR(program);
+ DAWN_INVALID_IF(!ir, "An error occurred while generating Tint IR\n%s",
+ ir.Failure().reason.str());
+
+ tintResult = tint::spirv::writer::Generate(ir.Get(), r.tintOptions);
+ } else {
+ tintResult = tint::spirv::writer::Generate(program, r.tintOptions);
+ }
DAWN_INVALID_IF(!tintResult, "An error occurred while generating SPIR-V\n%s",
tintResult.Failure().reason.str());
diff --git a/src/tint/cmd/tint/main.cc b/src/tint/cmd/tint/main.cc
index ca7d846..3624984 100644
--- a/src/tint/cmd/tint/main.cc
+++ b/src/tint/cmd/tint/main.cc
@@ -634,9 +634,20 @@
gen_options.disable_robustness = !options.enable_robustness;
gen_options.disable_workgroup_init = options.disable_workgroup_init;
gen_options.bindings = tint::spirv::writer::GenerateBindings(program);
- gen_options.use_tint_ir = options.use_ir;
- auto result = tint::spirv::writer::Generate(program, gen_options);
+ tint::Result<tint::spirv::writer::Output> result;
+ if (options.use_ir) {
+ // Convert the AST program to an IR module.
+ auto ir = tint::wgsl::reader::ProgramToLoweredIR(program);
+ if (!ir) {
+ std::cerr << "Failed to generate IR: " << ir << "\n";
+ return false;
+ }
+ result = tint::spirv::writer::Generate(ir.Get(), gen_options);
+ } else {
+ result = tint::spirv::writer::Generate(program, gen_options);
+ }
+
if (!result) {
tint::cmd::PrintWGSL(std::cerr, program);
std::cerr << "Failed to generate: " << result.Failure() << "\n";
@@ -747,7 +758,6 @@
// TODO(jrprice): Provide a way for the user to set non-default options.
tint::msl::writer::Options gen_options;
- gen_options.use_tint_ir = options.use_ir;
gen_options.disable_robustness = !options.enable_robustness;
gen_options.disable_workgroup_init = options.disable_workgroup_init;
gen_options.pixel_local_options = options.pixel_local_options;
@@ -757,7 +767,20 @@
0);
gen_options.array_length_from_uniform.bindpoint_to_size_index.emplace(tint::BindingPoint{0, 1},
1);
- auto result = tint::msl::writer::Generate(*input_program, gen_options);
+
+ tint::Result<tint::msl::writer::Output> result;
+ if (options.use_ir) {
+ // Convert the AST program to an IR module.
+ auto ir = tint::wgsl::reader::ProgramToLoweredIR(program);
+ if (!ir) {
+ std::cerr << "Failed to generate IR: " << ir << "\n";
+ return false;
+ }
+ result = tint::msl::writer::Generate(ir.Get(), gen_options);
+ } else {
+ result = tint::msl::writer::Generate(*input_program, gen_options);
+ }
+
if (!result) {
tint::cmd::PrintWGSL(std::cerr, program);
std::cerr << "Failed to generate: " << result.Failure() << "\n";
diff --git a/src/tint/fuzzers/tint_common_fuzzer.cc b/src/tint/fuzzers/tint_common_fuzzer.cc
index de7e8f6..ead0d65 100644
--- a/src/tint/fuzzers/tint_common_fuzzer.cc
+++ b/src/tint/fuzzers/tint_common_fuzzer.cc
@@ -364,12 +364,6 @@
}
case OutputFormat::kMSL: {
#if TINT_BUILD_MSL_WRITER
- // TODO(crbug.com/tint/1967): Skip fuzzing of the IR version of the MSL writer, which is
- // still under construction.
- if (options_msl_.use_tint_ir) {
- return 0;
- }
-
// Remap resource numbers to a flat namespace.
// TODO(crbug.com/tint/1501): Do this via Options::BindingMap.
if (auto flattened = tint::wgsl::FlattenBindings(program)) {
diff --git a/src/tint/lang/glsl/writer/BUILD.bazel b/src/tint/lang/glsl/writer/BUILD.bazel
index d5272f1..98f6fa3 100644
--- a/src/tint/lang/glsl/writer/BUILD.bazel
+++ b/src/tint/lang/glsl/writer/BUILD.bazel
@@ -51,13 +51,11 @@
"//src/tint/api/options",
"//src/tint/lang/core",
"//src/tint/lang/core/constant",
- "//src/tint/lang/core/ir",
"//src/tint/lang/core/type",
"//src/tint/lang/glsl/writer/raise",
"//src/tint/lang/wgsl",
"//src/tint/lang/wgsl/ast",
"//src/tint/lang/wgsl/program",
- "//src/tint/lang/wgsl/reader/lower",
"//src/tint/lang/wgsl/sem",
"//src/tint/utils/containers",
"//src/tint/utils/diagnostic",
@@ -80,11 +78,6 @@
"//src/tint/lang/glsl/writer/printer",
],
"//conditions:default": [],
- }) + select({
- ":tint_build_wgsl_reader": [
- "//src/tint/lang/wgsl/reader/program_to_ir",
- ],
- "//conditions:default": [],
}),
copts = COPTS,
visibility = ["//visibility:public"],
@@ -136,8 +129,3 @@
actual = "//src/tint:tint_build_glsl_writer_true",
)
-alias(
- name = "tint_build_wgsl_reader",
- actual = "//src/tint:tint_build_wgsl_reader_true",
-)
-
diff --git a/src/tint/lang/glsl/writer/BUILD.cmake b/src/tint/lang/glsl/writer/BUILD.cmake
index f266bae..a2164fb 100644
--- a/src/tint/lang/glsl/writer/BUILD.cmake
+++ b/src/tint/lang/glsl/writer/BUILD.cmake
@@ -58,13 +58,11 @@
tint_api_options
tint_lang_core
tint_lang_core_constant
- tint_lang_core_ir
tint_lang_core_type
tint_lang_glsl_writer_raise
tint_lang_wgsl
tint_lang_wgsl_ast
tint_lang_wgsl_program
- tint_lang_wgsl_reader_lower
tint_lang_wgsl_sem
tint_utils_containers
tint_utils_diagnostic
@@ -90,12 +88,6 @@
)
endif(TINT_BUILD_GLSL_WRITER)
-if(TINT_BUILD_WGSL_READER)
- tint_target_add_dependencies(tint_lang_glsl_writer lib
- tint_lang_wgsl_reader_program_to_ir
- )
-endif(TINT_BUILD_WGSL_READER)
-
endif(TINT_BUILD_GLSL_WRITER)
if(TINT_BUILD_GLSL_WRITER)
################################################################################
diff --git a/src/tint/lang/glsl/writer/BUILD.gn b/src/tint/lang/glsl/writer/BUILD.gn
index 0ed5983..6b2102c 100644
--- a/src/tint/lang/glsl/writer/BUILD.gn
+++ b/src/tint/lang/glsl/writer/BUILD.gn
@@ -54,13 +54,11 @@
"${tint_src_dir}/api/options",
"${tint_src_dir}/lang/core",
"${tint_src_dir}/lang/core/constant",
- "${tint_src_dir}/lang/core/ir",
"${tint_src_dir}/lang/core/type",
"${tint_src_dir}/lang/glsl/writer/raise",
"${tint_src_dir}/lang/wgsl",
"${tint_src_dir}/lang/wgsl/ast",
"${tint_src_dir}/lang/wgsl/program",
- "${tint_src_dir}/lang/wgsl/reader/lower",
"${tint_src_dir}/lang/wgsl/sem",
"${tint_src_dir}/utils/containers",
"${tint_src_dir}/utils/diagnostic",
@@ -85,10 +83,6 @@
"${tint_src_dir}/lang/glsl/writer/printer",
]
}
-
- if (tint_build_wgsl_reader) {
- deps += [ "${tint_src_dir}/lang/wgsl/reader/program_to_ir" ]
- }
}
}
if (tint_build_benchmarks) {
diff --git a/src/tint/lang/glsl/writer/common/options.h b/src/tint/lang/glsl/writer/common/options.h
index e9de953..8068595 100644
--- a/src/tint/lang/glsl/writer/common/options.h
+++ b/src/tint/lang/glsl/writer/common/options.h
@@ -61,9 +61,6 @@
/// Set to `true` to disable workgroup memory zero initialization
bool disable_workgroup_init = false;
- /// Set to `true` to generate GLSL via the Tint IR instead of from the AST.
- bool use_tint_ir = false;
-
/// The GLSL version to emit
Version version;
diff --git a/src/tint/lang/glsl/writer/writer.cc b/src/tint/lang/glsl/writer/writer.cc
index 452bd4b..7283deb 100644
--- a/src/tint/lang/glsl/writer/writer.cc
+++ b/src/tint/lang/glsl/writer/writer.cc
@@ -34,13 +34,26 @@
#include "src/tint/lang/glsl/writer/printer/printer.h"
#include "src/tint/lang/glsl/writer/raise/raise.h"
-#if TINT_BUILD_WGSL_READER
-#include "src/tint/lang/wgsl/reader/lower/lower.h"
-#include "src/tint/lang/wgsl/reader/program_to_ir/program_to_ir.h"
-#endif // TINT_BUILD_WGSL_REAdDER
-
namespace tint::glsl::writer {
+Result<Output> Generate(core::ir::Module& ir, const Options& options, const std::string&) {
+ Output output;
+
+ // Raise from core-dialect to GLSL-dialect.
+ if (auto res = raise::Raise(ir); !res) {
+ return res.Failure();
+ }
+
+ // Generate the GLSL code.
+ auto result = Print(ir, options.version);
+ if (!result) {
+ return result.Failure();
+ }
+ output.glsl = result.Get();
+
+ return output;
+}
+
Result<Output> Generate(const Program& program,
const Options& options,
const std::string& entry_point) {
@@ -50,58 +63,27 @@
Output output;
- if (options.use_tint_ir) {
-#if TINT_BUILD_WGSL_READER
- // Convert the AST program to an IR module.
- auto converted = wgsl::reader::ProgramToIR(program);
- if (!converted) {
- return converted.Failure();
- }
+ // Sanitize the program.
+ auto sanitized_result = Sanitize(program, options, entry_point);
+ if (!sanitized_result.program.IsValid()) {
+ return Failure{sanitized_result.program.Diagnostics()};
+ }
- auto ir = converted.Move();
+ // Generate the GLSL code.
+ auto impl = std::make_unique<ASTPrinter>(sanitized_result.program, options.version);
+ if (!impl->Generate()) {
+ return Failure{impl->Diagnostics()};
+ }
- // Lower from WGSL-dialect to core-dialect
- if (auto res = wgsl::reader::Lower(ir); !res) {
- return res.Failure();
- }
+ output.glsl = impl->Result();
+ output.needs_internal_uniform_buffer = sanitized_result.needs_internal_uniform_buffer;
+ output.bindpoint_to_data = std::move(sanitized_result.bindpoint_to_data);
- // Raise from core-dialect to GLSL-dialect.
- if (auto res = raise::Raise(ir); !res) {
- return res.Failure();
- }
-
- // Generate the GLSL code.
- auto result = Print(ir, options.version);
- if (!result) {
- return result.Failure();
- }
- output.glsl = result.Get();
-#else
- return Failure{"use_tint_ir requires building with TINT_BUILD_WGSL_READER"};
-#endif
- } else {
- // Sanitize the program.
- auto sanitized_result = Sanitize(program, options, entry_point);
- if (!sanitized_result.program.IsValid()) {
- return Failure{sanitized_result.program.Diagnostics()};
- }
-
- // Generate the GLSL code.
- auto impl = std::make_unique<ASTPrinter>(sanitized_result.program, options.version);
- if (!impl->Generate()) {
- return Failure{impl->Diagnostics()};
- }
-
- output.glsl = impl->Result();
- output.needs_internal_uniform_buffer = sanitized_result.needs_internal_uniform_buffer;
- output.bindpoint_to_data = std::move(sanitized_result.bindpoint_to_data);
-
- // Collect the list of entry points in the sanitized program.
- for (auto* func : sanitized_result.program.AST().Functions()) {
- if (func->IsEntryPoint()) {
- auto name = func->name->symbol.Name();
- output.entry_points.push_back({name, func->PipelineStage()});
- }
+ // Collect the list of entry points in the sanitized program.
+ for (auto* func : sanitized_result.program.AST().Functions()) {
+ if (func->IsEntryPoint()) {
+ auto name = func->name->symbol.Name();
+ output.entry_points.push_back({name, func->PipelineStage()});
}
}
diff --git a/src/tint/lang/glsl/writer/writer.h b/src/tint/lang/glsl/writer/writer.h
index a2aa79c..299ee08 100644
--- a/src/tint/lang/glsl/writer/writer.h
+++ b/src/tint/lang/glsl/writer/writer.h
@@ -39,12 +39,26 @@
namespace tint {
class Program;
} // namespace tint
+namespace tint::core::ir {
+class Module;
+} // namespace tint::core::ir
namespace tint::glsl::writer {
/// Generate GLSL for a program, according to a set of configuration options.
/// The result will contain the GLSL and supplementary information, or failure.
/// information.
+/// @param ir the IR module to translate to GLSL
+/// @param options the configuration options to use when generating GLSL
+/// @param entry_point the entry point to generate GLSL for
+/// @returns the resulting GLSL and supplementary information, or failure
+Result<Output> Generate(core::ir::Module& ir,
+ const Options& options,
+ const std::string& entry_point);
+
+/// Generate GLSL for a program, according to a set of configuration options.
+/// The result will contain the GLSL and supplementary information, or failure.
+/// information.
/// @param program the program to translate to GLSL
/// @param options the configuration options to use when generating GLSL
/// @param entry_point the entry point to generate GLSL for
diff --git a/src/tint/lang/msl/writer/common/options.h b/src/tint/lang/msl/writer/common/options.h
index d085a66..66623d9 100644
--- a/src/tint/lang/msl/writer/common/options.h
+++ b/src/tint/lang/msl/writer/common/options.h
@@ -130,9 +130,6 @@
/// for all vertex shaders in the module.
bool emit_vertex_point_size = false;
- /// Set to `true` to generate MSL via the Tint IR instead of from the AST.
- bool use_tint_ir = false;
-
/// The index to use when generating a UBO to receive storage buffer sizes.
/// Defaults to 30, which is the last valid buffer slot.
uint32_t buffer_size_ubo_index = 30;
@@ -155,7 +152,6 @@
TINT_REFLECT(disable_robustness,
disable_workgroup_init,
emit_vertex_point_size,
- use_tint_ir,
buffer_size_ubo_index,
fixed_sample_mask,
pixel_local_options,
diff --git a/src/tint/lang/msl/writer/output.cc b/src/tint/lang/msl/writer/output.cc
index ed184eb..cc2f3a0 100644
--- a/src/tint/lang/msl/writer/output.cc
+++ b/src/tint/lang/msl/writer/output.cc
@@ -35,4 +35,6 @@
Output::Output(const Output&) = default;
+Output& Output::operator=(const Output&) = default;
+
} // namespace tint::msl::writer
diff --git a/src/tint/lang/msl/writer/output.h b/src/tint/lang/msl/writer/output.h
index 6e873af..219e2a6 100644
--- a/src/tint/lang/msl/writer/output.h
+++ b/src/tint/lang/msl/writer/output.h
@@ -47,6 +47,10 @@
/// Copy constructor
Output(const Output&);
+ /// Copy assignment
+ /// @returns this
+ Output& operator=(const Output&);
+
/// The generated MSL.
std::string msl = "";
diff --git a/src/tint/lang/msl/writer/writer.cc b/src/tint/lang/msl/writer/writer.cc
index fc86c0c..54bf13b 100644
--- a/src/tint/lang/msl/writer/writer.cc
+++ b/src/tint/lang/msl/writer/writer.cc
@@ -42,6 +42,30 @@
namespace tint::msl::writer {
+Result<Output> Generate(core::ir::Module& ir, const Options& options) {
+ {
+ auto res = ValidateBindingOptions(options);
+ if (!res) {
+ return res.Failure();
+ }
+ }
+
+ Output output;
+
+ // Raise from core-dialect to MSL-dialect.
+ if (auto res = raise::Raise(ir); !res) {
+ return res.Failure();
+ }
+
+ // Generate the MSL code.
+ auto result = Print(ir);
+ if (!result) {
+ return result.Failure();
+ }
+ output.msl = result.Get();
+ return output;
+}
+
Result<Output> Generate(const Program& program, const Options& options) {
if (!program.IsValid()) {
return Failure{program.Diagnostics()};
@@ -56,54 +80,23 @@
Output output;
- if (options.use_tint_ir) {
-#if TINT_BUILD_WGSL_READER
- // Convert the AST program to an IR module.
- auto converted = wgsl::reader::ProgramToIR(program);
- if (!converted) {
- return converted.Failure();
- }
-
- auto ir = converted.Move();
-
- // Lower from WGSL-dialect to core-dialect
- if (auto res = wgsl::reader::Lower(ir); !res) {
- return res.Failure();
- }
-
- // Raise from core-dialect to MSL-dialect.
- if (auto res = raise::Raise(ir); !res) {
- return res.Failure();
- }
-
- // Generate the MSL code.
- auto result = Print(ir);
- if (!result) {
- return result.Failure();
- }
- output.msl = result.Get();
-#else
- return Failure{"use_tint_ir requires building with TINT_BUILD_WGSL_READER"};
-#endif
- } else {
- // Sanitize the program.
- auto sanitized_result = Sanitize(program, options);
- if (!sanitized_result.program.IsValid()) {
- return Failure{sanitized_result.program.Diagnostics()};
- }
- output.needs_storage_buffer_sizes = sanitized_result.needs_storage_buffer_sizes;
- output.used_array_length_from_uniform_indices =
- std::move(sanitized_result.used_array_length_from_uniform_indices);
-
- // Generate the MSL code.
- auto impl = std::make_unique<ASTPrinter>(sanitized_result.program);
- if (!impl->Generate()) {
- return Failure{impl->Diagnostics()};
- }
- output.msl = impl->Result();
- output.has_invariant_attribute = impl->HasInvariant();
- output.workgroup_allocations = impl->DynamicWorkgroupAllocations();
+ // Sanitize the program.
+ auto sanitized_result = Sanitize(program, options);
+ if (!sanitized_result.program.IsValid()) {
+ return Failure{sanitized_result.program.Diagnostics()};
}
+ output.needs_storage_buffer_sizes = sanitized_result.needs_storage_buffer_sizes;
+ output.used_array_length_from_uniform_indices =
+ std::move(sanitized_result.used_array_length_from_uniform_indices);
+
+ // Generate the MSL code.
+ auto impl = std::make_unique<ASTPrinter>(sanitized_result.program);
+ if (!impl->Generate()) {
+ return Failure{impl->Diagnostics()};
+ }
+ output.msl = impl->Result();
+ output.has_invariant_attribute = impl->HasInvariant();
+ output.workgroup_allocations = impl->DynamicWorkgroupAllocations();
return output;
}
diff --git a/src/tint/lang/msl/writer/writer.h b/src/tint/lang/msl/writer/writer.h
index 7d34ddd..e27c318 100644
--- a/src/tint/lang/msl/writer/writer.h
+++ b/src/tint/lang/msl/writer/writer.h
@@ -39,11 +39,21 @@
namespace tint {
class Program;
} // namespace tint
+namespace tint::core::ir {
+class Module;
+} // namespace tint::core::ir
namespace tint::msl::writer {
/// Generate MSL for a program, according to a set of configuration options.
/// The result will contain the MSL and supplementary information, or failure.
+/// @param ir the IR module to translate to MSL
+/// @param options the configuration options to use when generating MSL
+/// @returns the resulting MSL and supplementary information, or failure
+Result<Output> Generate(core::ir::Module& ir, const Options& options);
+
+/// Generate MSL for a program, according to a set of configuration options.
+/// The result will contain the MSL and supplementary information, or failure.
/// @param program the program to translate to MSL
/// @param options the configuration options to use when generating MSL
/// @returns the resulting MSL and supplementary information, or failure
diff --git a/src/tint/lang/spirv/writer/BUILD.bazel b/src/tint/lang/spirv/writer/BUILD.bazel
index 1525211..2a6307e 100644
--- a/src/tint/lang/spirv/writer/BUILD.bazel
+++ b/src/tint/lang/spirv/writer/BUILD.bazel
@@ -39,6 +39,7 @@
cc_library(
name = "writer",
srcs = [
+ "output.cc",
"writer.cc",
],
hdrs = [
@@ -55,7 +56,6 @@
"//src/tint/lang/wgsl",
"//src/tint/lang/wgsl/ast",
"//src/tint/lang/wgsl/program",
- "//src/tint/lang/wgsl/reader/lower",
"//src/tint/lang/wgsl/sem",
"//src/tint/utils/containers",
"//src/tint/utils/diagnostic",
@@ -83,11 +83,6 @@
"//src/tint/lang/spirv/writer/raise",
],
"//conditions:default": [],
- }) + select({
- ":tint_build_wgsl_reader": [
- "//src/tint/lang/wgsl/reader/program_to_ir",
- ],
- "//conditions:default": [],
}),
copts = COPTS,
visibility = ["//visibility:public"],
@@ -167,9 +162,11 @@
"//src/tint/cmd/bench:bench",
"//src/tint/lang/core",
"//src/tint/lang/core/constant",
+ "//src/tint/lang/core/ir",
"//src/tint/lang/core/type",
"//src/tint/lang/wgsl",
"//src/tint/lang/wgsl/ast",
+ "//src/tint/lang/wgsl/common",
"//src/tint/lang/wgsl/program",
"//src/tint/lang/wgsl/sem",
"//src/tint/utils/containers",
@@ -192,6 +189,11 @@
"//src/tint/lang/spirv/writer/common",
],
"//conditions:default": [],
+ }) + select({
+ ":tint_build_wgsl_reader": [
+ "//src/tint/lang/wgsl/reader",
+ ],
+ "//conditions:default": [],
}),
copts = COPTS,
visibility = ["//visibility:public"],
diff --git a/src/tint/lang/spirv/writer/BUILD.cmake b/src/tint/lang/spirv/writer/BUILD.cmake
index 767a497..f648776 100644
--- a/src/tint/lang/spirv/writer/BUILD.cmake
+++ b/src/tint/lang/spirv/writer/BUILD.cmake
@@ -48,6 +48,7 @@
# Condition: TINT_BUILD_SPV_WRITER
################################################################################
tint_add_target(tint_lang_spirv_writer lib
+ lang/spirv/writer/output.cc
lang/spirv/writer/output.h
lang/spirv/writer/writer.cc
lang/spirv/writer/writer.h
@@ -63,7 +64,6 @@
tint_lang_wgsl
tint_lang_wgsl_ast
tint_lang_wgsl_program
- tint_lang_wgsl_reader_lower
tint_lang_wgsl_sem
tint_utils_containers
tint_utils_diagnostic
@@ -95,12 +95,6 @@
)
endif(TINT_BUILD_SPV_WRITER)
-if(TINT_BUILD_WGSL_READER)
- tint_target_add_dependencies(tint_lang_spirv_writer lib
- tint_lang_wgsl_reader_program_to_ir
- )
-endif(TINT_BUILD_WGSL_READER)
-
endif(TINT_BUILD_SPV_WRITER)
if(TINT_BUILD_SPV_WRITER)
################################################################################
@@ -189,9 +183,11 @@
tint_cmd_bench_bench
tint_lang_core
tint_lang_core_constant
+ tint_lang_core_ir
tint_lang_core_type
tint_lang_wgsl
tint_lang_wgsl_ast
+ tint_lang_wgsl_common
tint_lang_wgsl_program
tint_lang_wgsl_sem
tint_utils_containers
@@ -220,4 +216,10 @@
)
endif(TINT_BUILD_SPV_WRITER)
+if(TINT_BUILD_WGSL_READER)
+ tint_target_add_dependencies(tint_lang_spirv_writer_bench bench
+ tint_lang_wgsl_reader
+ )
+endif(TINT_BUILD_WGSL_READER)
+
endif(TINT_BUILD_SPV_WRITER)
\ No newline at end of file
diff --git a/src/tint/lang/spirv/writer/BUILD.gn b/src/tint/lang/spirv/writer/BUILD.gn
index d9cefee..c0b00dc 100644
--- a/src/tint/lang/spirv/writer/BUILD.gn
+++ b/src/tint/lang/spirv/writer/BUILD.gn
@@ -44,6 +44,7 @@
if (tint_build_spv_writer) {
libtint_source_set("writer") {
sources = [
+ "output.cc",
"output.h",
"writer.cc",
"writer.h",
@@ -58,7 +59,6 @@
"${tint_src_dir}/lang/wgsl",
"${tint_src_dir}/lang/wgsl/ast",
"${tint_src_dir}/lang/wgsl/program",
- "${tint_src_dir}/lang/wgsl/reader/lower",
"${tint_src_dir}/lang/wgsl/sem",
"${tint_src_dir}/utils/containers",
"${tint_src_dir}/utils/diagnostic",
@@ -87,10 +87,6 @@
"${tint_src_dir}/lang/spirv/writer/raise",
]
}
-
- if (tint_build_wgsl_reader) {
- deps += [ "${tint_src_dir}/lang/wgsl/reader/program_to_ir" ]
- }
}
}
if (tint_build_unittests) {
@@ -170,9 +166,11 @@
"${tint_src_dir}/cmd/bench:bench",
"${tint_src_dir}/lang/core",
"${tint_src_dir}/lang/core/constant",
+ "${tint_src_dir}/lang/core/ir",
"${tint_src_dir}/lang/core/type",
"${tint_src_dir}/lang/wgsl",
"${tint_src_dir}/lang/wgsl/ast",
+ "${tint_src_dir}/lang/wgsl/common",
"${tint_src_dir}/lang/wgsl/program",
"${tint_src_dir}/lang/wgsl/sem",
"${tint_src_dir}/utils/containers",
@@ -196,6 +194,10 @@
"${tint_src_dir}/lang/spirv/writer/common",
]
}
+
+ if (tint_build_wgsl_reader) {
+ deps += [ "${tint_src_dir}/lang/wgsl/reader" ]
+ }
}
}
}
diff --git a/src/tint/lang/spirv/writer/ast_printer/BUILD.bazel b/src/tint/lang/spirv/writer/ast_printer/BUILD.bazel
index 40919cf..4c831b3 100644
--- a/src/tint/lang/spirv/writer/ast_printer/BUILD.bazel
+++ b/src/tint/lang/spirv/writer/ast_printer/BUILD.bazel
@@ -124,6 +124,7 @@
"//src/tint/api/common",
"//src/tint/lang/core",
"//src/tint/lang/core/constant",
+ "//src/tint/lang/core/ir",
"//src/tint/lang/core/type",
"//src/tint/lang/wgsl",
"//src/tint/lang/wgsl/ast",
diff --git a/src/tint/lang/spirv/writer/ast_printer/BUILD.cmake b/src/tint/lang/spirv/writer/ast_printer/BUILD.cmake
index e1f6e05..b8e949d 100644
--- a/src/tint/lang/spirv/writer/ast_printer/BUILD.cmake
+++ b/src/tint/lang/spirv/writer/ast_printer/BUILD.cmake
@@ -130,6 +130,7 @@
tint_api_common
tint_lang_core
tint_lang_core_constant
+ tint_lang_core_ir
tint_lang_core_type
tint_lang_wgsl
tint_lang_wgsl_ast
diff --git a/src/tint/lang/spirv/writer/ast_printer/BUILD.gn b/src/tint/lang/spirv/writer/ast_printer/BUILD.gn
index 12b2c96..ca8c42b 100644
--- a/src/tint/lang/spirv/writer/ast_printer/BUILD.gn
+++ b/src/tint/lang/spirv/writer/ast_printer/BUILD.gn
@@ -127,6 +127,7 @@
"${tint_src_dir}/api/common",
"${tint_src_dir}/lang/core",
"${tint_src_dir}/lang/core/constant",
+ "${tint_src_dir}/lang/core/ir",
"${tint_src_dir}/lang/core/type",
"${tint_src_dir}/lang/wgsl",
"${tint_src_dir}/lang/wgsl/ast",
diff --git a/src/tint/lang/spirv/writer/common/options.h b/src/tint/lang/spirv/writer/common/options.h
index 46718d2..f5c7897 100644
--- a/src/tint/lang/spirv/writer/common/options.h
+++ b/src/tint/lang/spirv/writer/common/options.h
@@ -138,9 +138,6 @@
/// Set to `true` to always pass matrices to user functions by pointer instead of by value.
bool pass_matrix_by_pointer = false;
- /// Set to `true` to generate SPIR-V via the Tint IR instead of from the AST.
- bool use_tint_ir = false;
-
/// Set to `true` to require `SPV_KHR_subgroup_uniform_control_flow` extension and
/// `SubgroupUniformControlFlowKHR` execution mode for compute stage entry points in generated
/// SPIRV module. Issue: dawn:464
@@ -157,7 +154,6 @@
use_zero_initialize_workgroup_memory_extension,
emit_vertex_point_size,
clamp_frag_depth,
- use_tint_ir,
experimental_require_subgroup_uniform_control_flow,
bindings);
};
diff --git a/src/tint/lang/spirv/writer/output.cc b/src/tint/lang/spirv/writer/output.cc
new file mode 100644
index 0000000..ec197e5
--- /dev/null
+++ b/src/tint/lang/spirv/writer/output.cc
@@ -0,0 +1,40 @@
+// Copyright 2023 The Dawn & Tint Authors
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions are met:
+//
+// 1. Redistributions of source code must retain the above copyright notice, this
+// list of conditions and the following disclaimer.
+//
+// 2. Redistributions in binary form must reproduce the above copyright notice,
+// this list of conditions and the following disclaimer in the documentation
+// and/or other materials provided with the distribution.
+//
+// 3. Neither the name of the copyright holder nor the names of its
+// contributors may be used to endorse or promote products derived from
+// this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+// OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+#include "src/tint/lang/spirv/writer/output.h"
+
+namespace tint::spirv::writer {
+
+Output::Output() = default;
+
+Output::~Output() = default;
+
+Output::Output(const Output&) = default;
+
+Output& Output::operator=(const Output&) = default;
+
+} // namespace tint::spirv::writer
diff --git a/src/tint/lang/spirv/writer/output.h b/src/tint/lang/spirv/writer/output.h
index e14f7b1..c6b6e3c 100644
--- a/src/tint/lang/spirv/writer/output.h
+++ b/src/tint/lang/spirv/writer/output.h
@@ -28,6 +28,7 @@
#ifndef SRC_TINT_LANG_SPIRV_WRITER_OUTPUT_H_
#define SRC_TINT_LANG_SPIRV_WRITER_OUTPUT_H_
+#include <cstdint>
#include <string>
#include <vector>
@@ -44,6 +45,10 @@
/// Copy constructor
Output(const Output&);
+ /// Copy assignment
+ /// @returns this
+ Output& operator=(const Output&);
+
/// The generated SPIR-V.
std::vector<uint32_t> spirv;
};
diff --git a/src/tint/lang/spirv/writer/writer.cc b/src/tint/lang/spirv/writer/writer.cc
index a0d7035..1ee7d51 100644
--- a/src/tint/lang/spirv/writer/writer.cc
+++ b/src/tint/lang/spirv/writer/writer.cc
@@ -34,20 +34,39 @@
#include "src/tint/lang/spirv/writer/common/option_helpers.h"
#include "src/tint/lang/spirv/writer/printer/printer.h"
#include "src/tint/lang/spirv/writer/raise/raise.h"
-#include "src/tint/lang/wgsl/reader/lower/lower.h"
-
-#if TINT_BUILD_WGSL_READER
-#include "src/tint/lang/wgsl/reader/program_to_ir/program_to_ir.h"
-#endif
// Included by 'ast_printer.h', included again here for './tools/run gen' track the dependency.
#include "spirv/unified1/spirv.h"
namespace tint::spirv::writer {
-Output::Output() = default;
-Output::~Output() = default;
-Output::Output(const Output&) = default;
+Result<Output> Generate(core::ir::Module& ir, const Options& options) {
+ bool zero_initialize_workgroup_memory =
+ !options.disable_workgroup_init && options.use_zero_initialize_workgroup_memory_extension;
+
+ {
+ auto res = ValidateBindingOptions(options);
+ if (!res) {
+ return res.Failure();
+ }
+ }
+
+ Output output;
+
+ // Raise from core-dialect to SPIR-V-dialect.
+ if (auto res = raise::Raise(ir, options); !res) {
+ return std::move(res.Failure());
+ }
+
+ // Generate the SPIR-V code.
+ auto spirv = Print(ir, zero_initialize_workgroup_memory);
+ if (!spirv) {
+ return std::move(spirv.Failure());
+ }
+ output.spirv = std::move(spirv.Get());
+
+ return output;
+}
Result<Output> Generate(const Program& program, const Options& options) {
if (!program.IsValid()) {
@@ -66,52 +85,21 @@
Output output;
- if (options.use_tint_ir) {
-#if TINT_BUILD_WGSL_READER
- // Convert the AST program to an IR module.
- auto converted = wgsl::reader::ProgramToIR(program);
- if (!converted) {
- return converted.Failure();
- }
-
- auto ir = converted.Move();
-
- // Lower from WGSL-dialect to core-dialect
- if (auto res = wgsl::reader::Lower(ir); !res) {
- return res.Failure();
- }
-
- // Raise from core-dialect to SPIR-V-dialect.
- if (auto res = raise::Raise(ir, options); !res) {
- return std::move(res.Failure());
- }
-
- // Generate the SPIR-V code.
- auto spirv = Print(ir, zero_initialize_workgroup_memory);
- if (!spirv) {
- return std::move(spirv.Failure());
- }
- output.spirv = std::move(spirv.Get());
-#else
- return Failure{"use_tint_ir requires building with TINT_BUILD_WGSL_READER"};
-#endif
- } else {
- // Sanitize the program.
- auto sanitized_result = Sanitize(program, options);
- if (!sanitized_result.program.IsValid()) {
- return Failure{sanitized_result.program.Diagnostics()};
- }
-
- // Generate the SPIR-V code.
- auto impl = std::make_unique<ASTPrinter>(
- sanitized_result.program, zero_initialize_workgroup_memory,
- options.experimental_require_subgroup_uniform_control_flow);
- if (!impl->Generate()) {
- return Failure{impl->Diagnostics()};
- }
- output.spirv = std::move(impl->Result());
+ // Sanitize the program.
+ auto sanitized_result = Sanitize(program, options);
+ if (!sanitized_result.program.IsValid()) {
+ return Failure{sanitized_result.program.Diagnostics()};
}
+ // Generate the SPIR-V code.
+ auto impl =
+ std::make_unique<ASTPrinter>(sanitized_result.program, zero_initialize_workgroup_memory,
+ options.experimental_require_subgroup_uniform_control_flow);
+ if (!impl->Generate()) {
+ return Failure{impl->Diagnostics()};
+ }
+ output.spirv = std::move(impl->Result());
+
return output;
}
diff --git a/src/tint/lang/spirv/writer/writer.h b/src/tint/lang/spirv/writer/writer.h
index b050065..807aa9f 100644
--- a/src/tint/lang/spirv/writer/writer.h
+++ b/src/tint/lang/spirv/writer/writer.h
@@ -30,6 +30,7 @@
#include <string>
+#include "src/tint/lang/core/ir/module.h"
#include "src/tint/lang/spirv/writer/common/options.h"
#include "src/tint/lang/spirv/writer/output.h"
#include "src/tint/utils/diagnostic/diagnostic.h"
@@ -44,6 +45,13 @@
/// Generate SPIR-V for a program, according to a set of configuration options.
/// The result will contain the SPIR-V or failure.
+/// @param ir the IR module to translate to SPIR-V
+/// @param options the configuration options to use when generating SPIR-V
+/// @returns the resulting SPIR-V and supplementary information, or failure.
+Result<Output> Generate(core::ir::Module& ir, const Options& options);
+
+/// Generate SPIR-V for a program, according to a set of configuration options.
+/// The result will contain the SPIR-V or failure.
/// @param program the program to translate to SPIR-V
/// @param options the configuration options to use when generating SPIR-V
/// @returns the resulting SPIR-V and supplementary information, or failure.
diff --git a/src/tint/lang/spirv/writer/writer_bench.cc b/src/tint/lang/spirv/writer/writer_bench.cc
index 5d8766d..2112631 100644
--- a/src/tint/lang/spirv/writer/writer_bench.cc
+++ b/src/tint/lang/spirv/writer/writer_bench.cc
@@ -30,31 +30,50 @@
#include "src/tint/cmd/bench/bench.h"
#include "src/tint/lang/spirv/writer/writer.h"
+#if TINT_BUILD_WGSL_READER
+#include "src/tint/lang/wgsl/reader/reader.h"
+#endif // TINT_BUILD_WGSL_READER
+
namespace tint::spirv::writer {
namespace {
-void RunBenchmark(benchmark::State& state, std::string input_name, Options options) {
+void GenerateSPIRV(benchmark::State& state, std::string input_name) {
auto res = bench::LoadProgram(input_name);
if (!res) {
state.SkipWithError(res.Failure().reason.str());
return;
}
for (auto _ : state) {
- auto gen_res = Generate(res->program, options);
+ auto gen_res = Generate(res->program, {});
if (!gen_res) {
state.SkipWithError(gen_res.Failure().reason.str());
}
}
}
-void GenerateSPIRV(benchmark::State& state, std::string input_name) {
- RunBenchmark(state, input_name, {});
-}
-
void GenerateSPIRV_UseIR(benchmark::State& state, std::string input_name) {
- Options options;
- options.use_tint_ir = true;
- RunBenchmark(state, input_name, std::move(options));
+#if TINT_BUILD_WGSL_READER
+ auto res = bench::LoadProgram(input_name);
+ if (!res) {
+ state.SkipWithError(res.Failure().reason.str());
+ return;
+ }
+ for (auto _ : state) {
+ // Convert the AST program to an IR module.
+ auto ir = tint::wgsl::reader::ProgramToLoweredIR(res->program);
+ if (!ir) {
+ state.SkipWithError(ir.Failure().reason.str());
+ return;
+ }
+
+ auto gen_res = Generate(ir.Get(), {});
+ if (!gen_res) {
+ state.SkipWithError(gen_res.Failure().reason.str());
+ }
+ }
+#else
+#error "WGSL Reader is required to build IR generator"
+#endif // TINT_BUILD_WGSL_READER
}
TINT_BENCHMARK_PROGRAMS(GenerateSPIRV);
diff --git a/src/tint/lang/wgsl/reader/reader.cc b/src/tint/lang/wgsl/reader/reader.cc
index df1dc7b..f74d837 100644
--- a/src/tint/lang/wgsl/reader/reader.cc
+++ b/src/tint/lang/wgsl/reader/reader.cc
@@ -55,4 +55,19 @@
return module;
}
+tint::Result<core::ir::Module> ProgramToLoweredIR(const Program& program) {
+ auto ir = tint::wgsl::reader::ProgramToIR(program);
+ if (!ir) {
+ return ir.Failure();
+ }
+
+ // Lower from WGSL-dialect to core-dialect
+ auto res = tint::wgsl::reader::Lower(ir.Get());
+ if (!res) {
+ return res.Failure();
+ }
+
+ return ir;
+}
+
} // namespace tint::wgsl::reader
diff --git a/src/tint/lang/wgsl/reader/reader.h b/src/tint/lang/wgsl/reader/reader.h
index 40c973a..8594250 100644
--- a/src/tint/lang/wgsl/reader/reader.h
+++ b/src/tint/lang/wgsl/reader/reader.h
@@ -49,6 +49,15 @@
/// @returns the resulting IR module, or failure
Result<core::ir::Module> WgslToIR(const Source::File* file, const Options& options = {});
+/// Builds a core-dialect core::ir::Module from the given Program
+/// @param program the Program to use.
+/// @returns the core-dialect IR module.
+///
+/// @note this assumes the `program.IsValid()`, and has had const-eval done so
+/// any abstract values have been calculated and converted into the relevant
+/// concrete types.
+tint::Result<core::ir::Module> ProgramToLoweredIR(const Program& program);
+
} // namespace tint::wgsl::reader
#endif // SRC_TINT_LANG_WGSL_READER_READER_H_