#include "reader.hpp" #include "common.hpp" static bool is_digit(char32_t c) { return c >= '0' && c <= '9'; } static bool is_alpha(char32_t c) { return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z'); } static bool is_hex_digit(char32_t c) { return is_digit(c) || (c >= 'a' && c <= 'f') || (c >= 'A' && c <= 'F'); } static bool is_symbol_char(char32_t c) { static char valid_char[] = {'!', '$', '%', '&', '*', '+', '-', '.', '/', ':', '<', '=', '>', '?', '@', '^', '_', '~'}; if (is_digit(c)) return true; if (is_alpha(c)) return true; for (size_t i = 0; i < sizeof(valid_char); ++i) { if (char32_t(valid_char[i]) == c) return true; } return false; } static bool is_whitespace(char32_t c) { return c == ' ' || c == '\t' || c == '\v' || c == '\f'; } static bool is_brace(char32_t c) { return c == '[' || c == ']' || c == '(' || c == ')' || c == '{' || c == '}'; } static bool is_newline(char32_t c) { return c == '\r' || c == '\n'; } static bool is_separator(char32_t c) { return is_whitespace(c) || is_brace(c) || is_newline(c) || c == ';'; } #define EOS 0 Result Reader::read_one() { forward_whitespace(); auto saved_position = position_; if (is_numeric_start()) { auto res = read_number(); if (res.has_value()) return res; } else if (match("true") || match("false")) { auto res = read_bool(); if (res.has_value()) return res; } else if (is_string_start()) { return read_string(); } else if (match('(')) { return read_list(); } else if (match('[')) { return read_array(); } else if (match('{')) { return read_dict(); } position_ = saved_position; if (is_symbol_start()) { return read_symbol(); } return ErrorCode::ReadError; } Result Reader::read_multiple() { Value res = TRY(Nil::create(_arena)); while (1) { forward_whitespace(); if (is_eof()) { return reverse(_arena, res); } auto val = TRY(read_one()); res = Value(TRY(Pair::create(_arena, val, res))); } return ErrorCode::ReadError; }