67 lines
2.1 KiB
C++
67 lines
2.1 KiB
C++
#ifndef MALACHSCRIPT_LEXER_HPP
|
|
#define MALACHSCRIPT_LEXER_HPP
|
|
|
|
#include <string_view>
|
|
#include "../../Diagnostics/Diagnostics.hpp"
|
|
#include "../../Utils/MemoryPool.hpp"
|
|
#include "LexToken.hpp"
|
|
|
|
namespace MalachScript::Parser {
|
|
class Lexer {
|
|
public:
|
|
Lexer(const char8_t* scriptName, const char8_t* script, Diagnostics::Diagnostics* diag)
|
|
: Lexer(std::u8string_view(scriptName), std::u8string_view(script), diag) {}
|
|
Lexer(std::u8string_view scriptName, std::u8string_view script, Diagnostics::Diagnostics* diag)
|
|
: _scriptName(scriptName), _script(script), _scriptLength(script.size()), _diagnostics(diag) {}
|
|
const LexToken* Lex();
|
|
|
|
private:
|
|
std::u8string_view _scriptName;
|
|
std::u8string_view _script;
|
|
size_t _position = -1;
|
|
size_t _scriptLength;
|
|
Diagnostics::Diagnostics* _diagnostics;
|
|
|
|
Utils::MemoryPool<2048, 1024> _allocator;
|
|
|
|
inline char8_t Consume() {
|
|
if (++_position >= _scriptLength) {
|
|
return '\0';
|
|
}
|
|
return _script[_position];
|
|
}
|
|
|
|
inline void Progress(size_t steps = 1) { _position += steps; }
|
|
|
|
inline char8_t Peek(size_t offset = 1) {
|
|
auto pos = _position + offset;
|
|
if (pos >= _scriptLength) {
|
|
return '\0';
|
|
}
|
|
return _script[pos];
|
|
}
|
|
|
|
LexToken* LexNext();
|
|
LexToken* LexNumerical(char8_t);
|
|
LexToken* LexDecimal(uint64_t initial);
|
|
IntegerLiteral* LexHexadecimal();
|
|
IntegerLiteral* LexOctal();
|
|
IntegerLiteral* LexBinary();
|
|
|
|
StringLiteral* LexString(char8_t opening, bool heredoc);
|
|
LexToken* LexKeywordOrIdentifier();
|
|
|
|
static bool IsAlphaNumericalOrUnderscore(char8_t c);
|
|
|
|
template <class T, class... parameters> inline T* Create(parameters... args) {
|
|
return _allocator.Create<T>(args...);
|
|
}
|
|
|
|
inline void LogError(Diagnostics::DiagnosticType type, TextSpan span) {
|
|
_diagnostics->LogError(type, _scriptName, span);
|
|
}
|
|
};
|
|
}
|
|
|
|
#endif // MALACHSCRIPT_LEXER_HPP
|