const {commaSep1} = require('./grammar/utils.js');
const types = require('./grammar/types.js');
const expressions = require('./grammar/expressions.js');
const functions = require('./grammar/functions.js');
const statements = require('./grammar/statements.js');
module.exports = grammar({
name: 'func',
extras: $ => [
/\s/,
$.comment,
],
word: $ => $.identifier,
rules: {
translation_unit: $ => repeat($._top_level_item),
_top_level_item: $ => choice(
$.function_definition,
$.include_directive,
$.pragma_directive,
$.global_var_declarations,
$.const_var_declarations,
),
include_directive: $ => seq(
'#include',
alias($._string_literal, $.include_path),
';',
),
pragma_directive: $ => seq(
'#pragma',
choice('version', 'not-version', 'test-version-set'),
optional(alias(/(\^|<=|>=|<|>|=)/, $.version_operator)),
optional('"'),
alias(/\d/, $.major_version),
optional(
seq(
'.',
alias(/\d/, $.minor_version),
optional(seq('.', alias(/\d/, $.patch_version))),
),
),
optional('"'),
';',
),
global_var_declarations: $ => seq(
'global',
commaSep1($._global_var_declaration),
';',
),
const_var_declarations: $ => seq(
'const',
optional(field('type', $._type)),
commaSep1($._const_var_declaration),
';',
),
_global_var_declaration: $ => seq(
field('type', optional($._type)),
field('name', $.identifier),
),
_const_var_declaration: $ => seq(
field('name', $.identifier),
'=',
field('value', $._expression),
),
...types,
...expressions,
...functions,
...statements,
number: _ => token(seq(
optional('-'),
choice(
seq('0x', /[0-9a-fA-F]+/),
/[0-9]+/,
),
)),
string: $ => choice(
$._string_literal,
$._raw_slice_const,
$._slice_const_address,
$._int_const_hex,
$._string_sha_first_32,
$._string_sha_256,
$._string_crc_32,
),
_string_literal: _ => /"[^"]*"/,
_raw_slice_const: $ => seq($._string_literal, alias('s', $.string_type)),
_slice_const_address: $ => seq($._string_literal, alias('a', $.string_type)),
_int_const_hex: $ => seq($._string_literal, alias('u', $.string_type)),
_string_sha_first_32: $ => seq($._string_literal, alias('h', $.string_type)),
_string_sha_256: $ => seq($._string_literal, alias('H', $.string_type)),
_string_crc_32: $ => seq($._string_literal, alias('c', $.string_type)),
identifier: _ => /(`.*`)|([a-zA-Z_](\w|['?:])+)|([a-zA-Z])/,
underscore: _ => '_',
comment: _ => {
let multiline_comment = seq('{-', /[^-]*-+([^-}][^-]*-+)*/, '}'); for (let i = 0; i < 5; i++) {
multiline_comment = seq('{-', repeat(choice(/[^-{]/, /-[^}]/, /\{[^-]/, multiline_comment)), '-}');
}
return token(choice(
seq(';;', /[^\n]*/), multiline_comment,
));
},
},
});