236 lines
6.8 KiB
C++
236 lines
6.8 KiB
C++
#ifndef SYNTAX_FOUNDATION_H
|
||
#define SYNTAX_FOUNDATION_H
|
||
|
||
#include "ast_foundation.h"
|
||
#include <QString>
|
||
|
||
namespace Load {
|
||
class DocIns;
|
||
}
|
||
|
||
namespace SyntaxX {
|
||
/**
|
||
* @brief 通用语法异常
|
||
*/
|
||
class SyntaxException : public Lex::WsBaseException {
|
||
private:
|
||
const Lex::Token ⌖
|
||
|
||
public:
|
||
SyntaxException(const Lex::Token &tins, const QString &simple);
|
||
virtual ~SyntaxException() = default;
|
||
|
||
virtual const Lex::Token &targetToken() const;
|
||
};
|
||
|
||
enum class Result { All, Part, Fail };
|
||
|
||
/**
|
||
* @brief 解析匹配规则
|
||
*/
|
||
class BaseRule {
|
||
public:
|
||
virtual ~BaseRule() = default;
|
||
|
||
/**
|
||
* @brief 转换成堆变量,持久化生命周期
|
||
* @return
|
||
*/
|
||
virtual BaseRule *toHeap() && = 0;
|
||
|
||
/**
|
||
* @brief 堆实例标志
|
||
* @return
|
||
*/
|
||
virtual bool heapMark() const = 0;
|
||
|
||
/**
|
||
* @brief 使用预读取方式匹配当前Token流,返回匹配结果
|
||
* @param port Token流
|
||
* @param start 起始Token索引
|
||
* @param count 本次匹配长度
|
||
* @return 匹配结果长度
|
||
*/
|
||
virtual QPair<uint, Result> match(Lex::TokenReader *port, uint start, uint count) const noexcept = 0;
|
||
|
||
/**
|
||
* @brief 解析Token流,构建AST
|
||
* @param port 输入端口
|
||
* @param start 父节点
|
||
*/
|
||
virtual void parse(Lex::TokenReader *port, Ast::ASTList *parent) = 0;
|
||
};
|
||
|
||
/**
|
||
* @brief Token匹配解析规则
|
||
*/
|
||
class TokenRule : public BaseRule {
|
||
private:
|
||
const Lex::TokenDef &token_type;
|
||
bool build_within_heap = false;
|
||
void *operator new(size_t s);
|
||
|
||
public:
|
||
explicit TokenRule(const Lex::TokenDef &def);
|
||
TokenRule *operator&() = delete;
|
||
|
||
virtual BaseRule *toHeap() && override;
|
||
virtual bool heapMark() const override;
|
||
|
||
virtual QPair<uint, Result> match(Lex::TokenReader *port, uint start, uint count) const noexcept override;
|
||
virtual void parse(Lex::TokenReader *port, Ast::ASTList *parent) override;
|
||
};
|
||
|
||
/**
|
||
* @brief 解析规则承载
|
||
*/
|
||
class ElmRule : public BaseRule {
|
||
private:
|
||
std::function<Ast::ASTList *(Lex::TokenReader *reader, Ast::ASTList *parent)> exec_store;
|
||
BaseRule *item_store;
|
||
|
||
public:
|
||
explicit ElmRule();
|
||
ElmRule(const ElmRule &) = delete;
|
||
ElmRule(const ElmRule &&) = delete;
|
||
virtual ~ElmRule();
|
||
|
||
void *operator new(size_t s) = delete;
|
||
ElmRule &operator=(const ElmRule &) = delete;
|
||
ElmRule &operator=(const ElmRule &&) = delete;
|
||
|
||
/**
|
||
* @brief 设置处理过程
|
||
* @param exec
|
||
*/
|
||
virtual void resetProcess(std::function<Ast::ASTList *(Lex::TokenReader *reader, Ast::ASTList *parent)> exec);
|
||
|
||
/**
|
||
* @brief 重置内部实际解析规则
|
||
* @param item
|
||
*/
|
||
void setRule(BaseRule &&item);
|
||
|
||
virtual QPair<uint, Result> match(Lex::TokenReader *port, uint start, uint count) const noexcept override;
|
||
virtual void parse(Lex::TokenReader *port, Ast::ASTList *parent) override;
|
||
|
||
// BaseRule interface
|
||
public:
|
||
virtual BaseRule *toHeap() && override;
|
||
virtual bool heapMark() const override;
|
||
};
|
||
|
||
/**
|
||
* @brief 序列解析规则
|
||
*/
|
||
class Seqs : public BaseRule {
|
||
private:
|
||
QList<BaseRule *> items_rule;
|
||
bool build_within_heap = false;
|
||
|
||
void *operator new(size_t s);
|
||
|
||
public:
|
||
Seqs();
|
||
template <class... Args> explicit Seqs(BaseRule *head, Args... args) : Seqs(std::forward<Args>(args)...) { items_rule.push_front(head); }
|
||
template <class... Args> explicit Seqs(BaseRule &&head, Args... args) : Seqs(std::forward<Args>(args)...) {
|
||
items_rule.push_front(std::move(head).toHeap());
|
||
}
|
||
Seqs(Seqs &&other);
|
||
virtual ~Seqs();
|
||
|
||
Seqs *operator&() = delete;
|
||
|
||
// BaseRule interface
|
||
public:
|
||
virtual BaseRule *toHeap() && override;
|
||
virtual bool heapMark() const override;
|
||
|
||
virtual QPair<uint, Result> match(Lex::TokenReader *port, uint start, uint count) const noexcept override;
|
||
virtual void parse(Lex::TokenReader *port, Ast::ASTList *parent) override;
|
||
};
|
||
|
||
/**
|
||
* @brief 多个分支,任意一个匹配都可以
|
||
*/
|
||
class Any : public BaseRule {
|
||
private:
|
||
QList<BaseRule *> items_rule;
|
||
bool build_within_heap = false;
|
||
|
||
void *operator new(size_t s);
|
||
|
||
public:
|
||
Any();
|
||
template <class... Args> explicit Any(BaseRule *head, Args... args) : Any(std::forward<Args>(args)...) { items_rule.push_front(head); }
|
||
template <class... Args> explicit Any(BaseRule &&head, Args... args) : Any(std::forward<Args>(args)...) {
|
||
items_rule.push_front(std::move(head).toHeap());
|
||
}
|
||
Any(Any &&other);
|
||
|
||
virtual ~Any();
|
||
|
||
Any *operator&() = delete;
|
||
|
||
// BaseRule interface
|
||
public:
|
||
virtual BaseRule *toHeap() && override;
|
||
virtual bool heapMark() const override;
|
||
|
||
virtual QPair<uint, Result> match(Lex::TokenReader *port, uint start, uint count) const noexcept override;
|
||
virtual void parse(Lex::TokenReader *port, Ast::ASTList *parent) override;
|
||
};
|
||
|
||
/**
|
||
* @brief 重复,指定匹配次数
|
||
*/
|
||
class Repeat : public BaseRule {
|
||
private:
|
||
BaseRule &item_store;
|
||
uint match_max, match_min;
|
||
bool build_within_heap = false;
|
||
|
||
void *operator new(size_t s);
|
||
|
||
public:
|
||
Repeat(BaseRule &&item, uint min = 1, uint max = UINT_MAX);
|
||
Repeat(BaseRule *item, uint min = 1, uint max = UINT_MAX);
|
||
|
||
Repeat *operator&() = delete;
|
||
|
||
// BaseRule interface
|
||
public:
|
||
virtual BaseRule *toHeap() && override;
|
||
virtual bool heapMark() const override;
|
||
|
||
virtual QPair<uint, Result> match(Lex::TokenReader *port, uint start, uint count) const noexcept override;
|
||
virtual void parse(Lex::TokenReader *port, Ast::ASTList *parent) override;
|
||
};
|
||
|
||
class Optional : public BaseRule {
|
||
private:
|
||
BaseRule &item_store;
|
||
bool build_within_heap = false;
|
||
|
||
void *operator new(size_t s);
|
||
|
||
public:
|
||
Optional(BaseRule *item);
|
||
Optional(BaseRule &&item);
|
||
|
||
Optional *operator&() = delete;
|
||
|
||
// BaseRule interface
|
||
public:
|
||
virtual BaseRule *toHeap() && override;
|
||
virtual bool heapMark() const override;
|
||
|
||
virtual QPair<uint, Result> match(Lex::TokenReader *port, uint start, uint count) const noexcept override;
|
||
virtual void parse(Lex::TokenReader *port, Ast::ASTList *parent) override;
|
||
};
|
||
|
||
typedef TokenRule T;
|
||
} // namespace SyntaxX
|
||
|
||
#endif // SYNTAX_FOUNDATION_H
|