grammar.lalrpop 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139
  1. use crate::ast::*;
  2. use crate::lexer::*;
  3. grammar<'input>(ast: &mut ASTArena);
  4. extern {
  5. type Location = usize;
  6. type Error = LexerError;
  7. enum Token<'input> {
  8. "<" => Token::LAngle,
  9. ">" => Token::RAngle,
  10. "(" => Token::LPar,
  11. ")" => Token::RPar,
  12. "{" => Token::LCurl,
  13. "}" => Token::RCurl,
  14. "|" => Token::Pipe,
  15. ":" => Token::Colon,
  16. "," => Token::Comma,
  17. ";" => Token::Semi,
  18. "." => Token::Dot,
  19. ".." => Token::DotDot,
  20. "=>" => Token::Arrow,
  21. ":=" => Token::Assn,
  22. "::=" => Token::LitAssn,
  23. "puts" => Token::Puts,
  24. "case" => Token::Case,
  25. "let" => Token::Let,
  26. "in" => Token::In,
  27. "fix" => Token::Fix,
  28. "var" => Token::Var(<&'input str>),
  29. "atom" => Token::Atom(<&'input str>),
  30. "num" => Token::Num(<i64>),
  31. "str" => Token::Str(<String>)
  32. }
  33. }
  34. pub Stmts: Vec<Stmt> = {
  35. <mut stmts:(<Stmt> ";")*> <stmt:Stmt?> => match stmt {
  36. None => stmts,
  37. Some(stmt) => {
  38. stmts.push(stmt);
  39. stmts
  40. }
  41. },
  42. };
  43. pub Stmt: Stmt = {
  44. "puts" <Expr> => Stmt::Puts(<>),
  45. <fixed:"fix"?> <name:Name> ":=" <expr:Expr> => Stmt::Assn(fixed.is_some(), name, expr),
  46. <fixed:"fix"?> <name:Name> "::=" <strs:(<"var">)*> =>
  47. Stmt::LitAssn(fixed.is_some(), name, strs.iter().map(|x| x.to_string()).collect()),
  48. "fix" <Name> => Stmt::Fix(<>),
  49. };
  50. pub Name: Name = {
  51. "var" => ast.add_string(<>),
  52. };
  53. pub Expr: ExprRef = {
  54. <mut ts:(<Choice> "|")*> <t:Choice> => {
  55. if ts.len() == 0 {
  56. t.value
  57. } else {
  58. ts.push(t);
  59. ast.add_expr(Expr::Chc(ts))
  60. }
  61. }
  62. };
  63. pub Choice: Choice = {
  64. <weight:"num"> ":" <value:Term> => Choice {
  65. weight: Some(weight),
  66. value
  67. },
  68. <value:Term> => Choice {
  69. weight: None,
  70. value
  71. }
  72. };
  73. pub Term: ExprRef = {
  74. <mut bs:(<Branch>)*> => {
  75. match bs.len() {
  76. 0 => ast.expr_nil(),
  77. 1 => bs.pop().unwrap(),
  78. _ => ast.add_expr(Expr::Cat(<>)),
  79. }
  80. }
  81. };
  82. pub Branch: ExprRef = {
  83. <l:Branch> "." <r:Subbranch> => ast.add_expr(Expr::Ap(l, r)),
  84. <Subbranch> => <>,
  85. };
  86. pub Subbranch: ExprRef = {
  87. <l:Subbranch> ".." <r:Leaf> => ast.add_expr(Expr::Range(l, r)),
  88. <Leaf> => <>,
  89. }
  90. pub Leaf: ExprRef = {
  91. <Literal> => ast.add_expr(Expr::Lit(<>)),
  92. <Name> => ast.add_expr(Expr::Var(<>)),
  93. "<" <mut es:(<Expr> ",")*> <e:Expr> ">" => {
  94. if es.len() == 0 && e == ast.expr_nil() {
  95. ast.add_expr(Expr::Tup(Vec::new()))
  96. } else {
  97. es.push(e);
  98. ast.add_expr(Expr::Tup(es))
  99. }
  100. },
  101. "let" <name:Name> ":=" <e1:Expr> "in" "{" <e2:Expr> "}" =>
  102. ast.add_expr(Expr::Let(name, e1, e2)),
  103. "{" <mut cs:(<Case> ";")*> <c:Case> "}" => {
  104. cs.push(c);
  105. ast.add_expr(Expr::Fun(cs))
  106. },
  107. "(" <e:Expr> ")" => e,
  108. };
  109. pub Case: Case = {
  110. <pat:Pat> "=>" <expr:Expr> => Case { pat, expr },
  111. };
  112. pub Pat: Pat = {
  113. <Literal> => Pat::Lit(<>),
  114. <Name> => Pat::Var(<>),
  115. "<" <mut ps:(<Pat> ",")*> <p:Pat> ">" => {
  116. ps.push(p);
  117. Pat::Tup(ps)
  118. },
  119. };
  120. pub Literal: Literal = {
  121. "num" => Literal::Num(<>),
  122. "str" => Literal::Str(<>),
  123. "atom" => Literal::Atom(ast.add_string(<>)),
  124. };