#include "tree_sitter/parser.h"
enum TokenType {
FLOAT_LITERAL,
IMAGINARY_LITERAL,
INTERPOLATION_CONTENT,
ERROR_SENTINEL, };
void *tree_sitter_qsharp_external_scanner_create(void) { return NULL; }
void tree_sitter_qsharp_external_scanner_destroy(void *payload) {
(void)payload;
}
unsigned tree_sitter_qsharp_external_scanner_serialize(void *payload,
char *buffer) {
(void)payload;
(void)buffer;
return 0;
}
void tree_sitter_qsharp_external_scanner_deserialize(void *payload,
const char *buffer,
unsigned length) {
(void)payload;
(void)buffer;
(void)length;
}
static inline void advance(TSLexer *lexer) { lexer->advance(lexer, false); }
static inline bool is_whitespace(int32_t c) {
return (c >= 0x09 && c <= 0x0D) || c == ' ' || c == 0x85 || c == 0xA0 ||
c == 0x1680 || (c >= 0x2000 && c <= 0x200A) || c == 0x2028 ||
c == 0x2029 || c == 0x202F || c == 0x205F || c == 0x3000;
}
static inline bool is_digit(int32_t c) {
return (c >= '0' && c <= '9') ? true : false;
}
static void skip_digits(TSLexer *lexer) {
while (!lexer->eof(lexer) &&
(is_digit(lexer->lookahead) || lexer->lookahead == '_')) {
advance(lexer);
}
}
static bool scan_exponent(TSLexer *lexer) {
if (lexer->eof(lexer)) {
return false;
}
if (lexer->lookahead != 'e' && lexer->lookahead != 'E') {
return false;
}
advance(lexer);
if (!lexer->eof(lexer) &&
(lexer->lookahead == '+' || lexer->lookahead == '-')) {
advance(lexer);
}
if (lexer->eof(lexer) || !is_digit(lexer->lookahead)) {
return false;
}
skip_digits(lexer);
return true;
}
static bool scan_interpolation_content(TSLexer *lexer) {
bool has_content = false;
while (!lexer->eof(lexer) && lexer->lookahead != '"' &&
lexer->lookahead != '{') {
if (lexer->lookahead == '\\') {
advance(lexer);
if (lexer->eof(lexer)) {
break;
}
}
advance(lexer);
has_content = true;
}
if (!has_content) {
return false;
}
lexer->mark_end(lexer);
lexer->result_symbol = INTERPOLATION_CONTENT;
return true;
}
bool tree_sitter_qsharp_external_scanner_scan(void *payload, TSLexer *lexer,
const bool *valid_symbols) {
(void)payload;
if (valid_symbols[ERROR_SENTINEL]) {
return false;
}
if (valid_symbols[INTERPOLATION_CONTENT]) {
return scan_interpolation_content(lexer);
}
if (!valid_symbols[FLOAT_LITERAL] && !valid_symbols[IMAGINARY_LITERAL]) {
return false;
}
while (!lexer->eof(lexer) && is_whitespace(lexer->lookahead)) {
lexer->advance(lexer, true);
}
if (lexer->eof(lexer) || !is_digit(lexer->lookahead)) {
return false;
}
skip_digits(lexer);
bool has_dot = false;
bool has_exp = false;
if (!lexer->eof(lexer) && lexer->lookahead == '.') {
lexer->mark_end(lexer);
advance(lexer);
if (lexer->lookahead == '.') {
return false; }
has_dot = true;
skip_digits(lexer);
}
has_exp = scan_exponent(lexer);
if (!has_dot && !has_exp) {
return false;
}
if (!lexer->eof(lexer) && lexer->lookahead == 'i') {
if (!valid_symbols[IMAGINARY_LITERAL]) {
return false;
}
advance(lexer);
lexer->mark_end(lexer);
lexer->result_symbol = IMAGINARY_LITERAL;
return true;
}
if (!lexer->eof(lexer) && lexer->lookahead == 'L') {
return false;
}
if (!valid_symbols[FLOAT_LITERAL]) {
return false;
}
lexer->mark_end(lexer);
lexer->result_symbol = FLOAT_LITERAL;
return true;
}