1 // =================================
  2 // Copyright (c) 2020 Seppo Laakko
  3 // Distributed under the MIT license
  4 // =================================
  5 
  6 #ifndef SNG2HTML_SNG2HTML_LEXER_FILEINCLUDED
  7 #define SNG2HTML_SNG2HTML_LEXER_FILEINCLUDED
  8 #include <sng2html/sng2html/RegEx.hpp>
  9 #include <sng2html/sng2html/LexerContext.hpp>
 10 #include <soulng/cppcode/Statement.hpp>
 11 #include <soulng/cppcode/Type.hpp>
 12 #include <soulng/util/CodeFormatter.hpp>
 13 #include <memory>
 14 #include <string>
 15 #include <map>
 16 #include <unordered_map>
 17 
 18 namespace sng2html { namespace sng2html {
 19 
 20 const char* LexerGeneratorVersionStr();
 21 
 22 using namespace soulng::util;
 23 
 24 class Tokens;
 25 
 26 class LexerFile;
 27 
 28 class Declaration 
 29 {
 30 public:
 31     Declaration(const std::u32string& name_);
 32     virtual ~Declaration();
 33     const std::u32string& Name() const { return name; }
 34     virtual void AddToLexerFile(LexerFile& lexerFile) {}
 35 private:
 36     std::u32string name;
 37 };
 38 
 39 class ClassMap public Declaration
 40 {
 41 public:
 42     ClassMap(const std::u32string& name_);
 43 };
 44 
 45 class Prefix public Declaration
 46 {
 47 public:
 48     Prefix(const std::u32string& prefix_);
 49 };
 50 
 51 class IncludeDeclaration public Declaration
 52 {
 53 public:
 54     IncludeDeclaration(const std::u32string& header_);
 55     const std::u32string& Header() const { return header; }
 56 private:
 57     std::u32string header;
 58 };
 59 
 60 struct Token 
 61 {
 62     Token();
 63     Token(const std::u32string& name_const std::string& info_);
 64     std::u32string name;
 65     std::string info;
 66 };
 67 
 68 class Tokens public Declaration
 69 {
 70 public:
 71     Tokens(const std::u32string& name_);
 72     void Add(const Token& token);
 73 private:
 74     std::vector<Token> tokens;
 75 };
 76 
 77 class Keyword 
 78 {
 79 public:
 80     Keyword(const std::u32string& kw_const std::u32string& token_);
 81     std::u32string kw;
 82     std::u32string token;
 83 };
 84 
 85 class Keywords public Declaration
 86 {
 87 public:
 88     Keywords(const std::u32string& name_);
 89     void Add(Keyword* keyword);
 90     void AddToLexerFile(LexerFile& lexerFile) override;
 91     std::u32string GetKeyword(const std::u32string& tokenId) const;
 92 private:
 93     std::vector<std::std::unique_ptr<Keyword>>keywords;
 94     std::map<std::u32stringstd::u32string> keywordMap;
 95 };
 96 
 97 class Expression 
 98 {
 99 public:
100     Expression(int index_const std::u32string& id_const std::u32string& value_int line_);
101     int Index() const { return index; }
102     const std::u32string& Id() const { return id; }
103     const std::u32string& Value() const { return value; }
104     int Line() const { return line; }
105     void Parse(LexerContext& lexerContext);
106     void SetRegEx(RegExpression* regEx_) { regEx.reset(regEx_); }
107     RegExpression* RegEx() const { return regEx.get(); }
108 private:
109     int index;
110     std::u32string id;
111     std::u32string value;
112     int line;
113     std::unique_ptr<RegExpression> regEx;
114 };
115 
116 class Expressions public Declaration
117 {
118 public:
119     Expressions();
120     void Add(Expression* expression);
121     Expression* Get(const std::u32string& id) const;
122     void AddToLexerFile(LexerFile& lexerFile) override;
123     void Parse(LexerContext& lexerContext);
124 private:
125     std::vector<std::std::unique_ptr<Expression>>expressions;
126     std::map<std::u32stringint> exprMap;
127 };
128 
129 class LexerVariable 
130 {
131 public:
132     LexerVariable(soulng::cppcode::TypeId* type_const std::u32string& name_);
133     soulng::cppcode::TypeId* GetType() const { return type.get(); }
134     const std::u32string& Name() const { return name; }
135 private:
136     std::unique_ptr<soulng::cppcode::TypeId> type;
137     std::u32string name;
138 };
139 
140 class LexerStatement 
141 {
142 public:
143     LexerStatement(const std::u32string& expr_soulng::cppcode::CompoundStatement* stmt_int action_int line_);
144     void SetIndex(int index_) { index = index_; }
145     int Index() const { return index; }
146     const std::u32string& Expr() const { return expr; }
147     soulng::cppcode::CompoundStatement* Code() const { return stmt.get(); }
148     bool Retract() const { return retract; }
149     int Action() const { return action; }
150     int Line() const { return line; }
151     const std::u32string& TokenId() const { return tokenId; }
152     void Parse(LexerContext& lexerContext);
153     RegExpression* RegEx() const { return regEx.get(); }
154 private:
155     int index;
156     std::u32string expr;
157     std::u32string tokenId;
158     std::unique_ptr<soulng::cppcode::CompoundStatement> stmt;
159     std::unique_ptr<RegExpression> regEx;
160     bool retract;
161     int action;
162     int line;
163 };
164 
165 class Action 
166 {
167 public:
168     Action(int id_soulng::cppcode::CompoundStatement* stmt_);
169     int Id() const { return id; }
170     soulng::cppcode::CompoundStatement* Code() const { return stmt.get(); }
171 private:
172     int id;
173     std::unique_ptr<soulng::cppcode::CompoundStatement> stmt;
174 };
175 
176 class Actions public Declaration
177 {
178 public:
179     Actions();
180     void Add(Action* action);
181     Action* Get(int id) const;
182 private:
183     std::vector<std::std::unique_ptr<Action>>actions;
184     std::map<intAction*> actionMap;
185 };
186 
187 class Lexer public Declaration
188 {
189 public:
190     Lexer(const std::u32string& api_const std::u32string& name_);
191     void AddStatement(LexerStatement* stmt);
192     LexerStatement* GetStatement(const std::u32string& tokenId) const;
193     void AddVariable(LexerVariable* variable);
194     void AddAction(Action* action);
195     void AddToLexerFile(LexerFile& lexerFile) override;
196     void Parse(LexerContext& lexerContext);
197 private:
198     std::u32string api;
199     std::vector<std::std::unique_ptr<LexerStatement>>statements;
200     std::vector<std::std::unique_ptr<LexerVariable>>variables;
201     Actions actions;
202     std::unordered_map<std::u32stringLexerStatement*> lexerStatementMap;
203 };
204 
205 class LexerFile 
206 {
207 public:
208     LexerFile();
209     void Accept(Visitor& visitor);
210     void Add(Declaration* declaration);
211     Keywords* GetKeywords() const { return keywords; }
212     void SetKeywords(Keywords* keywords_) { keywords = keywords_; }
213     Expressions* GetExpressions() const { return expressions; }
214     void SetExpressions(Expressions* expressions_) { expressions = expressions_; }
215     Lexer* GetLexer() const { return lexer; }
216     void SetLexer(Lexer* lexer_) { lexer = lexer_; }
217     void Parse(LexerContext& lexerContext);
218 private:
219     std::vector<std::std::unique_ptr<Declaration>>declarations;
220     Keywords* keywords;
221     Lexer* lexer;
222     Expressions* expressions;
223 };
224 
225 } } // namespace sng2html::sng2html
226 
227 #endif // SNG2HTML_SNG2HTML_LEXER_FILEINCLUDED