grammar.lalrpop 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122
  1. use crate::ast::*;
  2. use crate::lexer::*;
  3. grammar<'input>;
  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. "var" => Token::Var(<&'input str>),
  28. "atom" => Token::Atom(<&'input str>),
  29. "num" => Token::Num(<i64>),
  30. "str" => Token::Str(<String>)
  31. }
  32. }
  33. pub Stmts: Vec<Stmt> = {
  34. <mut stmts:(<Stmt> ";")*> <stmt:Stmt?> => match stmt {
  35. None => stmts,
  36. Some(stmt) => {
  37. stmts.push(stmt);
  38. stmts
  39. }
  40. },
  41. };
  42. pub Stmt: Stmt = {
  43. "puts" <Expr> => Stmt::Puts(<>),
  44. <Name> ":=" <Expr> => Stmt::Assn(<>),
  45. <name:Name> "::=" <strs:(<Name>)*> => Stmt::LitAssn(name, strs),
  46. };
  47. pub Name: String = {
  48. "var" => <>.to_owned(),
  49. };
  50. pub Expr: Expr = {
  51. <mut ts:(<Choice> "|")*> <t:Choice> => {
  52. ts.push(t);
  53. Expr::Chc(ts)
  54. }
  55. };
  56. pub Choice: Choice = {
  57. <weight:"num"> ":" <value:Term> => Choice {
  58. weight: Some(weight),
  59. value
  60. },
  61. <value:Term> => Choice {
  62. weight: None,
  63. value
  64. }
  65. };
  66. pub Term: Expr = {
  67. (<Branch>)* => Expr::Cat(<>),
  68. };
  69. pub Branch: Expr = {
  70. <l:Branch> "." <r:Subbranch> => Expr::Ap(Box::new(l), Box::new(r)),
  71. <Subbranch> => <>,
  72. };
  73. pub Subbranch: Expr = {
  74. <l:Subbranch> ".." <r:Leaf> => Expr::Range(Box::new(l), Box::new(r)),
  75. <Leaf> => <>,
  76. }
  77. pub Leaf: Expr = {
  78. <Literal> => Expr::Lit(<>),
  79. <Name> => Expr::Var(<>),
  80. "<" <mut es:(<Expr> ",")*> <e:Expr> ">" => {
  81. es.push(e);
  82. Expr::Tup(es)
  83. },
  84. "let" <name:Name> ":=" <e1:Expr> "in" "{" <e2:Expr> "}" =>
  85. Expr::Let(name, Box::new(e1), Box::new(e2)),
  86. "{" <mut cs:(<Case> ";")*> <c:Case> "}" => {
  87. cs.push(c);
  88. Expr::Fun(cs)
  89. },
  90. "(" <e:Expr> ")" => e,
  91. };
  92. pub Case: Case = {
  93. <pat:Pat> "=>" <expr:Expr> => Case { pat, expr },
  94. };
  95. pub Pat: Pat = {
  96. <Literal> => Pat::Lit(<>),
  97. <Name> => Pat::Var(<>),
  98. "<" <mut ps:(<Pat> ",")*> <p:Pat> ">" => {
  99. ps.push(p);
  100. Pat::Tup(ps)
  101. },
  102. };
  103. pub Literal: Literal = {
  104. "num" => Literal::Num(<>),
  105. "str" => Literal::Str(<>),
  106. "atom" => Literal::Atom(<>.to_owned()),
  107. };