1 #pragma once
2 
3 #include "Stage.h"
4 #include <cstddef>
5 #include <queue>
6 #include <rumur/rumur.h>
7 #include <vector>
8 
9 class ExplicitSemicolons : public IntermediateStage {
10 
11 private:
12   // does the next written character need to be a semicolon?
13   bool pending_semi = false;
14 
15   // buffered tokens we have not yet sent to the next stage
16   std::vector<Token> pending;
17 
18   // queued updates to .pending_semi
19   std::queue<bool> state;
20 
21 public:
22   explicit ExplicitSemicolons(Stage &next_);
23 
24   void process(const Token &t) final;
25 
26   // override visitors for all nodes that can have an omitted semicolon
27   void visit_aliasrule(const rumur::AliasRule &n) final;
28   void visit_constdecl(const rumur::ConstDecl &n) final;
29   void visit_function(const rumur::Function &n) final;
30   void visit_propertyrule(const rumur::PropertyRule &n) final;
31   void visit_ruleset(const rumur::Ruleset &n) final;
32   void visit_simplerule(const rumur::SimpleRule &n) final;
33   void visit_startstate(const rumur::StartState &n) final;
34   void visit_typedecl(const rumur::TypeDecl &n) final;
35   void visit_vardecl(const rumur::VarDecl &n) final;
36 
37   void finalise() final;
38 
39   virtual ~ExplicitSemicolons() = default;
40 
41 private:
42   void flush();
43 
44   // queue an update of .pending_semi = true
45   void set_pending_semi();
46 };
47