1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-27 03:57:44 +00:00

LibJS: Allow multiple labels on the same statement

Since there are only a number of statements where labels can actually be
used we now also only store labels when necessary.
Also now tracks the first continue usage of a label since this might not
be valid but that can only be determined after we have parsed the
statement.
Also ensures the correct error does not get wiped by load_state.
This commit is contained in:
davidot 2021-09-18 23:01:54 +02:00 committed by Linus Groh
parent bfc1b4ba61
commit 79caca8ca2
7 changed files with 194 additions and 47 deletions

View file

@ -80,13 +80,22 @@ public:
: ASTNode(source_range)
{
}
};
HashTable<FlyString> const& labels() const { return m_labels; }
void add_label(FlyString label) { m_labels.set(move(label)); }
bool has_label(FlyString const& label) const { return m_labels.contains(label); }
class LabelableStatement : public Statement {
public:
using Statement::Statement;
Vector<FlyString> const& labels() const { return m_labels; }
virtual void add_label(FlyString string) { m_labels.append(move(string)); }
protected:
HashTable<FlyString> m_labels;
Vector<FlyString> m_labels;
};
class IterationStatement : public LabelableStatement {
public:
using LabelableStatement::LabelableStatement;
};
class EmptyStatement final : public Statement {
@ -128,7 +137,7 @@ private:
NonnullRefPtr<Expression> m_expression;
};
class ScopeNode : public Statement {
class ScopeNode : public LabelableStatement {
public:
template<typename T, typename... Args>
T& append(SourceRange range, Args&&... args)
@ -156,7 +165,7 @@ public:
protected:
explicit ScopeNode(SourceRange source_range)
: Statement(source_range)
: LabelableStatement(source_range)
{
}
@ -514,10 +523,10 @@ private:
RefPtr<Statement> m_alternate;
};
class WhileStatement final : public Statement {
class WhileStatement final : public IterationStatement {
public:
WhileStatement(SourceRange source_range, NonnullRefPtr<Expression> test, NonnullRefPtr<Statement> body)
: Statement(source_range)
: IterationStatement(source_range)
, m_test(move(test))
, m_body(move(body))
{
@ -535,10 +544,10 @@ private:
NonnullRefPtr<Statement> m_body;
};
class DoWhileStatement final : public Statement {
class DoWhileStatement final : public IterationStatement {
public:
DoWhileStatement(SourceRange source_range, NonnullRefPtr<Expression> test, NonnullRefPtr<Statement> body)
: Statement(source_range)
: IterationStatement(source_range)
, m_test(move(test))
, m_body(move(body))
{
@ -576,10 +585,10 @@ private:
NonnullRefPtr<Statement> m_body;
};
class ForStatement final : public Statement {
class ForStatement final : public IterationStatement {
public:
ForStatement(SourceRange source_range, RefPtr<ASTNode> init, RefPtr<Expression> test, RefPtr<Expression> update, NonnullRefPtr<Statement> body)
: Statement(source_range)
: IterationStatement(source_range)
, m_init(move(init))
, m_test(move(test))
, m_update(move(update))
@ -603,10 +612,10 @@ private:
NonnullRefPtr<Statement> m_body;
};
class ForInStatement final : public Statement {
class ForInStatement final : public IterationStatement {
public:
ForInStatement(SourceRange source_range, NonnullRefPtr<ASTNode> lhs, NonnullRefPtr<Expression> rhs, NonnullRefPtr<Statement> body)
: Statement(source_range)
: IterationStatement(source_range)
, m_lhs(move(lhs))
, m_rhs(move(rhs))
, m_body(move(body))
@ -626,10 +635,10 @@ private:
NonnullRefPtr<Statement> m_body;
};
class ForOfStatement final : public Statement {
class ForOfStatement final : public IterationStatement {
public:
ForOfStatement(SourceRange source_range, NonnullRefPtr<ASTNode> lhs, NonnullRefPtr<Expression> rhs, NonnullRefPtr<Statement> body)
: Statement(source_range)
: IterationStatement(source_range)
, m_lhs(move(lhs))
, m_rhs(move(rhs))
, m_body(move(body))
@ -1498,10 +1507,10 @@ private:
NonnullRefPtr<BlockStatement> m_body;
};
class TryStatement final : public Statement {
class TryStatement final : public LabelableStatement {
public:
TryStatement(SourceRange source_range, NonnullRefPtr<BlockStatement> block, RefPtr<CatchClause> handler, RefPtr<BlockStatement> finalizer)
: Statement(source_range)
: LabelableStatement(source_range)
, m_block(move(block))
, m_handler(move(handler))
, m_finalizer(move(finalizer))
@ -1515,6 +1524,7 @@ public:
virtual void dump(int indent) const override;
virtual Value execute(Interpreter&, GlobalObject&) const override;
virtual void generate_bytecode(Bytecode::Generator&) const override;
void add_label(FlyString string) override;
private:
NonnullRefPtr<BlockStatement> m_block;
@ -1560,10 +1570,10 @@ private:
NonnullRefPtrVector<Statement> m_consequent;
};
class SwitchStatement final : public Statement {
class SwitchStatement final : public LabelableStatement {
public:
SwitchStatement(SourceRange source_range, NonnullRefPtr<Expression> discriminant, NonnullRefPtrVector<SwitchCase> cases)
: Statement(source_range)
: LabelableStatement(source_range)
, m_discriminant(move(discriminant))
, m_cases(move(cases))
{