tree-sitter / tree-sitter-rust

Rust grammar for tree-sitter
MIT License
340 stars 97 forks source link

Grammar railroad diagram #166

Closed mingodad closed 1 year ago

mingodad commented 1 year ago

Using this script https://github.com/mingodad/plgh/blob/main/json2ebnf.js (with quickjs) and with some manual fixes we can have a navigable railroad diagram.

Copy and paste the EBNF shown bellow on https://www.bottlecaps.de/rr/ui on the tab Edit Grammar the click on the tab View Diagram to see/download a navigable railroad diagram.

/*
Grammar originally from https://github.com/tree-sitter/tree-sitter-rust
Converted by excuting:
    qjs json2ebnf.js
Then manualy fixing the problems reported by https://www.bottlecaps.de/rr/ui in a way to allow visualization (correctnes is not the priority now)
*/
//
// EBNF to generate railroad diagram at https://www.bottlecaps.de/rr/ui
//
source_file ::=  _statement*
_statement ::=  expression_statement |  _declaration_statement
empty_statement ::=  ';'
expression_statement ::=  ( _expression ';'  )  |   (  _expression_ending_with_block )
_declaration_statement ::=  const_item |  macro_invocation |  macro_definition |  empty_statement |  attribute_item |  inner_attribute_item |  mod_item |  foreign_mod_item |  struct_item |  union_item |  enum_item |  type_item |  function_item |  function_signature_item |  impl_item |  trait_item |  associated_type |  let_declaration |  use_declaration |  extern_crate_declaration |  static_item
macro_definition ::=  'macro_rules!'  (  ( identifier |  _reserved_identifier )  )  ( ( '('  ( ( macro_rule ';'  ) *  macro_rule?  )  ')'  ';'  )  |  ( '{'  ( ( macro_rule ';'  ) *  macro_rule?  )  '}'  )  )
macro_rule ::=  (  token_tree_pattern )  '=>'  (  token_tree )
_token_pattern ::=  token_tree_pattern |  token_repetition_pattern |  token_binding_pattern |  metavariable |  _non_special_token
token_tree_pattern ::=  ( '('  _token_pattern*  ')'  )  |  ( '['  _token_pattern*  ']'  )  |  ( '{'  _token_pattern*  '}'  )
token_binding_pattern ::=   (  ( (  metavariable )  ':'  (  fragment_specifier )  )  )
token_repetition_pattern ::=  '$'  '('  _token_pattern*  ')'  [^+*?]*  ( '+'  |  '*'  |  '?'  )
fragment_specifier ::=  'block'  |  'expr'  |  'ident'  |  'item'  |  'lifetime'  |  'literal'  |  'meta'  |  'pat'  |  'path'  |  'stmt'  |  'tt'  |  'ty'  |  'vis'
_tokens ::=  token_tree |  token_repetition |  metavariable |  _non_special_token
token_tree ::=  ( '('  _tokens*  ')'  )  |  ( '['  _tokens*  ']'  )  |  ( '{'  _tokens*  '}'  )
token_repetition ::=  '$'  '('  _tokens*  ')'  [^+*?]*  ( '+'  |  '*'  |  '?'  )
_non_special_token ::=  _literal |  identifier |  mutable_specifier |  self |  super |  crate |  ( 'u8'  |  'i8'  |  'u16'  |  'i16'  |  'u32'  |  'i32'  |  'u64'  |  'i64'  |  'u128'  |  'i128'  |  'isize'  |  'usize'  |  'f32'  |  'f64'  |  'bool'  |  'str'  |  'char'  )  |  [/_\-=->,;:::!=?.@*&#%^+<>|~]+ |  "'"  |  'as'  |  'async'  |  'await'  |  'break'  |  'const'  |  'continue'  |  'default'  |  'enum'  |  'fn'  |  'for'  |  'if'  |  'impl'  |  'let'  |  'loop'  |  'match'  |  'mod'  |  'pub'  |  'return'  |  'static'  |  'struct'  |  'trait'  |  'type'  |  'union'  |  'unsafe'  |  'use'  |  'where'  |  'while'
attribute_item ::=  '#'  '['  attribute ']'
inner_attribute_item ::=  '#'  '!'  '['  attribute ']'
attribute ::=  _path ( ( '='  (  _expression )  )  |  (  delim_token_tree )  ) ?
mod_item ::=  visibility_modifier?  'mod'  (  identifier )  ( ';'  |  (  declaration_list )  )
foreign_mod_item ::=  visibility_modifier?  extern_modifier ( ';'  |  (  declaration_list )  )
declaration_list ::=  '{'  _declaration_statement*  '}'
struct_item ::=  visibility_modifier?  'struct'  (  _type_identifier )  (  type_parameters?  )  ( ( where_clause?  (  field_declaration_list )  )  |  ( (  ordered_field_declaration_list )  where_clause?  ';'  )  |  ';'  )
union_item ::=  visibility_modifier?  'union'  (  _type_identifier )  (  type_parameters?  )  where_clause?  (  field_declaration_list )
enum_item ::=  visibility_modifier?  'enum'  (  _type_identifier )  (  type_parameters?  )  where_clause?  (  enum_variant_list )
enum_variant_list ::=  '{'  ( ( attribute_item*  enum_variant )  ( ','  ( attribute_item*  enum_variant )  ) *  ) ?  ',' ?  '}'
enum_variant ::=  visibility_modifier?  (  identifier )  (  ( field_declaration_list |  ordered_field_declaration_list ) ?  )  ( '='  (  _expression )  ) ?
field_declaration_list ::=  '{'  ( ( attribute_item*  field_declaration )  ( ','  ( attribute_item*  field_declaration )  ) *  ) ?  ',' ?  '}'
field_declaration ::=  visibility_modifier?  (  _field_identifier )  ':'  (  _type )
ordered_field_declaration_list ::=  '('  ( ( attribute_item*  visibility_modifier?  (  _type )  )  ( ','  ( attribute_item*  visibility_modifier?  (  _type )  )  ) *  ) ?  ',' ?  ')'
extern_crate_declaration ::=  visibility_modifier?  'extern'  crate (  identifier )  ( 'as'  (  identifier )  ) ?  ';'
const_item ::=  visibility_modifier?  'const'  (  identifier )  ':'  (  _type )  ( '='  (  _expression )  ) ?  ';'
static_item ::=  visibility_modifier?  'static'  'ref' ?  mutable_specifier?  (  identifier )  ':'  (  _type )  ( '='  (  _expression )  ) ?  ';'
type_item ::=  visibility_modifier?  'type'  (  _type_identifier )  (  type_parameters?  )  '='  (  _type )  ';'
function_item ::=  visibility_modifier?  function_modifiers?  'fn'  (  ( identifier |  metavariable )  )  (  type_parameters?  )  (  parameters )  ( '->'  (  _type )  ) ?  where_clause?  (  block )
function_signature_item ::=  visibility_modifier?  function_modifiers?  'fn'  (  ( identifier |  metavariable )  )  (  type_parameters?  )  (  parameters )  ( '->'  (  _type )  ) ?  where_clause?  ';'
function_modifiers ::=  ( 'async'  |  'default'  |  'const'  |  'unsafe'  |  extern_modifier ) +
where_clause ::=  'where'  ( where_predicate ( ','  where_predicate ) *  )  ',' ?
where_predicate ::=  (  ( lifetime |  _type_identifier |  scoped_type_identifier |  generic_type |  reference_type |  pointer_type |  tuple_type |  higher_ranked_trait_bound |  ( 'u8'  |  'i8'  |  'u16'  |  'i16'  |  'u32'  |  'i32'  |  'u64'  |  'i64'  |  'u128'  |  'i128'  |  'isize'  |  'usize'  |  'f32'  |  'f64'  |  'bool'  |  'str'  |  'char'  )  )  )  (  trait_bounds )
impl_item ::=  'unsafe' ?  'impl'  (  type_parameters?  )  ( (  ( _type_identifier |  scoped_type_identifier |  generic_type )  )  'for'  ) ?  (  _type )  where_clause?  ( (  declaration_list )  |  ';'  )
trait_item ::=  visibility_modifier?  'unsafe' ?  'trait'  (  _type_identifier )  (  type_parameters?  )  (  trait_bounds?  )  where_clause?  (  declaration_list )
associated_type ::=  'type'  (  _type_identifier )  (  type_parameters?  )  (  trait_bounds?  )  ';'
trait_bounds ::=  ':'  ( ( _type |  lifetime |  higher_ranked_trait_bound |  removed_trait_bound )  ( '+'  ( _type |  lifetime |  higher_ranked_trait_bound |  removed_trait_bound )  ) *  )
higher_ranked_trait_bound ::=  'for'  (  type_parameters )  (  _type )
removed_trait_bound ::=  '?'  _type
type_parameters ::=   (  ( '<'  ( ( lifetime |  metavariable |  _type_identifier |  constrained_type_parameter |  optional_type_parameter |  const_parameter )  ( ','  ( lifetime |  metavariable |  _type_identifier |  constrained_type_parameter |  optional_type_parameter |  const_parameter )  ) *  )  ',' ?  '>'  )  )
const_parameter ::=  'const'  (  identifier )  ':'  (  _type )
constrained_type_parameter ::=  (  ( lifetime |  _type_identifier )  )  (  trait_bounds )
optional_type_parameter ::=  (  ( _type_identifier |  constrained_type_parameter )  )  '='  (  _type )
let_declaration ::=  'let'  mutable_specifier?  (  _pattern )  ( ':'  (  _type )  ) ?  ( '='  (  _expression )  ) ?  ( 'else'  (  block )  ) ?  ';'
use_declaration ::=  visibility_modifier?  'use'  (  _use_clause )  ';'
_use_clause ::=  _path |  use_as_clause |  use_list |  scoped_use_list |  use_wildcard
scoped_use_list ::=  (  _path?  )  '::'  (  use_list )
use_list ::=  '{'  ( _use_clause ( ','  _use_clause ) *  ) ?  ',' ?  '}'
use_as_clause ::=  (  _path )  'as'  (  identifier )
use_wildcard ::=  ( _path '::'  ) ?  '*'
parameters ::=  '('  ( ( attribute_item?  ( parameter |  self_parameter |  variadic_parameter |  '_'  |  _type )  )  ( ','  ( attribute_item?  ( parameter |  self_parameter |  variadic_parameter |  '_'  |  _type )  )  ) *  ) ?  ',' ?  ')'
self_parameter ::=  '&' ?  lifetime?  mutable_specifier?  self
variadic_parameter ::=  '...'
parameter ::=  mutable_specifier?  (  ( _pattern |  self )  )  ':'  (  _type )
extern_modifier ::=  'extern'  string_literal?
visibility_modifier ::=   (  ( crate |  ( 'pub'  ( '('  ( self |  super |  crate |  ( 'in'  _path )  )  ')'  ) ?  )  )  )
_type ::=  abstract_type |  reference_type |  metavariable |  pointer_type |  generic_type |  scoped_type_identifier |  tuple_type |  unit_type |  array_type |  function_type |  _type_identifier |  macro_invocation |  empty_type |  dynamic_type |  bounded_type |  ( 'u8'  |  'i8'  |  'u16'  |  'i16'  |  'u32'  |  'i32'  |  'u64'  |  'i64'  |  'u128'  |  'i128'  |  'isize'  |  'usize'  |  'f32'  |  'f64'  |  'bool'  |  'str'  |  'char'  )
bracketed_type ::=  '<'  ( _type |  qualified_type )  '>'
qualified_type ::=  (  _type )  'as'  (  _type )
lifetime ::=  "'"  identifier
array_type ::=  '['  (  _type )  ( ';'  (  _expression )  ) ?  ']'
for_lifetimes ::=  'for'  '<'  ( lifetime ( ','  lifetime ) *  )  ',' ?  '>'
function_type ::=  for_lifetimes?   (  ( ( (  ( _type_identifier |  scoped_type_identifier )  )  |  ( function_modifiers?  'fn'  )  )  (  parameters )  )  )  ( '->'  (  _type )  ) ?
tuple_type ::=  '('  ( _type ( ','  _type ) *  )  ',' ?  ')'
unit_type ::=  '('  ')'
generic_function ::=   (  ( (  ( identifier |  scoped_identifier |  field_expression )  )  '::'  (  type_arguments )  )  )
generic_type ::=   (  ( (  ( _type_identifier |  scoped_type_identifier )  )  (  type_arguments )  )  )
generic_type_with_turbofish ::=  (  ( _type_identifier |  scoped_identifier )  )  '::'  (  type_arguments )
bounded_type ::=   (  ( ( lifetime '+'  _type )  |  ( _type '+'  _type )  |  ( _type '+'  lifetime )  )  )
type_arguments ::=  (   (  '<'  )  )  ( ( _type |  type_binding |  lifetime |  _literal |  block )  ( ','  ( _type |  type_binding |  lifetime |  _literal |  block )  ) *  )  ',' ?  '>'
type_binding ::=  (  _type_identifier )  (  type_arguments?  )  '='  (  _type )
reference_type ::=  '&'  lifetime?  mutable_specifier?  (  _type )
pointer_type ::=  '*'  ( 'const'  |  mutable_specifier )  (  _type )
empty_type ::=  '!'
abstract_type ::=  'impl'  (  ( _type_identifier |  scoped_type_identifier |  generic_type |  function_type )  )
dynamic_type ::=  'dyn'  (  ( _type_identifier |  scoped_type_identifier |  generic_type |  function_type )  )
mutable_specifier ::=  'mut'
_expression_except_range ::=  unary_expression |  reference_expression |  try_expression |  binary_expression |  assignment_expression |  compound_assignment_expr |  type_cast_expression |  call_expression |  return_expression |  yield_expression |  _literal |   (  identifier )  |  ( 'u8'  |  'i8'  |  'u16'  |  'i16'  |  'u32'  |  'i32'  |  'u64'  |  'i64'  |  'u128'  |  'i128'  |  'isize'  |  'usize'  |  'f32'  |  'f64'  |  'bool'  |  'str'  |  'char'  )  |   (  _reserved_identifier )  |  self |  scoped_identifier |  generic_function |  await_expression |  field_expression |  array_expression |  tuple_expression |   (  macro_invocation )  |  unit_expression |  break_expression |  continue_expression |  index_expression |  metavariable |  closure_expression |  parenthesized_expression |  struct_expression |  _expression_ending_with_block
_expression ::=  _expression_except_range |  range_expression
_expression_ending_with_block ::=  unsafe_block |  async_block |  block |  if_expression |  match_expression |  while_expression |  loop_expression |  for_expression |  const_block
macro_invocation ::=  (  ( scoped_identifier |  identifier |  _reserved_identifier )  )  '!'  delim_token_tree
delim_token_tree ::=  ( '('  _delim_tokens*  ')'  )  |  ( '['  _delim_tokens*  ']'  )  |  ( '{'  _delim_tokens*  '}'  )
_delim_tokens ::=  _non_delim_token |  delim_token_tree
_non_delim_token ::=  _non_special_token |  '$'
scoped_identifier ::=  (  ( _path |  bracketed_type |  generic_type_with_turbofish ) ?  )  '::'  (  identifier )
scoped_type_identifier_in_expression_position ::=   (  ( (  ( _path |  generic_type_with_turbofish ) ?  )  '::'  (  _type_identifier )  )  )
scoped_type_identifier ::=  (  ( _path |  generic_type_with_turbofish |  bracketed_type |  generic_type ) ?  )  '::'  (  _type_identifier )
range_expression ::=   (  ( ( _expression ( '..'  |  '...'  |  '..='  )  _expression )  |  ( _expression '..'  )  |  ( '..'  _expression )  |  '..'  )  )
unary_expression ::=   (  ( ( '-'  |  '*'  |  '!'  )  _expression )  )
try_expression ::=  _expression '?'
reference_expression ::=   (  ( '&'  mutable_specifier?  (  _expression )  )  )
binary_expression ::=   (  ( (  _expression )  (  '&&'  )  (  _expression )  )  )  |   (  ( (  _expression )  (  '||'  )  (  _expression )  )  )  |   (  ( (  _expression )  (  '&'  )  (  _expression )  )  )  |   (  ( (  _expression )  (  '|'  )  (  _expression )  )  )  |   (  ( (  _expression )  (  '^'  )  (  _expression )  )  )  |   (  ( (  _expression )  (  ( '=='  |  '!='  |  '<'  |  '<='  |  '>'  |  '>='  )  )  (  _expression )  )  )  |   (  ( (  _expression )  (  ( '<<'  |  '>>'  )  )  (  _expression )  )  )  |   (  ( (  _expression )  (  ( '+'  |  '-'  )  )  (  _expression )  )  )  |   (  ( (  _expression )  (  ( '*'  |  '/'  |  '%'  )  )  (  _expression )  )  )
assignment_expression ::=   (  ( (  _expression )  '='  (  _expression )  )  )
compound_assignment_expr ::=   (  ( (  _expression )  (  ( '+='  |  '-='  |  '*='  |  '/='  |  '%='  |  '&='  |  '|='  |  '^='  |  '<<='  |  '>>='  )  )  (  _expression )  )  )
type_cast_expression ::=   (  ( (  _expression )  'as'  (  _type )  )  )
return_expression ::=   (  ( 'return'  _expression )  )  |   (  'return'  )
yield_expression ::=   (  ( 'yield'  _expression )  )  |   (  'yield'  )
call_expression ::=   (  ( (  _expression_except_range )  (  arguments )  )  )
arguments ::=  '('  ( ( attribute_item*  _expression )  ( ','  ( attribute_item*  _expression )  ) *  ) ?  ',' ?  ')'
array_expression ::=  '['  attribute_item*  ( ( _expression ';'  (  _expression )  )  |  ( ( _expression ( ','  _expression ) *  ) ?  ',' ?  )  )  ']'
parenthesized_expression ::=  '('  _expression ')'
tuple_expression ::=  '('  attribute_item*  ( _expression ','  )  ( _expression ','  ) *  _expression?  ')'
unit_expression ::=  '('  ')'
struct_expression ::=  (  ( _type_identifier |  scoped_type_identifier_in_expression_position |  generic_type_with_turbofish )  )  (  field_initializer_list )
field_initializer_list ::=  '{'  ( ( shorthand_field_initializer |  field_initializer |  base_field_initializer )  ( ','  ( shorthand_field_initializer |  field_initializer |  base_field_initializer )  ) *  ) ?  ',' ?  '}'
shorthand_field_initializer ::=  attribute_item*  identifier
field_initializer ::=  attribute_item*  (  _field_identifier )  ':'  (  _expression )
base_field_initializer ::=  '..'  _expression
if_expression ::=   (  ( 'if'  (  _condition )  (  block )  (  else_clause ) ?  )  )
let_condition ::=  'let'  (  _pattern )  '='  (   (  _expression )  )
_let_chain ::=   (  ( ( _let_chain '&&'  let_condition )  |  ( _let_chain '&&'  _expression )  |  ( let_condition '&&'  _expression )  |  ( let_condition '&&'  let_condition )  |  ( _expression '&&'  let_condition )  )  )
_condition ::=  _expression |  let_condition |  _let_chain
else_clause ::=  'else'  ( block |  if_expression )
match_expression ::=  'match'  (  _expression )  (  match_block )
match_block ::=  '{'  ( match_arm*  last_match_arm ) ?  '}'
match_arm ::=  attribute_item*  (  match_pattern )  '=>'  ( ( (  _expression )  ','  )  |  (   (  _expression_ending_with_block )  )  )
last_match_arm ::=  attribute_item*  (  match_pattern )  '=>'  (  _expression )  ',' ?
match_pattern ::=  _pattern ( 'if'  (  _condition )  ) ?
while_expression ::=  ( loop_label ':'  ) ?  'while'  (  _condition )  (  block )
loop_expression ::=  ( loop_label ':'  ) ?  'loop'  (  block )
for_expression ::=  ( loop_label ':'  ) ?  'for'  (  _pattern )  'in'  (  _expression )  (  block )
const_block ::=  'const'  (  block )
closure_expression ::=   (  ( 'move' ?  (  closure_parameters )  ( ( ( '->'  (  _type )  ) ?  (  block )  )  |  (  _expression )  )  )  )
closure_parameters ::=  '|'  ( ( _pattern |  parameter )  ( ','  ( _pattern |  parameter )  ) *  ) ?  '|'
loop_label ::=  "'"  identifier
break_expression ::=   (  ( 'break'  loop_label?  _expression?  )  )
continue_expression ::=   (  ( 'continue'  loop_label?  )  )
index_expression ::=   (  ( _expression '['  _expression ']'  )  )
await_expression ::=   (  ( _expression '.'  'await'  )  )
field_expression ::=   (  ( (  _expression )  '.'  (  ( _field_identifier |  integer_literal )  )  )  )
unsafe_block ::=  'unsafe'  block
async_block ::=  'async'  'move' ?  block
block ::=  '{'  _statement*  _expression?  '}'
_pattern ::=  _literal_pattern |  ( 'u8'  |  'i8'  |  'u16'  |  'i16'  |  'u32'  |  'i32'  |  'u64'  |  'i64'  |  'u128'  |  'i128'  |  'isize'  |  'usize'  |  'f32'  |  'f64'  |  'bool'  |  'str'  |  'char'  )  |  identifier |  scoped_identifier |  tuple_pattern |  tuple_struct_pattern |  struct_pattern |  _reserved_identifier |  ref_pattern |  slice_pattern |  captured_pattern |  reference_pattern |  remaining_field_pattern |  mut_pattern |  range_pattern |  or_pattern |  const_block |  macro_invocation |  '_'
tuple_pattern ::=  '('  ( _pattern ( ','  _pattern ) *  ) ?  ',' ?  ')'
slice_pattern ::=  '['  ( _pattern ( ','  _pattern ) *  ) ?  ',' ?  ']'
tuple_struct_pattern ::=  (  ( identifier |  scoped_identifier )  )  '('  ( _pattern ( ','  _pattern ) *  ) ?  ',' ?  ')'
struct_pattern ::=  (  ( _type_identifier |  scoped_type_identifier )  )  '{'  ( ( field_pattern |  remaining_field_pattern )  ( ','  ( field_pattern |  remaining_field_pattern )  ) *  ) ?  ',' ?  '}'
field_pattern ::=  'ref' ?  mutable_specifier?  ( (  identifier )  |  ( (  _field_identifier )  ':'  (  _pattern )  )  )
remaining_field_pattern ::=  '..'
mut_pattern ::=   (  ( mutable_specifier _pattern )  )
range_pattern ::=  ( _literal_pattern |  _path )  ( '...'  |  '..='  )  ( _literal_pattern |  _path )
ref_pattern ::=  'ref'  _pattern
captured_pattern ::=  identifier '@'  _pattern
reference_pattern ::=  '&'  mutable_specifier?  _pattern
or_pattern ::=   (  ( _pattern '|'  _pattern )  )
_literal ::=  string_literal |  raw_string_literal |  char_literal |  boolean_literal |  integer_literal |  float_literal
_literal_pattern ::=  string_literal |  raw_string_literal |  char_literal |  boolean_literal |  integer_literal |  float_literal |  negative_literal
negative_literal ::=  '-'  ( integer_literal |  float_literal )
integer_literal ::=  (  ( ( [0-9][0-9_]* |  '0x'[0-9a-fA-F_]+ |  '0b'[01_]+ |  '0o'[0-7_]+ )  ( 'u8'  |  'i8'  |  'u16'  |  'i16'  |  'u32'  |  'i32'  |  'u64'  |  'i64'  |  'u128'  |  'i128'  |  'isize'  |  'usize'  |  'f32'  |  'f64'  ) ?  )  )
string_literal ::=  'b'?'"' ( escape_sequence |  _string_content ) *  (  '"'  )
char_literal ::=  (  ( 'b' ?  "'"  ( ( '\'  ( [^xu] |  'u' hex_digit hex_digit hex_digit hex_digit |  'u{' hex_digit+ '}' |  'x' hex_digit hex_digit )  )  |  [^\'] ) ?  "'"  )  )
escape_sequence ::=  (  ( '\'  ( [^xu] |  'u' hex_digit hex_digit hex_digit hex_digit |  'u{' hex_digit+ '}' |  'x' hex_digit hex_digit )  )  )
boolean_literal ::=  'true'  |  'false'
comment ::=  line_comment |  block_comment
line_comment ::=  (  ( '//'  .* )  )
_path ::=  self |  ( 'u8'  |  'i8'  |  'u16'  |  'i16'  |  'u32'  |  'i32'  |  'u64'  |  'i64'  |  'u128'  |  'i128'  |  'isize'  |  'usize'  |  'f32'  |  'f64'  |  'bool'  |  'str'  |  'char'  )  |  metavariable |  super |  crate |  identifier |  scoped_identifier |  _reserved_identifier
identifier ::=  ('r#')?[_\p{XID_Start}][_\p{XID_Continue}]*
_reserved_identifier ::=  ( 'default'  |  'union'  )
_type_identifier ::=  identifier
_field_identifier ::=  identifier
self ::=  'self'
super ::=  'super'
crate ::=  'crate'
metavariable ::=  '$'[a-zA-Z_][a-zA-Z]*
hex_digit ::= [0-9a-fA-F]

Obs.: Update to the latest grammar of this project as of today.