definition.go 8.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214
  1. package syntax
  2. import (
  3. "regexp"
  4. "strings"
  5. )
  6. type Regexp = *regexp.Regexp
  7. func r (pattern string) Regexp { return regexp.MustCompile(`^` + pattern) }
  8. const defaultRoot = "root"
  9. const replRoot = "repl_cmd"
  10. func DefaultRoot() Id { return Name2IdMustExist(defaultRoot) }
  11. func ReplRoot() Id { return Name2IdMustExist(replRoot) }
  12. var __EscapeMap = map[string] string {
  13. "_bar": "|",
  14. "_at": "@",
  15. }
  16. var __IgnoreTokens = [...] string {
  17. "Comment",
  18. "Blank",
  19. "LF",
  20. }
  21. const LF = `\n`
  22. const Blanks = ` \t\r `
  23. const Symbols = `\{\}\[\]\(\)\.,:;@#\|\&\\'"` + "`"
  24. const nameEverywhereDisallow = (Symbols + Blanks + LF)
  25. const nameHeadDisallow = (`0-9` + nameEverywhereDisallow)
  26. const NamePattern = `[^`+nameHeadDisallow+`][^`+nameEverywhereDisallow+`]*`
  27. var __Tokens = [...] Token {
  28. // doc
  29. Token { Name: "Doc", Pattern: r(`///[^`+LF+`]*`) },
  30. // ignored
  31. Token { Name: "Comment", Pattern: r(`//[^`+LF+`]*`) },
  32. Token { Name: "Blank", Pattern: r(`[`+Blanks+`]+`) },
  33. Token { Name: "LF", Pattern: r(`[`+LF+`]+`) },
  34. // literals
  35. Token { Name: "Text", Pattern: r(`'[^']*'`) },
  36. Token { Name: "Text", Pattern: r(`"(\\"|[^"])*"`) },
  37. Token { Name: "Int", Pattern: r(`\-?0[xX][0-9A-Fa-f]+`) },
  38. Token { Name: "Int", Pattern: r(`\-?0[oO][0-7]+`) },
  39. Token { Name: "Int", Pattern: r(`\-?0[bB][01]+`) },
  40. Token { Name: "Float", Pattern: r(`\-?\d+(\.\d+)?[Ee][\+\-]?\d+`) },
  41. Token { Name: "Float", Pattern: r(`\-?\d+\.\d+`) },
  42. Token { Name: "Int", Pattern: r(`\-?\d+`) },
  43. Token { Name: "Byte", Pattern: r(`\\x[0-9A-Fa-f][0-9A-Fa-f]`) },
  44. Token { Name: "Char", Pattern: r("`.`") },
  45. Token { Name: "Char", Pattern: r(`\\u[0-9A-Fa-f]+`) },
  46. Token { Name: "Char", Pattern: r(`\\[a-z]`) },
  47. // symbols
  48. Token { Name: "(", Pattern: r(`\(`) },
  49. Token { Name: ")", Pattern: r(`\)`) },
  50. Token { Name: "[", Pattern: r(`\[`) },
  51. Token { Name: "]", Pattern: r(`\]`) },
  52. Token { Name: "{", Pattern: r(`\{`) },
  53. Token { Name: "}", Pattern: r(`\}`) },
  54. Token { Name: "...", Pattern: r(`\.\.\.`) },
  55. Token { Name: "..", Pattern: r(`\.\.`) },
  56. Token { Name: ".", Pattern: r(`\.`) },
  57. Token { Name: ",", Pattern: r(`,`) },
  58. Token { Name: "::", Pattern: r(`::`) },
  59. Token { Name: ":", Pattern: r(`:`) },
  60. Token { Name: ";", Pattern: r(`;`) },
  61. Token { Name: "@", Pattern: r(`@`) },
  62. Token { Name: "#", Pattern: r(`#`) },
  63. Token { Name: "|", Pattern: r(`\|`) },
  64. Token { Name: "&", Pattern: r(`\&`) },
  65. // keywords
  66. Token { Name: "Const", Pattern: r(`const`), Keyword: true },
  67. Token { Name: "If", Pattern: r(`if`), Keyword: true },
  68. Token { Name: "Else", Pattern: r(`else`), Keyword: true },
  69. Token { Name: "When", Pattern: r(`when`), Keyword: true },
  70. Token { Name: "Each", Pattern: r(`each`), Keyword: true },
  71. Token { Name: "Let", Pattern: r(`let`), Keyword: true },
  72. Token { Name: "New", Pattern: r(`new`), Keyword: true },
  73. Token { Name: "=>", Pattern: r(`=>`), Keyword: true },
  74. Token { Name: "=", Pattern: r(`=`), Keyword: true },
  75. // identifier
  76. Token { Name: "Name", Pattern: r(NamePattern) },
  77. }
  78. var nameTokenRegexp = regexp.MustCompile(NamePattern)
  79. func Tokens() ([] Token) { return __Tokens[:] }
  80. func IgnoreTokens() ([] string) { return __IgnoreTokens[:] }
  81. func NameTokenId() Id { return Name2IdMustExist("Name") }
  82. func NameTokenRegexp() Regexp { return nameTokenRegexp }
  83. var __ConditionalKeywords = [...] string {
  84. "@namespace", "@using",
  85. "@run",
  86. "@entry", "@type", "@function", "@operator", "@method",
  87. "@native", "@record", "@interface", "@union", "@enum",
  88. "@variadic",
  89. }
  90. func GetKeywordList() ([] string) {
  91. var list = make([] string, 0)
  92. for _, v := range __ConditionalKeywords {
  93. var kw = strings.TrimPrefix(v, "@")
  94. list = append(list, kw)
  95. }
  96. for _, t := range __Tokens {
  97. if t.Keyword {
  98. var kw = strings.TrimPrefix(t.Pattern.String(), "^")
  99. list = append(list, kw)
  100. }
  101. }
  102. return list
  103. }
  104. var __SyntaxDefinition = [...] string {
  105. "root = ns! alias* stmt*",
  106. "ns = @namespace name? ::! ",
  107. "name = Name",
  108. "alias = off @using alias_name alias_target",
  109. "off? = #",
  110. "alias_name? = name = ",
  111. "alias_target = alias_to_ns | alias_to_ref_base",
  112. "alias_to_ns = @namespace name!",
  113. "alias_to_ref_base = ref_base!",
  114. "stmt = decl_entry | decl_type | decl_func | decl_const | decl_method",
  115. "decl_entry = docs off @entry block!",
  116. "docs? = doc+",
  117. "doc = Doc",
  118. "decl_type = docs off @type name! type_params impl type_def!",
  119. "type_params? = [ name*, ]!",
  120. "impl? = ( ref_base*, )!",
  121. "ref_base = ns_prefix name",
  122. "ns_prefix? = name :: ",
  123. "type_def = native_type_def | record | interface | union | enum",
  124. "native_type_def = @native",
  125. "record = @record record_def!",
  126. "record_def = { field*, }!",
  127. "field = docs name type! field_default",
  128. "field_default? = ( expr! )!",
  129. "interface = @interface {! method*, }!",
  130. "method = docs name type!",
  131. "union = @union {! type+,! }!",
  132. "enum = @enum {! enum_item+,! }!",
  133. "enum_item = docs name",
  134. "decl_func = docs off function variadic name! sig! body!",
  135. "function = @function | @operator",
  136. "variadic? = @variadic",
  137. "sig = type_params inputs! implicit output!",
  138. "inputs = record_def",
  139. "implicit? = inputs",
  140. "output = type",
  141. "body = native_body | block!",
  142. "native_body = @native (! text! )!",
  143. "decl_const = docs off Const name! type! body!",
  144. "decl_method = docs off @method receiver! .! name! type! body!",
  145. "receiver = name",
  146. "type = ref",
  147. "ref = ref_base type_args",
  148. "type_args? = [ type*, ]!",
  149. "expr = cast* term pipe*",
  150. "cast = ( [ type! ]! )!",
  151. "pipe = pipe_call | pipe_infix | pipe_cast | pipe_get | pipe_interior",
  152. "pipe_call = call_ordered | call_unordered",
  153. "call_ordered = ( expr*, )!",
  154. "call_unordered = { arg_mapping*, }!",
  155. "arg_mapping = name arg_mapping_to",
  156. "arg_mapping_to? = : expr!",
  157. "pipe_infix = off _bar ref! pipe_call!",
  158. "pipe_cast = . cast",
  159. "pipe_get = . name",
  160. "pipe_interior = . ( ref_base! )!",
  161. "term = infix_term | lambda | if | when | each | block | ref_term " +
  162. "| int | float | char | bytes | string ",
  163. "infix_term = ( infix_left operator infix_right! )!",
  164. "infix_left = expr",
  165. "operator = ref",
  166. "infix_right = expr",
  167. "lambda = { pattern? lambda_self => expr! }!",
  168. "lambda_self? = & name!",
  169. "pattern = pattern_single | pattern_multiple",
  170. "pattern_single = name",
  171. "pattern_multiple = ( name+, )",
  172. "if = If (! cond+,! )! if_yes elif* Else! if_no",
  173. "cond = cond_pattern expr!",
  174. "cond_pattern? = Let pattern! =! ",
  175. "if_yes = block!",
  176. "if_no = block!",
  177. "elif = If (! cond+,! )! block!",
  178. "when = When (! expr! )! {! case+,! }!",
  179. "case = off name+_bar pattern? =>! expr!",
  180. "each = Each (! type! )! {! case+,! }!",
  181. "block = { binding* expr! }!",
  182. "binding = binding_plain | binding_cps",
  183. "binding_plain = off let pattern! =! expr! ,!",
  184. "let = Let | Const",
  185. "binding_cps = off _at ref! cps_pattern expr! ,!",
  186. "cps_pattern? = pattern = ",
  187. "ref_term = new ref",
  188. "new? = New new_tag",
  189. "new_tag? = : name!",
  190. "int = Int",
  191. "float = Float",
  192. "char = Char",
  193. "bytes = byte+",
  194. "byte = Byte",
  195. "string = text string_part* ",
  196. "text = Text",
  197. "string_part = .. string_part_content!",
  198. "string_part_content = text | char",
  199. "repl_cmd = repl_assign | repl_run | repl_eval",
  200. "repl_assign = name = expr!",
  201. "repl_run = : @run expr!",
  202. "repl_eval = expr!",
  203. }