[ir] Split `TextGenerator` apart.
Currently the `TextGenerator` class contains code specific to generating
from the AST. This CL splits out the AST specific bits into an
`ASTTextGenerator` subclass and uses that in the AST writers.
Bug: tint:1718
Change-Id: Ib4b15308a065fb8f7d8915e9cf67dde9f6e6ed19
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/138680
Kokoro: Kokoro <noreply+kokoro@google.com>
Reviewed-by: James Price <jrprice@google.com>
Commit-Queue: Dan Sinclair <dsinclair@chromium.org>
diff --git a/src/tint/BUILD.gn b/src/tint/BUILD.gn
index 3e807e9..3901d5d 100644
--- a/src/tint/BUILD.gn
+++ b/src/tint/BUILD.gn
@@ -988,6 +988,8 @@
"writer/append_vector.h",
"writer/array_length_from_uniform_options.cc",
"writer/array_length_from_uniform_options.h",
+ "writer/ast_text_generator.cc",
+ "writer/ast_text_generator.h",
"writer/binding_point.h",
"writer/binding_remapper_options.cc",
"writer/binding_remapper_options.h",
@@ -1894,10 +1896,10 @@
tint_unittests_source_set("tint_unittests_writer_src") {
sources = [
"writer/append_vector_test.cc",
+ "writer/ast_text_generator_test.cc",
"writer/check_supported_extensions_test.cc",
"writer/flatten_bindings_test.cc",
"writer/float_to_string_test.cc",
- "writer/text_generator_test.cc",
]
deps = [
":libtint_unittests_ast_helper",
diff --git a/src/tint/CMakeLists.txt b/src/tint/CMakeLists.txt
index 5cc2e76..a9c5a8d 100644
--- a/src/tint/CMakeLists.txt
+++ b/src/tint/CMakeLists.txt
@@ -562,6 +562,8 @@
writer/append_vector.h
writer/array_length_from_uniform_options.cc
writer/array_length_from_uniform_options.h
+ writer/ast_text_generator.cc
+ writer/ast_text_generator.h
writer/binding_point.h
writer/binding_remapper_options.cc
writer/binding_remapper_options.h
@@ -1110,10 +1112,10 @@
utils/unique_vector_test.cc
utils/vector_test.cc
writer/append_vector_test.cc
+ writer/ast_text_generator_test.cc
writer/check_supported_extensions_test.cc
writer/flatten_bindings_test.cc
writer/float_to_string_test.cc
- writer/text_generator_test.cc
)
# Noet, the source files are included here otherwise the cmd sources would not be included in the
diff --git a/src/tint/writer/ast_text_generator.cc b/src/tint/writer/ast_text_generator.cc
new file mode 100644
index 0000000..dc0530b
--- /dev/null
+++ b/src/tint/writer/ast_text_generator.cc
@@ -0,0 +1,42 @@
+// Copyright 2023 The Tint Authors.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#include "src/tint/writer/ast_text_generator.h"
+
+#include <algorithm>
+#include <limits>
+
+#include "src/tint/utils/map.h"
+
+namespace tint::writer {
+
+ASTTextGenerator::ASTTextGenerator(const Program* program)
+ : program_(program), builder_(ProgramBuilder::Wrap(program)) {}
+
+ASTTextGenerator::~ASTTextGenerator() = default;
+
+std::string ASTTextGenerator::UniqueIdentifier(const std::string& prefix) {
+ return builder_.Symbols().New(prefix).Name();
+}
+
+std::string ASTTextGenerator::StructName(const type::Struct* s) {
+ auto name = s->Name().Name();
+ if (name.size() > 1 && name[0] == '_' && name[1] == '_') {
+ name = utils::GetOrCreate(builtin_struct_names_, s,
+ [&] { return UniqueIdentifier(name.substr(2)); });
+ }
+ return name;
+}
+
+} // namespace tint::writer
diff --git a/src/tint/writer/ast_text_generator.h b/src/tint/writer/ast_text_generator.h
new file mode 100644
index 0000000..243458c
--- /dev/null
+++ b/src/tint/writer/ast_text_generator.h
@@ -0,0 +1,71 @@
+// Copyright 2023 The Tint Authors.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#ifndef SRC_TINT_WRITER_AST_TEXT_GENERATOR_H_
+#define SRC_TINT_WRITER_AST_TEXT_GENERATOR_H_
+
+#include <string>
+#include <unordered_map>
+#include <utility>
+#include <vector>
+
+#include "src/tint/program_builder.h"
+#include "src/tint/writer/text_generator.h"
+
+namespace tint::writer {
+
+/// Helper methods for generators which are creating text output
+class ASTTextGenerator : public TextGenerator {
+ public:
+ /// Constructor
+ /// @param program the program used by the generator
+ explicit ASTTextGenerator(const Program* program);
+ ~ASTTextGenerator();
+
+ /// @return a new, unique identifier with the given prefix.
+ /// @param prefix optional prefix to apply to the generated identifier. If
+ /// empty "tint_symbol" will be used.
+ std::string UniqueIdentifier(const std::string& prefix = "");
+
+ /// @param s the semantic structure
+ /// @returns the name of the structure, taking special care of builtin
+ /// structures that start with double underscores. If the structure is a
+ /// builtin, then the returned name will be a unique name without the leading
+ /// underscores.
+ std::string StructName(const type::Struct* s);
+
+ protected:
+ /// @returns the resolved type of the ast::Expression `expr`
+ /// @param expr the expression
+ const type::Type* TypeOf(const ast::Expression* expr) const { return builder_.TypeOf(expr); }
+
+ /// @returns the resolved type of the ast::TypeDecl `type_decl`
+ /// @param type_decl the type
+ const type::Type* TypeOf(const ast::TypeDecl* type_decl) const {
+ return builder_.TypeOf(type_decl);
+ }
+
+ /// The program
+ Program const* const program_;
+ /// A ProgramBuilder that thinly wraps program_
+ ProgramBuilder builder_;
+
+ private:
+ /// Map of builtin structure to unique generated name
+ std::unordered_map<const type::Struct*, std::string> builtin_struct_names_;
+};
+
+} // namespace tint::writer
+
+#endif // SRC_TINT_WRITER_AST_TEXT_GENERATOR_H_
diff --git a/src/tint/writer/text_generator_test.cc b/src/tint/writer/ast_text_generator_test.cc
similarity index 84%
rename from src/tint/writer/text_generator_test.cc
rename to src/tint/writer/ast_text_generator_test.cc
index 1bfa41f..d879f68 100644
--- a/src/tint/writer/text_generator_test.cc
+++ b/src/tint/writer/ast_text_generator_test.cc
@@ -12,29 +12,29 @@
// See the License for the specific language governing permissions and
// limitations under the License.
-#include "src/tint/writer/text_generator.h"
+#include "src/tint/writer/ast_text_generator.h"
#include "gtest/gtest.h"
namespace tint::writer {
namespace {
-TEST(TextGeneratorTest, UniqueIdentifier) {
+TEST(ASTTextGeneratorTest, UniqueIdentifier) {
Program program(ProgramBuilder{});
- TextGenerator gen(&program);
+ ASTTextGenerator gen(&program);
ASSERT_EQ(gen.UniqueIdentifier("ident"), "ident");
ASSERT_EQ(gen.UniqueIdentifier("ident"), "ident_1");
}
-TEST(TextGeneratorTest, UniqueIdentifier_ConflictWithExisting) {
+TEST(ASTTextGeneratorTest, UniqueIdentifier_ConflictWithExisting) {
ProgramBuilder builder;
builder.Symbols().Register("ident_1");
builder.Symbols().Register("ident_2");
Program program(std::move(builder));
- TextGenerator gen(&program);
+ ASTTextGenerator gen(&program);
ASSERT_EQ(gen.UniqueIdentifier("ident"), "ident");
ASSERT_EQ(gen.UniqueIdentifier("ident"), "ident_3");
diff --git a/src/tint/writer/glsl/generator_impl.cc b/src/tint/writer/glsl/generator_impl.cc
index 1bb2f85..537d328 100644
--- a/src/tint/writer/glsl/generator_impl.cc
+++ b/src/tint/writer/glsl/generator_impl.cc
@@ -254,7 +254,7 @@
}
GeneratorImpl::GeneratorImpl(const Program* program, const Version& version)
- : TextGenerator(program), version_(version) {}
+ : ASTTextGenerator(program), version_(version) {}
GeneratorImpl::~GeneratorImpl() = default;
diff --git a/src/tint/writer/glsl/generator_impl.h b/src/tint/writer/glsl/generator_impl.h
index 7f9e31c..23633ae 100644
--- a/src/tint/writer/glsl/generator_impl.h
+++ b/src/tint/writer/glsl/generator_impl.h
@@ -38,9 +38,9 @@
#include "src/tint/scope_stack.h"
#include "src/tint/utils/hash.h"
#include "src/tint/utils/string_stream.h"
+#include "src/tint/writer/ast_text_generator.h"
#include "src/tint/writer/glsl/generator.h"
#include "src/tint/writer/glsl/version.h"
-#include "src/tint/writer/text_generator.h"
// Forward declarations
namespace tint::sem {
@@ -75,7 +75,7 @@
const std::string& entry_point);
/// Implementation class for GLSL generator
-class GeneratorImpl : public TextGenerator {
+class GeneratorImpl : public ASTTextGenerator {
public:
/// Constructor
/// @param program the program to generate
diff --git a/src/tint/writer/hlsl/generator_impl.cc b/src/tint/writer/hlsl/generator_impl.cc
index 06a4d7c..d00859c 100644
--- a/src/tint/writer/hlsl/generator_impl.cc
+++ b/src/tint/writer/hlsl/generator_impl.cc
@@ -328,7 +328,7 @@
return result;
}
-GeneratorImpl::GeneratorImpl(const Program* program) : TextGenerator(program) {}
+GeneratorImpl::GeneratorImpl(const Program* program) : ASTTextGenerator(program) {}
GeneratorImpl::~GeneratorImpl() = default;
diff --git a/src/tint/writer/hlsl/generator_impl.h b/src/tint/writer/hlsl/generator_impl.h
index 2ae653c..3028853 100644
--- a/src/tint/writer/hlsl/generator_impl.h
+++ b/src/tint/writer/hlsl/generator_impl.h
@@ -38,8 +38,8 @@
#include "src/tint/sem/binding_point.h"
#include "src/tint/utils/hash.h"
#include "src/tint/writer/array_length_from_uniform_options.h"
+#include "src/tint/writer/ast_text_generator.h"
#include "src/tint/writer/hlsl/generator.h"
-#include "src/tint/writer/text_generator.h"
// Forward declarations
namespace tint::sem {
@@ -74,7 +74,7 @@
SanitizedResult Sanitize(const Program* program, const Options& options);
/// Implementation class for HLSL generator
-class GeneratorImpl : public TextGenerator {
+class GeneratorImpl : public ASTTextGenerator {
public:
/// Constructor
/// @param program the program to generate
diff --git a/src/tint/writer/msl/generator_impl.cc b/src/tint/writer/msl/generator_impl.cc
index b0799d4..3cf5b31 100644
--- a/src/tint/writer/msl/generator_impl.cc
+++ b/src/tint/writer/msl/generator_impl.cc
@@ -271,7 +271,7 @@
return result;
}
-GeneratorImpl::GeneratorImpl(const Program* program) : TextGenerator(program) {}
+GeneratorImpl::GeneratorImpl(const Program* program) : ASTTextGenerator(program) {}
GeneratorImpl::~GeneratorImpl() = default;
diff --git a/src/tint/writer/msl/generator_impl.h b/src/tint/writer/msl/generator_impl.h
index 0be80be..b9bd3501 100644
--- a/src/tint/writer/msl/generator_impl.h
+++ b/src/tint/writer/msl/generator_impl.h
@@ -42,8 +42,8 @@
#include "src/tint/sem/struct.h"
#include "src/tint/utils/string_stream.h"
#include "src/tint/writer/array_length_from_uniform_options.h"
+#include "src/tint/writer/ast_text_generator.h"
#include "src/tint/writer/msl/generator.h"
-#include "src/tint/writer/text_generator.h"
// Forward declarations
namespace tint::sem {
@@ -80,7 +80,7 @@
SanitizedResult Sanitize(const Program* program, const Options& options);
/// Implementation class for MSL generator
-class GeneratorImpl : public TextGenerator {
+class GeneratorImpl : public ASTTextGenerator {
public:
/// Constructor
/// @param program the program to generate
diff --git a/src/tint/writer/syntax_tree/generator_impl.cc b/src/tint/writer/syntax_tree/generator_impl.cc
index 56f7f57..e8e58a3 100644
--- a/src/tint/writer/syntax_tree/generator_impl.cc
+++ b/src/tint/writer/syntax_tree/generator_impl.cc
@@ -41,7 +41,7 @@
namespace tint::writer::syntax_tree {
-GeneratorImpl::GeneratorImpl(const Program* program) : TextGenerator(program) {}
+GeneratorImpl::GeneratorImpl(const Program* program) : ASTTextGenerator(program) {}
GeneratorImpl::~GeneratorImpl() = default;
diff --git a/src/tint/writer/syntax_tree/generator_impl.h b/src/tint/writer/syntax_tree/generator_impl.h
index dc2cf01..2473df2 100644
--- a/src/tint/writer/syntax_tree/generator_impl.h
+++ b/src/tint/writer/syntax_tree/generator_impl.h
@@ -36,12 +36,12 @@
#include "src/tint/program.h"
#include "src/tint/sem/struct.h"
#include "src/tint/utils/string_stream.h"
-#include "src/tint/writer/text_generator.h"
+#include "src/tint/writer/ast_text_generator.h"
namespace tint::writer::syntax_tree {
/// Implementation class for AST generator
-class GeneratorImpl : public TextGenerator {
+class GeneratorImpl : public ASTTextGenerator {
public:
/// Constructor
/// @param program the program
diff --git a/src/tint/writer/text_generator.cc b/src/tint/writer/text_generator.cc
index 4b0ab6a..89e1a6f 100644
--- a/src/tint/writer/text_generator.cc
+++ b/src/tint/writer/text_generator.cc
@@ -17,28 +17,14 @@
#include <algorithm>
#include <limits>
-#include "src/tint/utils/map.h"
+#include "src/tint/debug.h"
namespace tint::writer {
-TextGenerator::TextGenerator(const Program* program)
- : program_(program), builder_(ProgramBuilder::Wrap(program)) {}
+TextGenerator::TextGenerator() = default;
TextGenerator::~TextGenerator() = default;
-std::string TextGenerator::UniqueIdentifier(const std::string& prefix) {
- return builder_.Symbols().New(prefix).Name();
-}
-
-std::string TextGenerator::StructName(const type::Struct* s) {
- auto name = s->Name().Name();
- if (name.size() > 1 && name[0] == '_' && name[1] == '_') {
- name = utils::GetOrCreate(builtin_struct_names_, s,
- [&] { return UniqueIdentifier(name.substr(2)); });
- }
- return name;
-}
-
TextGenerator::LineWriter::LineWriter(TextBuffer* buf) : buffer(buf) {}
TextGenerator::LineWriter::LineWriter(LineWriter&& other) {
diff --git a/src/tint/writer/text_generator.h b/src/tint/writer/text_generator.h
index ad3eb80..8458db0 100644
--- a/src/tint/writer/text_generator.h
+++ b/src/tint/writer/text_generator.h
@@ -21,7 +21,6 @@
#include <vector>
#include "src/tint/diagnostic/diagnostic.h"
-#include "src/tint/program_builder.h"
#include "src/tint/utils/string_stream.h"
namespace tint::writer {
@@ -87,8 +86,7 @@
};
/// Constructor
- /// @param program the program used by the generator
- explicit TextGenerator(const Program* program);
+ TextGenerator();
~TextGenerator();
/// Increment the emitter indent level
@@ -102,18 +100,6 @@
/// @returns the list of diagnostics raised by the generator.
const diag::List& Diagnostics() const { return diagnostics_; }
- /// @return a new, unique identifier with the given prefix.
- /// @param prefix optional prefix to apply to the generated identifier. If
- /// empty "tint_symbol" will be used.
- std::string UniqueIdentifier(const std::string& prefix = "");
-
- /// @param s the semantic structure
- /// @returns the name of the structure, taking special care of builtin
- /// structures that start with double underscores. If the structure is a
- /// builtin, then the returned name will be a unique name without the leading
- /// underscores.
- std::string StructName(const type::Struct* s);
-
protected:
/// LineWriter is a helper that acts as a string buffer, who's content is
/// emitted to the TextBuffer as a single line on destruction.
@@ -183,16 +169,6 @@
TextBuffer* buffer_;
};
- /// @returns the resolved type of the ast::Expression `expr`
- /// @param expr the expression
- const type::Type* TypeOf(const ast::Expression* expr) const { return builder_.TypeOf(expr); }
-
- /// @returns the resolved type of the ast::TypeDecl `type_decl`
- /// @param type_decl the type
- const type::Type* TypeOf(const ast::TypeDecl* type_decl) const {
- return builder_.TypeOf(type_decl);
- }
-
/// @returns a new LineWriter, used for buffering and writing a line to
/// the end of #current_buffer_.
LineWriter line() { return LineWriter(current_buffer_); }
@@ -202,10 +178,6 @@
/// the end of `buffer`.
static LineWriter line(TextBuffer* buffer) { return LineWriter(buffer); }
- /// The program
- Program const* const program_;
- /// A ProgramBuilder that thinly wraps program_
- ProgramBuilder builder_;
/// Diagnostics generated by the generator
diag::List diagnostics_;
/// The buffer the TextGenerator is currently appending lines to
@@ -214,8 +186,6 @@
private:
/// The primary text buffer that the generator will emit
TextBuffer main_buffer_;
- /// Map of builtin structure to unique generated name
- std::unordered_map<const type::Struct*, std::string> builtin_struct_names_;
};
} // namespace tint::writer
diff --git a/src/tint/writer/wgsl/generator_impl.cc b/src/tint/writer/wgsl/generator_impl.cc
index 0d626f2..751d16ff 100644
--- a/src/tint/writer/wgsl/generator_impl.cc
+++ b/src/tint/writer/wgsl/generator_impl.cc
@@ -42,7 +42,7 @@
namespace tint::writer::wgsl {
-GeneratorImpl::GeneratorImpl(const Program* program) : TextGenerator(program) {}
+GeneratorImpl::GeneratorImpl(const Program* program) : ASTTextGenerator(program) {}
GeneratorImpl::~GeneratorImpl() = default;
diff --git a/src/tint/writer/wgsl/generator_impl.h b/src/tint/writer/wgsl/generator_impl.h
index 5d69821..6c67d79 100644
--- a/src/tint/writer/wgsl/generator_impl.h
+++ b/src/tint/writer/wgsl/generator_impl.h
@@ -36,12 +36,12 @@
#include "src/tint/program.h"
#include "src/tint/sem/struct.h"
#include "src/tint/utils/string_stream.h"
-#include "src/tint/writer/text_generator.h"
+#include "src/tint/writer/ast_text_generator.h"
namespace tint::writer::wgsl {
/// Implementation class for WGSL generator
-class GeneratorImpl : public TextGenerator {
+class GeneratorImpl : public ASTTextGenerator {
public:
/// Constructor
/// @param program the program