[spirv-reader] Update to create BlockStatements

This CL updates the SPIR-V Reader to create BlockStatements instead of
StatementLists.

Bug: tint:136
Change-Id: I957019446ca00306187de701f86ae3e0dd5c5eb8
Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/25740
Reviewed-by: Sarah Mashayekhi <sarahmashay@google.com>
This commit is contained in:
dan sinclair 2020-07-27 15:25:00 +00:00 committed by Sarah Mashayekhi
parent f751501c35
commit cfdc5995ec
4 changed files with 25 additions and 20 deletions

View File

@ -51,6 +51,10 @@ class BlockStatement : public Statement {
const ast::Statement* last() const {
return statements_.empty() ? nullptr : statements_.back().get();
}
/// @returns the last statement in the block or nullptr if block empty
ast::Statement* last() {
return statements_.empty() ? nullptr : statements_.back().get();
}
/// Retrieves the statement at |idx|
/// @param idx the index. The index is not bounds checked.

View File

@ -460,7 +460,7 @@ FunctionEmitter::StatementBlock::StatementBlock(
const Construct* construct,
uint32_t end_id,
CompletionAction completion_action,
ast::StatementList statements,
std::unique_ptr<ast::BlockStatement> statements,
std::unique_ptr<ast::CaseStatementList> cases)
: construct_(construct),
end_id_(end_id),
@ -476,7 +476,8 @@ void FunctionEmitter::PushNewStatementBlock(const Construct* construct,
uint32_t end_id,
CompletionAction action) {
statements_stack_.emplace_back(
StatementBlock{construct, end_id, action, ast::StatementList{}, nullptr});
StatementBlock{construct, end_id, action,
std::make_unique<ast::BlockStatement>(), nullptr});
}
void FunctionEmitter::PushGuard(const std::string& guard_name,
@ -509,9 +510,9 @@ void FunctionEmitter::PushTrueGuard(uint32_t end_id) {
});
}
const ast::StatementList& FunctionEmitter::ast_body() {
const ast::BlockStatement* FunctionEmitter::ast_body() {
assert(!statements_stack_.empty());
return statements_stack_[0].statements_;
return statements_stack_[0].statements_.get();
}
ast::Statement* FunctionEmitter::AddStatement(
@ -519,7 +520,7 @@ ast::Statement* FunctionEmitter::AddStatement(
assert(!statements_stack_.empty());
auto* result = statement.get();
if (result != nullptr) {
statements_stack_.back().statements_.emplace_back(std::move(statement));
statements_stack_.back().statements_->append(std::move(statement));
}
return result;
}
@ -527,8 +528,8 @@ ast::Statement* FunctionEmitter::AddStatement(
ast::Statement* FunctionEmitter::LastStatement() {
assert(!statements_stack_.empty());
const auto& statement_list = statements_stack_.back().statements_;
assert(!statement_list.empty());
return statement_list.back().get();
assert(!statement_list->empty());
return statement_list->last();
}
bool FunctionEmitter::Emit() {
@ -554,7 +555,7 @@ bool FunctionEmitter::Emit() {
"element but has "
<< statements_stack_.size();
}
ast::StatementList body(std::move(statements_stack_[0].statements_));
auto body = std::move(statements_stack_[0].statements_);
parser_impl_.get_module().functions().back()->set_body(std::move(body));
// Maintain the invariant by repopulating the one and only element.
statements_stack_.clear();
@ -1984,7 +1985,7 @@ bool FunctionEmitter::EmitIfStart(const BlockInfo& block_info) {
// Push the else clause onto the stack first.
PushNewStatementBlock(construct, else_end, [if_stmt](StatementBlock* s) {
// Only set the else-clause if there are statements to fill it.
if (!s->statements_.empty()) {
if (!s->statements_->empty()) {
// The "else" consists of the statement list from the top of statments
// stack, without an elseif condition.
ast::ElseStatementList else_stmts;
@ -2136,8 +2137,8 @@ bool FunctionEmitter::EmitSwitchStart(const BlockInfo& block_info) {
if ((default_info == clause_heads[i]) && has_selectors &&
construct->ContainsPos(default_info->pos)) {
// Generate a default clause with a just fallthrough.
ast::StatementList stmts;
stmts.emplace_back(std::make_unique<ast::FallthroughStatement>());
auto stmts = std::make_unique<ast::BlockStatement>();
stmts->append(std::make_unique<ast::FallthroughStatement>());
auto case_stmt = std::make_unique<ast::CaseStatement>();
case_stmt->set_body(std::move(stmts));
cases->emplace_back(std::move(case_stmt));
@ -2362,13 +2363,13 @@ std::unique_ptr<ast::Statement> FunctionEmitter::MakeSimpleIf(
auto if_stmt = std::make_unique<ast::IfStatement>();
if_stmt->set_condition(std::move(condition));
if (then_stmt != nullptr) {
ast::StatementList stmts;
stmts.emplace_back(std::move(then_stmt));
auto stmts = std::make_unique<ast::BlockStatement>();
stmts->append(std::move(then_stmt));
if_stmt->set_body(std::move(stmts));
}
if (else_stmt != nullptr) {
ast::StatementList stmts;
stmts.emplace_back(std::move(else_stmt));
auto stmts = std::make_unique<ast::BlockStatement>();
stmts->append(std::move(else_stmt));
ast::ElseStatementList else_stmts;
else_stmts.emplace_back(
std::make_unique<ast::ElseStatement>(nullptr, std::move(stmts)));

View File

@ -293,7 +293,7 @@ class FunctionEmitter {
/// Returns the body of the function. It is the bottom of the statement
/// stack.
/// @returns the body of the function.
const ast::StatementList& ast_body();
const ast::BlockStatement* ast_body();
/// Records failure.
/// @returns a FailStream on which to emit diagnostics.
@ -713,7 +713,7 @@ class FunctionEmitter {
StatementBlock(const Construct* construct,
uint32_t end_id,
CompletionAction completion_action,
ast::StatementList statements,
std::unique_ptr<ast::BlockStatement> statements,
std::unique_ptr<ast::CaseStatementList> cases);
StatementBlock(StatementBlock&&);
~StatementBlock();
@ -730,7 +730,7 @@ class FunctionEmitter {
// Only one of |statements| or |cases| is active.
// The list of statements being built, if this construct is not a switch.
ast::StatementList statements_;
std::unique_ptr<ast::BlockStatement> statements_;
// The list of switch cases being built, if this construct is a switch.
// The algorithm will cache a pointer to the vector. We want that pointer
// to be stable no matter how |statements_stack_| is resized. That's

View File

@ -70,9 +70,9 @@ using SpvParserTest = SpvParserTestBase<::testing::Test>;
/// Returns the string dump of a function body.
/// @param body the statement in the body
/// @returnss the string dump of a function body.
inline std::string ToString(const ast::StatementList& body) {
inline std::string ToString(const ast::BlockStatement* body) {
std::ostringstream outs;
for (const auto& stmt : body) {
for (const auto& stmt : *body) {
stmt->to_str(outs, 0);
}
return outs.str();