ppc-lang/include/compiler/treeifier/ast.hh

124 lines
3.8 KiB
C++
Raw Normal View History

2022-09-27 11:09:02 +00:00
#pragma once
#include <string>
2022-10-04 13:00:18 +00:00
#include <set>
2022-09-27 11:09:02 +00:00
#include <unordered_map>
#include <memory>
#include "compiler/treeifier/tokenizer.hh"
#include "utils/data.hh"
#include "lang/common.hh"
using namespace std::string_literals;
using namespace ppc;
2022-10-04 20:45:08 +00:00
using namespace ppc::lang;
2022-10-04 13:00:18 +00:00
using namespace ppc::messages;
2022-09-27 11:09:02 +00:00
namespace ppc::comp::tree::ast {
2022-10-04 13:00:18 +00:00
class parser_t;
class group_parser_t;
2022-10-09 13:34:02 +00:00
using parser_factory_t = parser_t *(*)();
using group_parser_factory_t = group_parser_t *(*)();
extern parser_factory_t glob_parser;
extern parser_factory_t identifier_parser;
extern parser_factory_t nmsp_parser;
extern group_parser_factory_t def_parser;
2022-10-09 11:18:38 +00:00
2022-10-04 13:00:18 +00:00
struct ast_ctx_t {
2022-09-27 11:09:02 +00:00
private:
2022-10-04 13:00:18 +00:00
struct parser_proxy_t {
private:
2022-10-09 11:18:38 +00:00
ast_ctx_t *parent;
2022-10-04 13:00:18 +00:00
public:
2022-10-09 11:18:38 +00:00
const parser_t &operator[](const std::string &name) const;
parser_proxy_t(ast_ctx_t *parent): parent(parent) { }
2022-10-04 13:00:18 +00:00
};
struct group_proxy_t {
private:
2022-10-09 11:18:38 +00:00
ast_ctx_t *parent;
2022-10-04 13:00:18 +00:00
public:
2022-10-09 11:18:38 +00:00
const group_parser_t &operator[](const std::string &name) const;
group_proxy_t(ast_ctx_t *parent): parent(parent) { }
2022-10-04 13:00:18 +00:00
};
2022-10-09 11:18:38 +00:00
std::unordered_map<std::string, const parser_t*> parsers;
std::set<const parser_t*> groups;
2022-10-04 13:00:18 +00:00
2022-10-09 13:34:02 +00:00
void add_parser(const parser_t *parser);
void add_parser(const group_parser_t *parser);
2022-09-27 11:09:02 +00:00
public:
2022-10-04 13:00:18 +00:00
msg_stack_t &messages;
std::vector<token_t> &tokens;
2022-10-09 11:18:38 +00:00
std::set<loc_namespace_name_t> imports;
loc_namespace_name_t nmsp;
2022-10-04 13:00:18 +00:00
2022-10-09 13:34:02 +00:00
void add_parser(parser_factory_t factory) { add_parser(factory()); }
void add_parser(group_parser_factory_t factory) { add_parser(factory()); }
ast_ctx_t &operator=(const ast_ctx_t &other) = delete;
2022-10-04 13:00:18 +00:00
const parser_proxy_t parser;
const group_proxy_t group;
2022-10-09 11:18:38 +00:00
ast_ctx_t &init() {
add_parser(glob_parser);
2022-10-09 13:34:02 +00:00
add_parser(identifier_parser);
add_parser(nmsp_parser);
add_parser(def_parser);
2022-10-09 11:18:38 +00:00
return *this;
}
2022-10-09 13:34:02 +00:00
bool parse(std::string parser, size_t &pi, data::map_t &out);
2022-10-09 11:18:38 +00:00
static bool parse(msg_stack_t &messages, std::vector<token_t> &tokens, data::map_t &out);
2022-10-09 13:34:02 +00:00
~ast_ctx_t();
2022-10-09 11:18:38 +00:00
ast_ctx_t(msg_stack_t &messages, std::vector<token_t> &tokens):
2022-10-04 13:00:18 +00:00
messages(messages),
tokens(tokens),
2022-10-09 11:18:38 +00:00
parser(this),
group(this) { }
2022-09-27 11:09:02 +00:00
};
2022-10-04 13:00:18 +00:00
class parser_t {
2022-10-09 11:18:38 +00:00
private:
std::string _name;
protected:
2022-10-04 13:00:18 +00:00
virtual bool parse(ast_ctx_t &ctx, size_t &res_i, data::map_t &out) const = 0;
2022-10-09 11:18:38 +00:00
public:
const std::string &name() const { return _name; }
2022-10-04 13:00:18 +00:00
bool operator()(ast_ctx_t &ctx, size_t &i, data::map_t &out) const {
2022-10-09 11:18:38 +00:00
data::map_t res;
out["$_name"] = _name;
2022-10-04 13:00:18 +00:00
return parse(ctx, i, out);
}
2022-10-09 11:18:38 +00:00
2022-10-09 13:34:02 +00:00
virtual ~parser_t() = default;
2022-10-09 11:18:38 +00:00
parser_t(const std::string &name): _name(name) { }
2022-10-04 13:00:18 +00:00
};
2022-09-27 11:09:02 +00:00
2022-10-04 13:00:18 +00:00
class group_parser_t : public parser_t {
private:
std::vector<std::pair<lang::namespace_name_t, parser_t*>> named_parsers;
std::vector<parser_t*> parsers;
public:
group_parser_t &add(parser_t &parser);
group_parser_t &add(parser_t &parser, const lang::namespace_name_t &name);
2022-09-27 11:09:02 +00:00
2022-10-04 13:00:18 +00:00
bool parse(ast_ctx_t &ctx, size_t &i, data::map_t &out) const;
2022-10-09 13:34:02 +00:00
group_parser_t(const std::string &name): parser_t(name) { }
2022-09-27 11:09:02 +00:00
};
2022-09-27 11:09:52 +00:00
2022-10-09 11:18:38 +00:00
namespace conv {
data::map_t identifier_to_map(const located_t<std::string> &loc);
located_t<std::string> map_to_identifier(const data::map_t &map);
data::map_t loc_to_map(const location_t &loc);
location_t map_to_loc(const data::map_t &map);
2022-10-04 13:00:18 +00:00
2022-10-09 11:18:38 +00:00
data::map_t nmsp_to_map(const loc_namespace_name_t &nmsp);
loc_namespace_name_t map_to_nmsp(const data::map_t &map);
}
2022-09-27 11:09:02 +00:00
}