1use crate::{
2 parser::{ParseError, SyntaxObject},
3 tokens::{NumberLiteral, ParenMod, RealLiteral, TokenType},
4};
5
6use std::{convert::TryFrom, fmt::Write, sync::Arc};
7
8use crate::tokens::IntLiteral;
9use pretty::RcDoc;
10use serde::{Deserialize, Serialize};
11use std::fmt;
12use std::ops::Deref;
13
14use super::{interner::InternedString, parser::SyntaxObjectId, span::Span};
15
16macro_rules! define_symbols {
18 ($($name:tt => $str:expr,) * ) => {
19 $(
20 pub static $name: once_cell::sync::Lazy<InternedString> = once_cell::sync::Lazy::new(|| $str.into());
21 )*
22 };
23}
24
25define_symbols! {
26 UNREADABLE_MODULE_GET => "##__module-get",
27 STANDARD_MODULE_GET => "%module-get%",
28 PROTO_HASH_GET => "%proto-hash-get%",
29 PROVIDE => "provide",
30 DATUM_SYNTAX => "datum->syntax",
31 SYNTAX_SPAN => "#%syntax-span",
32 IF => "if",
33 DEFINE => "define",
34 LET => "let",
35 QUOTE =>"quote",
36 RETURN => "return!",
37 REQUIRE => "require",
38 SET => "set!",
39 PLAIN_LET => "%plain-let",
40 LAMBDA => "lambda",
41 LAMBDA_SYMBOL => "λ",
42 LAMBDA_FN => "fn",
43 BEGIN => "begin",
44 DOC_MACRO => "@doc",
45 REQUIRE_BUILTIN => "require-builtin",
46 REQUIRE_DYLIB => "#%require-dylib",
47 STRUCT_KEYWORD => "struct",
48 UNQUOTE => "unquote",
49 UNQUOTE_COMMA => "#%unquote-comma",
50 RAW_UNQUOTE => "#%unquote",
51 UNQUOTE_SPLICING => "unquote-splicing",
52 RAW_UNQUOTE_SPLICING => "#%unquote-splicing",
53 QUASIQUOTE => "quasiquote",
54 RAW_QUOTE => "#%quote",
55 QUASISYNTAX => "quasisyntax",
56 UNSYNTAX => "unsyntax",
57 RAW_UNSYNTAX => "#%unsyntax",
58 UNSYNTAX_SPLICING => "unsyntax-splicing",
59 RAW_UNSYNTAX_SPLICING => "#%unsyntax-splicing",
60 SYNTAX_QUOTE => "syntax",
61 DEFINE_SYNTAX => "define-syntax",
62 SYNTAX_RULES => "syntax-rules",
63}
64
65pub trait AstTools {
66 fn pretty_print(&self);
67}
68
69impl AstTools for Vec<ExprKind> {
70 fn pretty_print(&self) {
71 println!("{}", self.iter().map(|x| x.to_pretty(60)).join("\n\n"))
72 }
73}
74
75impl AstTools for Vec<&ExprKind> {
76 fn pretty_print(&self) {
77 println!("{}", self.iter().map(|x| x.to_pretty(60)).join("\n\n"))
78 }
79}
80
81impl AstTools for &mut Vec<ExprKind> {
82 fn pretty_print(&self) {
83 println!("{}", self.iter().map(|x| x.to_pretty(60)).join("\n\n"))
84 }
85}
86
87pub trait IteratorExtensions: Iterator {
88 fn join(&mut self, sep: &str) -> String
89 where
90 Self::Item: std::fmt::Display,
91 {
92 match self.next() {
93 None => String::new(),
94 Some(first_elt) => {
95 let (lower, _) = self.size_hint();
97 let mut result = String::with_capacity(sep.len() * lower);
98 write!(&mut result, "{}", first_elt).unwrap();
99 self.for_each(|elt| {
100 result.push_str(sep);
101 write!(&mut result, "{}", elt).unwrap();
102 });
103 result
104 }
105 }
106 }
107}
108
109impl<T> IteratorExtensions for T where T: Iterator {}
110
111#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
112pub enum ExprKind {
113 Atom(Atom),
114 If(Box<If>),
115 Let(Box<Let>),
116 Define(Box<Define>),
117 LambdaFunction(Box<LambdaFunction>),
118 Begin(Box<Begin>),
119 Return(Box<Return>),
120 Quote(Box<Quote>),
121 Macro(Box<Macro>),
122 SyntaxRules(Box<SyntaxRules>),
123 List(List),
124 Set(Box<Set>),
125 Require(Box<Require>),
126 Vector(Vector),
127}
128
129impl Default for ExprKind {
130 fn default() -> Self {
131 ExprKind::List(List::new(Vec::new()))
132 }
133}
134
135#[test]
136fn check_size() {
137 println!("ExprKind: {}", std::mem::size_of::<ExprKind>());
138 println!("SyntaxRules: {}", std::mem::size_of::<SyntaxRules>());
139 println!("Macro: {}", std::mem::size_of::<Macro>());
140 println!("List: {}", std::mem::size_of::<List>());
141 println!("Atom: {}", std::mem::size_of::<Atom>());
142 println!("Require: {}", std::mem::size_of::<Require>());
143 println!("Vector: {}", std::mem::size_of::<Vector>());
144}
145
146#[macro_export]
147macro_rules! expr_list {
148 () => { $crate::ast::ExprKind::List($crate::ast::List::new(vec![])) };
149
150 ( $($x:expr),* ) => {{
151 $crate::ast::ExprKind::List($crate::ast::List::new(vec![$(
152 $x,
153 ) *]))
154 }};
155
156 ( $($x:expr ,)* ) => {{
157 $crate::ast::ExprKind::List($crate::ast::List::new(vec![$($x, )*]))
158 }};
159}
160
161impl ExprKind {
162 pub fn span(&self) -> Option<Span> {
163 match self {
164 ExprKind::Atom(expr) => Some(expr.syn.span),
165 ExprKind::If(expr) => Some(expr.location.span),
166 ExprKind::Let(expr) => Some(expr.location.span),
167 ExprKind::Define(expr) => Some(expr.location.span),
168 ExprKind::LambdaFunction(expr) => Some(expr.location.span),
169 ExprKind::Begin(expr) => Some(expr.location.span),
170 ExprKind::Return(expr) => Some(expr.location.span),
171 ExprKind::Quote(expr) => Some(expr.location.span),
172 ExprKind::Macro(expr) => Some(expr.location.span),
173 ExprKind::SyntaxRules(expr) => Some(expr.location.span),
174 ExprKind::List(expr) => Some(expr.location),
175 ExprKind::Set(expr) => Some(expr.location.span),
176 ExprKind::Require(expr) => Some(expr.location.span),
177 ExprKind::Vector(vec) => Some(vec.span),
178 }
179 }
180
181 pub fn to_string_literal(&self) -> Option<&String> {
182 if let ExprKind::Atom(a) = self {
183 if let TokenType::StringLiteral(s) = &a.syn.ty {
184 Some(s)
185 } else {
186 None
187 }
188 } else {
189 None
190 }
191 }
192
193 pub fn into_lambda_function(self) -> Option<Box<LambdaFunction>> {
194 if let ExprKind::LambdaFunction(func) = self {
195 Some(func)
196 } else {
197 None
198 }
199 }
200
201 pub fn quoted_list() -> ExprKind {
202 ExprKind::Quote(Box::new(Quote::new(
203 Self::empty(),
204 SyntaxObject::default(TokenType::QuoteTick),
205 )))
206 }
207
208 pub fn empty() -> ExprKind {
209 ExprKind::List(List::new(Vec::new()))
210 }
211
212 pub fn integer_literal(value: isize, span: Span) -> ExprKind {
213 ExprKind::Atom(crate::ast::Atom::new(SyntaxObject::new(
214 IntLiteral::Small(value).into(),
215 span,
216 )))
217 }
218
219 pub fn atom<T: Into<InternedString>>(name: T) -> ExprKind {
220 ExprKind::Atom(Atom::new(SyntaxObject::default(TokenType::Identifier(
221 name.into(),
222 ))))
223 }
224
225 pub fn ident(name: &str) -> ExprKind {
226 ExprKind::Atom(Atom::new(SyntaxObject::default(TokenType::Identifier(
227 name.into(),
228 ))))
229 }
230
231 pub fn ident_with_span(name: &str, span: Span) -> ExprKind {
232 ExprKind::Atom(Atom::new(SyntaxObject::new(
233 TokenType::Identifier(name.into()),
234 span,
235 )))
236 }
237
238 pub fn string_lit(input: String) -> ExprKind {
239 ExprKind::Atom(Atom::new(SyntaxObject::default(TokenType::StringLiteral(
240 Arc::new(input),
241 ))))
242 }
243
244 pub fn bool_lit(b: bool) -> ExprKind {
245 ExprKind::Atom(Atom::new(SyntaxObject::default(TokenType::BooleanLiteral(
246 b,
247 ))))
248 }
249
250 pub fn default_if(test: ExprKind, then: ExprKind, els: ExprKind) -> ExprKind {
251 ExprKind::If(Box::new(If::new(
252 test,
253 then,
254 els,
255 SyntaxObject::default(TokenType::If),
256 )))
257 }
258
259 pub fn into_atom_syntax_object(self) -> Option<SyntaxObject> {
260 match self {
261 Self::Atom(Atom { syn }) => Some(syn),
262 _ => None,
263 }
264 }
265
266 pub fn atom_syntax_object(&self) -> Option<&SyntaxObject> {
267 match self {
268 Self::Atom(Atom { syn }) => Some(syn),
269 _ => None,
270 }
271 }
272
273 pub fn atom_syntax_object_mut(&mut self) -> Option<&mut SyntaxObject> {
274 match self {
275 Self::Atom(Atom { syn }) => Some(syn),
276 _ => None,
277 }
278 }
279
280 pub fn define_syntax_ident(&self) -> bool {
281 match self {
282 Self::Atom(Atom {
283 syn:
284 SyntaxObject {
285 ty: TokenType::DefineSyntax,
286 ..
287 },
288 }) => true,
289 _ => false,
290 }
291 }
292
293 pub fn atom_identifier_mut(&mut self) -> Option<&mut InternedString> {
294 match self {
295 Self::Atom(Atom {
296 syn:
297 SyntaxObject {
298 ty: TokenType::Identifier(s),
299 ..
300 },
301 }) => Some(s),
302 _ => None,
303 }
304 }
305
306 pub fn lambda_function(&self) -> Option<&LambdaFunction> {
307 match self {
308 Self::LambdaFunction(l) => Some(l),
309 _ => None,
310 }
311 }
312
313 pub fn atom_identifier_or_else<E, F: FnOnce() -> E>(
314 &self,
315 err: F,
316 ) -> std::result::Result<&InternedString, E> {
317 match self {
318 Self::Atom(Atom {
319 syn:
320 SyntaxObject {
321 ty: TokenType::Identifier(s),
322 ..
323 },
324 }) => Ok(s),
325 _ => Err(err()),
326 }
327 }
328
329 pub fn atom_identifier(&self) -> Option<&InternedString> {
330 match self {
331 Self::Atom(Atom {
332 syn:
333 SyntaxObject {
334 ty: TokenType::Identifier(s),
335 ..
336 },
337 }) => Some(s),
338 _ => None,
339 }
340 }
341
342 pub fn string_literal(&self) -> Option<&str> {
343 match self {
344 Self::Atom(Atom {
345 syn:
346 SyntaxObject {
347 ty: TokenType::StringLiteral(s),
348 ..
349 },
350 }) => Some(s),
351 _ => None,
352 }
353 }
354
355 pub fn list(&self) -> Option<&List> {
356 if let ExprKind::List(l) = self {
357 Some(l)
358 } else {
359 None
360 }
361 }
362
363 pub fn list_mut(&mut self) -> Option<&mut List> {
364 if let ExprKind::List(l) = self {
365 Some(l)
366 } else {
367 None
368 }
369 }
370
371 pub fn list_or_else<E, F: FnOnce() -> E>(&self, err: F) -> std::result::Result<&List, E> {
372 match self {
373 Self::List(l) => Ok(l),
374 _ => Err(err()),
375 }
376 }
377
378 pub fn list_mut_or_else<E, F: FnOnce() -> E>(
379 &mut self,
380 err: F,
381 ) -> std::result::Result<&mut List, E> {
382 match self {
383 Self::List(l) => Ok(l),
384 _ => Err(err()),
385 }
386 }
387
388 pub fn into_list_or_else<E, F: FnOnce() -> E>(self, err: F) -> std::result::Result<List, E> {
389 match self {
390 Self::List(l) => Ok(l),
391 _ => Err(err()),
392 }
393 }
394
395 pub fn into_list(self) -> List {
396 if let ExprKind::List(l) = self {
397 l
398 } else {
399 panic!("Attempted to coerce a non list to a list");
400 }
401 }
402
403 pub fn unwrap_function(self) -> Option<Box<LambdaFunction>> {
404 if let ExprKind::LambdaFunction(l) = self {
405 Some(l)
406 } else {
407 None
408 }
409 }
410
411 pub fn get_list(&self) -> Option<&List> {
412 if let ExprKind::List(l) = self {
413 Some(l)
414 } else {
415 None
416 }
417 }
418
419 pub fn update_string_in_atom(&mut self, ident: InternedString) {
420 if let ExprKind::Atom(Atom {
421 syn:
422 SyntaxObject {
423 ty: TokenType::Identifier(ref mut s),
424 ..
425 },
426 }) = self
427 {
428 *s = ident;
429 }
430 }
431}
432
433pub trait ToDoc {
434 fn to_doc(&self) -> RcDoc<()>;
435}
436
437impl ToDoc for ExprKind {
438 fn to_doc(&self) -> RcDoc<()> {
439 match self {
440 ExprKind::Atom(a) => a.to_doc(),
441 ExprKind::If(i) => i.to_doc(),
442 ExprKind::Define(d) => d.to_doc(),
443 ExprKind::LambdaFunction(l) => l.to_doc(),
444 ExprKind::Begin(b) => b.to_doc(),
445 ExprKind::Return(r) => r.to_doc(),
446 ExprKind::Let(l) => l.to_doc(),
447 ExprKind::Quote(q) => q.to_doc(),
448 ExprKind::Macro(m) => m.to_doc(),
449 ExprKind::SyntaxRules(s) => s.to_doc(),
450 ExprKind::List(l) => l.to_doc(),
451 ExprKind::Set(s) => s.to_doc(),
452 ExprKind::Require(r) => r.to_doc(),
453 ExprKind::Vector(v) => v.to_doc(),
454 }
455 }
456}
457
458impl ExprKind {
459 pub fn to_pretty(&self, width: usize) -> String {
460 let mut w = Vec::new();
461 self.to_doc().render(width, &mut w).unwrap();
462 String::from_utf8(w).unwrap()
463 }
464}
465
466impl fmt::Display for ExprKind {
467 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
468 match self {
469 ExprKind::Atom(a) => write!(f, "{a}"),
470 ExprKind::If(i) => write!(f, "{i}"),
471 ExprKind::Define(d) => write!(f, "{d}"),
472 ExprKind::LambdaFunction(l) => write!(f, "{l}"),
473 ExprKind::Begin(b) => write!(f, "{b}"),
474 ExprKind::Return(r) => write!(f, "{r}"),
475 ExprKind::Let(l) => write!(f, "{l}"),
476 ExprKind::Quote(q) => write!(f, "{q}"),
477 ExprKind::Macro(m) => write!(f, "{m}"),
478 ExprKind::SyntaxRules(s) => write!(f, "{s}"),
479 ExprKind::List(l) => write!(f, "{l}"),
480 ExprKind::Set(s) => write!(f, "{s}"),
481 ExprKind::Require(r) => write!(f, "{r}"),
482 ExprKind::Vector(v) => write!(f, "{v}"),
483 }
484 }
485}
486
487#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
488pub struct Atom {
489 pub syn: SyntaxObject,
490}
491
492impl Atom {
493 pub fn new(syn: SyntaxObject) -> Self {
494 Atom { syn }
495 }
496
497 pub fn ident(&self) -> Option<&InternedString> {
498 if let TokenType::Identifier(ref ident) = self.syn.ty {
499 Some(ident)
500 } else {
501 None
502 }
503 }
504
505 pub fn ident_mut(&mut self) -> Option<&mut InternedString> {
506 if let TokenType::Identifier(ref mut ident) = self.syn.ty {
507 Some(ident)
508 } else {
509 None
510 }
511 }
512
513 pub fn byte(&self) -> Option<u8> {
514 let TokenType::Number(number) = &self.syn.ty else {
516 return None;
517 };
518
519 match &**number {
520 NumberLiteral::Real(RealLiteral::Int(int)) => match int {
521 IntLiteral::Small(int) => u8::try_from(*int).ok(),
522 IntLiteral::Big(bigint) => u8::try_from(&**bigint).ok(),
523 },
524 _ => None,
525 }
526 }
527}
528
529impl fmt::Display for Atom {
530 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
531 write!(f, "{}", self.syn.ty)
532 }
533}
534
535impl ToDoc for Atom {
536 fn to_doc(&self) -> RcDoc<()> {
537 RcDoc::text(self.syn.ty.to_string())
538 }
539}
540
541impl From<Atom> for ExprKind {
542 fn from(val: Atom) -> Self {
543 ExprKind::Atom(val)
544 }
545}
546
547#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
548pub struct Let {
549 pub bindings: Vec<(ExprKind, ExprKind)>,
550 pub body_expr: ExprKind,
551 pub location: SyntaxObject,
552 pub syntax_object_id: u32,
553}
554
555impl Let {
556 pub fn new(
557 bindings: Vec<(ExprKind, ExprKind)>,
558 body_expr: ExprKind,
559 location: SyntaxObject,
560 ) -> Self {
561 Let {
562 bindings,
563 body_expr,
564 location,
565 syntax_object_id: SyntaxObjectId::fresh().0,
566 }
567 }
568
569 pub fn local_bindings(&self) -> impl Iterator<Item = &'_ ExprKind> {
570 self.bindings.iter().map(|x| &x.0)
571 }
572
573 pub fn expression_arguments(&self) -> impl Iterator<Item = &'_ ExprKind> {
574 self.bindings.iter().map(|x| &x.1)
575 }
576}
577
578impl fmt::Display for Let {
579 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
580 write!(
581 f,
582 "(%plain-let ({}) {})",
583 self.bindings
584 .iter()
585 .map(|x| format!("({} {})", x.0, x.1))
586 .join(" "),
587 self.body_expr
588 )
589 }
590}
591
592impl ToDoc for Let {
593 fn to_doc(&self) -> RcDoc<()> {
594 RcDoc::text("(%plain-let")
595 .append(RcDoc::space())
596 .append(RcDoc::text("("))
597 .append(
598 RcDoc::intersperse(
599 self.bindings.iter().map(|x| {
600 RcDoc::text("(")
601 .append(x.0.to_doc())
602 .append(RcDoc::space())
603 .append(x.1.to_doc())
604 .append(RcDoc::text(")"))
605 }),
606 RcDoc::line(),
607 )
608 .nest(2)
609 .group(),
610 )
611 .append(RcDoc::text(")"))
612 .append(RcDoc::line())
613 .append(self.body_expr.to_doc())
614 .append(RcDoc::text(")"))
615 .nest(2)
616 }
617}
618
619impl From<Let> for ExprKind {
620 fn from(val: Let) -> Self {
621 ExprKind::Let(Box::new(val))
622 }
623}
624
625#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
626pub struct Set {
627 pub variable: ExprKind,
628 pub expr: ExprKind,
629 pub location: SyntaxObject,
630}
631
632impl Set {
633 pub fn new(variable: ExprKind, expr: ExprKind, location: SyntaxObject) -> Self {
634 Set {
635 variable,
636 expr,
637 location,
638 }
639 }
640}
641
642impl fmt::Display for Set {
643 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
644 write!(f, "(set! {} {})", self.variable, self.expr)
645 }
646}
647
648impl ToDoc for Set {
649 fn to_doc(&self) -> RcDoc<()> {
650 RcDoc::text("(set!")
651 .append(RcDoc::space())
652 .append(self.variable.to_doc())
653 .append(RcDoc::line())
654 .append(self.expr.to_doc())
655 .append(RcDoc::text(")"))
656 .nest(2)
657 .group()
658 }
659}
660
661impl From<Set> for ExprKind {
662 fn from(val: Set) -> Self {
663 ExprKind::Set(Box::new(val))
664 }
665}
666
667#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
668pub struct If {
669 pub test_expr: ExprKind,
670 pub then_expr: ExprKind,
671 pub else_expr: ExprKind,
672 pub location: SyntaxObject,
673}
674
675impl ToDoc for If {
676 fn to_doc(&self) -> RcDoc<()> {
677 RcDoc::text("(if")
678 .append(RcDoc::space())
679 .append(self.test_expr.to_doc())
680 .append(RcDoc::line())
681 .append(self.then_expr.to_doc())
682 .append(RcDoc::line())
683 .append(self.else_expr.to_doc())
684 .append(RcDoc::text(")"))
685 .nest(2)
686 .group()
687 }
688}
689
690impl fmt::Display for If {
691 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
692 write!(
693 f,
694 "(if {} {} {})",
695 self.test_expr, self.then_expr, self.else_expr
696 )
697 }
698}
699
700impl If {
701 pub fn new(
702 test_expr: ExprKind,
703 then_expr: ExprKind,
704 else_expr: ExprKind,
705 location: SyntaxObject,
706 ) -> Self {
707 If {
708 test_expr,
709 then_expr,
710 else_expr,
711 location,
712 }
713 }
714}
715
716impl From<If> for ExprKind {
717 fn from(val: If) -> Self {
718 ExprKind::If(Box::new(val))
719 }
720}
721
722#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
724pub struct Define {
725 pub name: ExprKind,
727 pub body: ExprKind,
728 pub location: SyntaxObject,
729}
730
731impl fmt::Display for Define {
732 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
733 write!(f, "(define {} {})", self.name, self.body)
734 }
735}
736
737impl ToDoc for Define {
738 fn to_doc(&self) -> RcDoc<()> {
739 RcDoc::text("(define")
740 .append(RcDoc::space())
741 .append(self.name.to_doc())
742 .append(RcDoc::line())
743 .append(self.body.to_doc())
744 .append(RcDoc::text(")"))
745 .nest(2)
746 }
747}
748
749impl Define {
750 pub fn new(name: ExprKind, body: ExprKind, location: SyntaxObject) -> Self {
751 Define {
752 name,
753 body,
754 location,
755 }
756 }
757
758 pub fn is_an_alias_definition(&self) -> Option<SyntaxObjectId> {
759 if let Some(atom) = self.body.atom_syntax_object() {
760 if let TokenType::Identifier(_) = atom.ty {
761 return Some(atom.syntax_object_id);
762 }
763 }
764
765 None
766 }
767
768 pub fn name_id(&self) -> Option<SyntaxObjectId> {
769 self.name.atom_syntax_object().map(|x| x.syntax_object_id)
770 }
771}
772
773impl From<Define> for ExprKind {
774 fn from(val: Define) -> Self {
775 ExprKind::Define(Box::new(val))
776 }
777}
778
779#[derive(Debug, Serialize, Deserialize)]
780pub struct LambdaFunction {
781 pub args: Vec<ExprKind>,
782 pub body: ExprKind,
783 pub location: SyntaxObject,
784 pub rest: bool,
785 pub syntax_object_id: u32,
786 pub kwargs: bool,
789}
790
791impl Clone for LambdaFunction {
792 fn clone(&self) -> Self {
793 Self {
794 args: self.args.clone(),
795 body: self.body.clone(),
796 location: self.location.clone(),
797 rest: self.rest,
798 syntax_object_id: SyntaxObjectId::fresh().0,
799 kwargs: self.kwargs,
800 }
801 }
802}
803
804impl PartialEq for LambdaFunction {
805 fn eq(&self, other: &Self) -> bool {
806 self.args == other.args
807 && self.body == other.body
808 && self.location == other.location
809 && self.rest == other.rest
810 }
811}
812
813impl fmt::Display for LambdaFunction {
814 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
815 write!(
816 f,
817 "(lambda ({}) {})",
818 self.args.iter().map(|x| x.to_string()).join(" "),
819 self.body
820 )
821 }
822}
823
824impl ToDoc for LambdaFunction {
825 fn to_doc(&self) -> RcDoc<()> {
826 if self.rest && self.args.len() == 1 {
827 RcDoc::text("(λ")
828 .append(RcDoc::space())
829 .append(self.args.first().unwrap().to_doc())
830 .append(RcDoc::line())
831 .append(self.body.to_doc())
832 .append(RcDoc::text(")"))
833 .nest(2)
834 } else {
835 RcDoc::text("(λ")
836 .append(RcDoc::space())
837 .append(RcDoc::text("("))
838 .append(
839 RcDoc::intersperse(self.args.iter().map(|x| x.to_doc()), RcDoc::line())
840 .nest(2)
841 .group(),
842 )
843 .append(RcDoc::text(")"))
844 .append(RcDoc::line())
845 .append(self.body.to_doc())
846 .append(RcDoc::text(")"))
847 .nest(2)
848 }
849 }
850}
851
852impl LambdaFunction {
853 pub fn new(args: Vec<ExprKind>, body: ExprKind, location: SyntaxObject) -> Self {
854 LambdaFunction {
855 args,
856 body,
857 location,
858 rest: false,
859 syntax_object_id: SyntaxObjectId::fresh().0,
860 kwargs: false,
861 }
862 }
863
864 pub fn new_with_rest_arg(args: Vec<ExprKind>, body: ExprKind, location: SyntaxObject) -> Self {
865 LambdaFunction {
866 args,
867 body,
868 location,
869 rest: true,
870 syntax_object_id: SyntaxObjectId::fresh().0,
871 kwargs: false,
872 }
873 }
874
875 pub fn new_maybe_rest(
876 args: Vec<ExprKind>,
877 body: ExprKind,
878 location: SyntaxObject,
879 rest: bool,
880 ) -> Self {
881 LambdaFunction {
882 args,
883 body,
884 location,
885 rest,
886 syntax_object_id: SyntaxObjectId::fresh().0,
887 kwargs: false,
888 }
889 }
890
891 pub fn arguments(&self) -> Option<Vec<&InternedString>> {
892 self.args.iter().map(|x| x.atom_identifier()).collect()
893 }
894
895 pub fn arguments_mut(&mut self) -> impl Iterator<Item = &mut InternedString> {
896 self.args.iter_mut().filter_map(|x| x.atom_identifier_mut())
897 }
898
899 pub fn syntax_objects_arguments_mut(&mut self) -> impl Iterator<Item = &mut SyntaxObject> {
900 self.args
901 .iter_mut()
902 .filter_map(|x| x.atom_syntax_object_mut())
903 }
904}
905
906impl From<LambdaFunction> for ExprKind {
907 fn from(val: LambdaFunction) -> Self {
908 ExprKind::LambdaFunction(Box::new(val))
909 }
910}
911
912#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
913pub struct Begin {
914 pub exprs: Vec<ExprKind>,
915 pub location: SyntaxObject,
916}
917
918impl fmt::Display for Begin {
919 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
920 write!(f, "(begin {})", self.exprs.iter().join(" "))
921 }
922}
923
924impl ToDoc for Begin {
925 fn to_doc(&self) -> RcDoc<()> {
926 RcDoc::text("(begin")
927 .append(RcDoc::line())
928 .nest(5)
929 .append(
930 RcDoc::intersperse(self.exprs.iter().map(|x| x.to_doc()), RcDoc::line())
931 .nest(5)
932 .group(),
933 )
934 .append(RcDoc::text(")"))
935 .nest(1)
936 .group()
937 }
938}
939
940impl Begin {
941 pub fn new(exprs: Vec<ExprKind>, location: SyntaxObject) -> Self {
942 Begin { exprs, location }
943 }
944}
945
946impl From<Begin> for ExprKind {
947 fn from(val: Begin) -> Self {
948 ExprKind::Begin(Box::new(val))
949 }
950}
951
952#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
953pub struct Return {
954 pub expr: ExprKind,
955 pub location: SyntaxObject,
956}
957
958impl Return {
959 pub fn new(expr: ExprKind, location: SyntaxObject) -> Self {
960 Return { expr, location }
961 }
962}
963
964impl ToDoc for Return {
965 fn to_doc(&self) -> RcDoc<()> {
966 RcDoc::text("(return")
967 .append(RcDoc::line())
968 .append(self.expr.to_doc())
969 .append(RcDoc::text(")"))
970 .nest(2)
971 }
972}
973
974impl fmt::Display for Return {
975 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
976 write!(f, "(return! {})", self.expr)
977 }
978}
979
980impl From<Return> for ExprKind {
981 fn from(val: Return) -> Self {
982 ExprKind::Return(Box::new(val))
983 }
984}
985
986#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
987pub struct Require {
988 pub modules: Vec<ExprKind>,
989 pub location: SyntaxObject,
990}
991
992impl Require {
993 pub fn new(modules: Vec<ExprKind>, location: SyntaxObject) -> Self {
994 Require { modules, location }
995 }
996}
997
998impl ToDoc for Require {
999 fn to_doc(&self) -> RcDoc<()> {
1000 RcDoc::text("(require")
1001 .append(RcDoc::line())
1002 .append(
1003 RcDoc::intersperse(self.modules.iter().map(|x| x.to_doc()), RcDoc::line())
1004 .nest(2)
1005 .group(),
1006 )
1007 .append(RcDoc::text(")"))
1008 .nest(2)
1009 }
1010}
1011
1012impl fmt::Display for Require {
1013 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1014 write!(f, "(require {})", self.modules.iter().join(" "))
1015 }
1016}
1017
1018impl From<Require> for ExprKind {
1019 fn from(val: Require) -> Self {
1020 ExprKind::Require(Box::new(val))
1021 }
1022}
1023
1024#[derive(Clone, Debug, Serialize, Deserialize, PartialEq)]
1025pub struct Vector {
1026 pub args: Vec<ExprKind>,
1027 pub bytes: bool,
1028 pub span: Span,
1029}
1030
1031impl Vector {
1032 fn prefix(&self) -> ParenMod {
1033 if self.bytes {
1034 ParenMod::Bytes
1035 } else {
1036 ParenMod::Vector
1037 }
1038 }
1039
1040 pub fn as_bytes(&self) -> impl Iterator<Item = u8> + '_ {
1041 self.args.iter().flat_map(move |expr| {
1042 let byte = if let ExprKind::Atom(atom) = expr {
1043 atom.byte()
1044 } else {
1045 None
1046 };
1047
1048 debug_assert!(!(self.bytes && byte.is_none()));
1049
1050 byte
1051 })
1052 }
1053}
1054
1055impl fmt::Display for Vector {
1056 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1057 write!(f, "{}(", self.prefix())?;
1058
1059 if let Some((first, rest)) = self.args.split_first() {
1060 write!(f, "{first}")?;
1061
1062 for arg in rest {
1063 write!(f, " {arg}")?;
1064 }
1065 }
1066
1067 write!(f, ")")
1068 }
1069}
1070
1071impl ToDoc for Vector {
1072 fn to_doc(&self) -> RcDoc<()> {
1073 RcDoc::text(self.prefix().as_str())
1074 .append("(")
1075 .append(
1076 RcDoc::intersperse(self.args.iter().map(ToDoc::to_doc), RcDoc::line())
1077 .nest(1)
1078 .group(),
1079 )
1080 .append(RcDoc::text(")"))
1081 .nest(2)
1082 .group()
1083 }
1084}
1085
1086impl From<Vector> for ExprKind {
1087 fn from(value: Vector) -> Self {
1088 ExprKind::Vector(value)
1089 }
1090}
1091
1092#[derive(Clone, Debug, Serialize, Deserialize)]
1093pub struct List {
1094 pub args: Vec<ExprKind>,
1095 pub syntax_object_id: u32,
1096 pub improper: bool,
1097 pub location: Span,
1100}
1101
1102impl PartialEq for List {
1103 fn eq(&self, other: &Self) -> bool {
1104 self.args == other.args
1105 && self.improper == other.improper
1106 && self.location == other.location
1107 }
1108}
1109
1110impl List {
1111 pub fn new(args: Vec<ExprKind>) -> Self {
1112 List {
1113 args,
1114 syntax_object_id: SyntaxObjectId::fresh().0 as _,
1115 improper: false,
1116 location: Span::default(),
1117 }
1118 }
1119
1120 pub fn new_maybe_improper(args: Vec<ExprKind>, improper: bool) -> Self {
1121 List {
1122 args,
1123 syntax_object_id: SyntaxObjectId::fresh().0 as _,
1124 improper,
1125 location: Span::default(),
1126 }
1127 }
1128
1129 pub fn with_spans(args: Vec<ExprKind>, open: Span, close: Span) -> Self {
1130 List {
1131 args,
1132 improper: false,
1133 location: Span::merge(open, close),
1134 syntax_object_id: SyntaxObjectId::fresh().0 as _,
1135 }
1136 }
1137
1138 pub fn make_improper(&mut self) {
1139 let Some(last) = self.args.pop() else {
1140 debug_assert!(false);
1141
1142 self.improper = true;
1143
1144 return;
1145 };
1146
1147 let ExprKind::List(l) = last else {
1148 self.args.push(last);
1149
1150 self.improper = true;
1151
1152 return;
1153 };
1154
1155 self.args.extend(l.args);
1156 self.improper = l.improper;
1157 }
1158
1159 pub fn is_empty(&self) -> bool {
1160 self.args.is_empty()
1161 }
1162
1163 pub fn rest_mut(&mut self) -> Option<&mut [ExprKind]> {
1164 self.args.split_first_mut().map(|x| x.1)
1165 }
1166
1167 pub fn args_proper(self, ty: TokenType<&str>) -> Result<Vec<ExprKind>, ParseError> {
1168 if self.improper {
1169 return Err(ParseError::SyntaxError(
1170 format!("{} expression requires a proper list", ty),
1171 self.location,
1172 None,
1173 ));
1174 }
1175
1176 Ok(self.args)
1177 }
1178
1179 pub fn first_ident_mut(&mut self) -> Option<&mut InternedString> {
1180 if let Some(ExprKind::Atom(Atom {
1181 syn:
1182 SyntaxObject {
1183 ty: TokenType::Identifier(s),
1184 ..
1185 },
1186 })) = self.args.first_mut()
1187 {
1188 Some(s)
1189 } else {
1190 None
1191 }
1192 }
1193
1194 pub fn is_require(&self) -> bool {
1195 matches!(
1196 self.args.first(),
1197 Some(ExprKind::Atom(Atom {
1198 syn: SyntaxObject {
1199 ty: TokenType::Require,
1200 ..
1201 },
1202 }))
1203 )
1204 }
1205
1206 pub fn is_begin(&self) -> bool {
1207 matches!(
1208 self.args.first(),
1209 Some(ExprKind::Atom(Atom {
1210 syn: SyntaxObject {
1211 ty: TokenType::Begin,
1212 ..
1213 },
1214 }))
1215 )
1216 }
1217
1218 pub fn is_define_syntax(&self) -> bool {
1219 if let Some(ExprKind::Atom(Atom {
1220 syn:
1221 SyntaxObject {
1222 ty: TokenType::DefineSyntax,
1223 ..
1224 },
1225 })) = self.args.first()
1226 {
1227 self.args.len() == 3
1228 } else {
1229 false
1230 }
1231 }
1232
1233 pub fn is_syntax_rules(&self) -> bool {
1234 if let Some(ExprKind::Atom(Atom {
1235 syn:
1236 SyntaxObject {
1237 ty: TokenType::SyntaxRules,
1238 ..
1239 },
1240 })) = self.args.first()
1241 {
1242 self.args.len() > 2
1243 } else {
1244 false
1245 }
1246 }
1247
1248 pub fn is_quote(&self) -> bool {
1249 matches!(
1250 self.args.first(),
1251 Some(ExprKind::Atom(Atom {
1252 syn: SyntaxObject {
1253 ty: TokenType::Quote,
1254 ..
1255 },
1256 }))
1257 )
1258 }
1259
1260 pub fn first_ident(&self) -> Option<&InternedString> {
1261 if let Some(ExprKind::Atom(Atom {
1262 syn:
1263 SyntaxObject {
1264 ty: TokenType::Identifier(s),
1265 ..
1266 },
1267 })) = self.args.first()
1268 {
1269 Some(s)
1270 } else {
1271 None
1272 }
1273 }
1274
1275 pub fn second_ident(&self) -> Option<&InternedString> {
1276 if let Some(ExprKind::Atom(Atom {
1277 syn:
1278 SyntaxObject {
1279 ty: TokenType::Identifier(s),
1280 ..
1281 },
1282 })) = self.args.get(1)
1283 {
1284 Some(s)
1285 } else {
1286 None
1287 }
1288 }
1289
1290 pub fn is_anonymous_function_call(&self) -> bool {
1291 matches!(self.args.get(0), Some(ExprKind::LambdaFunction(_)))
1292 }
1293
1294 pub fn is_a_builtin_expr(&self) -> bool {
1295 matches!(self.first_ident(), Some(func) if *func == *UNREADABLE_MODULE_GET || *func == *STANDARD_MODULE_GET)
1296 }
1297
1298 pub fn first_func_mut(&mut self) -> Option<&mut LambdaFunction> {
1299 if let Some(ExprKind::LambdaFunction(l)) = self.args.first_mut() {
1300 Some(l)
1301 } else {
1302 None
1303 }
1304 }
1305
1306 pub fn first_func(&self) -> Option<&LambdaFunction> {
1307 if let Some(ExprKind::LambdaFunction(l)) = self.args.first() {
1308 Some(l)
1309 } else {
1310 None
1311 }
1312 }
1313
1314 pub fn split_improper(&self) -> Option<(&[ExprKind], &ExprKind)> {
1315 if self.improper {
1316 self.args.split_last().map(|(last, rest)| (rest, last))
1317 } else {
1318 None
1319 }
1320 }
1321}
1322
1323impl ToDoc for List {
1324 fn to_doc(&self) -> RcDoc<()> {
1325 if let Some(func) = self.first_func().filter(|_| !self.improper) {
1326 let mut args_iter = self.args.iter();
1327 args_iter.next();
1328
1329 let bindings = func.args.iter().zip(args_iter);
1330
1331 RcDoc::text("(let")
1332 .append(RcDoc::space())
1333 .append(RcDoc::text("("))
1334 .append(
1335 RcDoc::intersperse(
1336 bindings.map(|x| {
1337 RcDoc::text("(")
1338 .append(x.0.to_doc())
1339 .append(RcDoc::space())
1340 .append(x.1.to_doc())
1341 .append(RcDoc::text(")"))
1342 }),
1343 RcDoc::line(),
1344 )
1345 .nest(2)
1346 .group(),
1347 )
1348 .append(RcDoc::text(")"))
1349 .append(RcDoc::line())
1350 .append(func.body.to_doc())
1351 .append(RcDoc::text(")"))
1352 .nest(2)
1353 } else {
1354 let args = if let Some((car, cdr)) = self.split_improper() {
1355 let iter = car
1356 .iter()
1357 .map(ToDoc::to_doc)
1358 .chain(std::iter::once(RcDoc::text(".")))
1359 .chain(std::iter::once(cdr.to_doc()));
1360
1361 RcDoc::intersperse(iter, RcDoc::line())
1362 } else {
1363 RcDoc::intersperse(self.args.iter().map(ToDoc::to_doc), RcDoc::line())
1364 };
1365
1366 RcDoc::text("(")
1367 .append(args.nest(1).group())
1368 .append(RcDoc::text(")"))
1369 .nest(2)
1370 .group()
1371 }
1372 }
1373}
1374
1375impl fmt::Display for List {
1376 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1377 let Some((car, cdr)) = self.split_improper() else {
1378 return write!(f, "({})", self.args.iter().join(" "));
1379 };
1380
1381 write!(f, "(")?;
1382
1383 for arg in car {
1384 write!(f, "{} ", arg)?;
1385 }
1386
1387 write!(f, ". {})", cdr)
1388 }
1389}
1390
1391impl From<List> for ExprKind {
1392 fn from(val: List) -> Self {
1393 ExprKind::List(val)
1394 }
1395}
1396
1397impl Deref for List {
1398 type Target = [ExprKind];
1399
1400 fn deref(&self) -> &[ExprKind] {
1401 &self.args
1402 }
1403}
1404
1405impl IntoIterator for List {
1407 type Item = ExprKind;
1408 type IntoIter = std::vec::IntoIter<Self::Item>;
1409
1410 fn into_iter(self) -> Self::IntoIter {
1411 self.args.into_iter()
1412 }
1413}
1414
1415#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
1416pub struct Quote {
1417 pub expr: ExprKind,
1418 pub location: SyntaxObject,
1419}
1420
1421impl Quote {
1422 pub fn new(expr: ExprKind, location: SyntaxObject) -> Self {
1423 Quote { expr, location }
1424 }
1425}
1426
1427impl ToDoc for Quote {
1428 fn to_doc(&self) -> RcDoc<()> {
1429 RcDoc::text("(quote")
1430 .append(RcDoc::line())
1431 .append(self.expr.to_doc())
1432 .append(RcDoc::text(")"))
1433 .nest(2)
1434 }
1435}
1436
1437impl fmt::Display for Quote {
1438 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1439 write!(f, "(quote {})", self.expr)
1440 }
1441}
1442
1443impl From<Quote> for ExprKind {
1444 fn from(val: Quote) -> Self {
1445 ExprKind::Quote(Box::new(val))
1446 }
1447}
1448
1449#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
1452pub struct Macro {
1453 pub name: Box<ExprKind>,
1454 pub syntax_rules: Box<SyntaxRules>,
1455 pub location: SyntaxObject,
1456}
1457
1458impl fmt::Display for Macro {
1459 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1460 write!(f, "(define-syntax {} {})", self.name, self.syntax_rules)
1461 }
1462}
1463
1464impl ToDoc for Macro {
1465 fn to_doc(&self) -> RcDoc<()> {
1466 RcDoc::text("(define-syntax")
1467 .append(RcDoc::line())
1468 .append(self.name.to_doc())
1469 .append(RcDoc::line())
1470 .append(self.syntax_rules.to_doc())
1471 .append(RcDoc::text(")"))
1472 .nest(1)
1473 .group()
1474 }
1475}
1476
1477impl Macro {
1478 pub fn new(name: ExprKind, syntax_rules: Box<SyntaxRules>, location: SyntaxObject) -> Self {
1479 Macro {
1480 name: Box::new(name),
1481 syntax_rules,
1482 location,
1483 }
1484 }
1485}
1486
1487impl From<Macro> for ExprKind {
1488 fn from(val: Macro) -> Self {
1489 ExprKind::Macro(Box::new(val))
1490 }
1491}
1492
1493#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
1496pub struct SyntaxRules {
1497 pub syntax: Vec<ExprKind>,
1498 pub patterns: Vec<PatternPair>,
1499 pub location: SyntaxObject,
1500}
1501
1502impl SyntaxRules {
1503 pub fn new(syntax: Vec<ExprKind>, patterns: Vec<PatternPair>, location: SyntaxObject) -> Self {
1504 SyntaxRules {
1505 syntax,
1506 patterns,
1507 location,
1508 }
1509 }
1510}
1511
1512impl fmt::Display for SyntaxRules {
1513 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1514 write!(
1515 f,
1516 "(syntax-rules ({}) {})",
1517 self.syntax.iter().map(|x| x.to_string()).join(" "),
1518 self.patterns.iter().map(|x| x.to_string()).join("\n")
1519 )
1520 }
1521}
1522
1523impl ToDoc for SyntaxRules {
1524 fn to_doc(&self) -> RcDoc<()> {
1525 RcDoc::text("(syntax-rules")
1526 .append(RcDoc::line())
1527 .append(RcDoc::text("("))
1528 .append(
1529 RcDoc::intersperse(self.syntax.iter().map(|x| x.to_doc()), RcDoc::line())
1530 .nest(1)
1531 .group(),
1532 )
1533 .append(RcDoc::text(")"))
1534 .append(RcDoc::line())
1535 .append(
1536 RcDoc::intersperse(self.patterns.iter().map(|x| x.to_doc()), RcDoc::line())
1537 .nest(2)
1538 .group(),
1539 )
1540 .append(RcDoc::text(")"))
1541 .nest(2)
1542 }
1543}
1544
1545impl From<SyntaxRules> for ExprKind {
1546 fn from(val: SyntaxRules) -> Self {
1547 ExprKind::SyntaxRules(Box::new(val))
1548 }
1549}
1550
1551#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
1552pub struct PatternPair {
1553 pub pattern: ExprKind,
1554 pub body: ExprKind,
1555}
1556
1557impl PatternPair {
1558 pub fn new(pattern: ExprKind, body: ExprKind) -> Self {
1559 PatternPair { pattern, body }
1560 }
1561}
1562
1563impl ToDoc for PatternPair {
1564 fn to_doc(&self) -> RcDoc<()> {
1565 RcDoc::text("[")
1566 .append(self.pattern.to_doc())
1567 .append(RcDoc::line())
1568 .append(self.body.to_doc())
1569 .append(RcDoc::text("]"))
1570 .nest(1)
1571 .group()
1572 }
1573}
1574
1575impl fmt::Display for PatternPair {
1576 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1577 write!(f, "[{}\n{}]", self.pattern, self.body)
1578 }
1579}
1580
1581#[inline]
1582pub(crate) fn parse_if<I>(
1583 mut value_iter: I,
1584 syn: SyntaxObject,
1585) -> std::result::Result<ExprKind, ParseError>
1586where
1587 I: Iterator<Item = ExprKind>,
1588{
1589 value_iter.next();
1591
1592 let ret_value = If::new(
1593 value_iter.next().ok_or_else(|| {
1594 ParseError::SyntaxError(
1595 "if expects a test condition, found none".to_string(),
1596 syn.span,
1597 None,
1598 )
1599 })?,
1600 value_iter.next().ok_or_else(|| {
1601 ParseError::SyntaxError(
1602 "if expects a then condition, found none".to_string(),
1603 syn.span,
1604 None,
1605 )
1606 })?,
1607 value_iter
1609 .next()
1610 .unwrap_or_else(|| ExprKind::ident("#%prim.void")),
1611 syn.clone(),
1619 )
1620 .into();
1621
1622 if value_iter.next().is_some() {
1623 Err(ParseError::SyntaxError(
1624 "if takes only 3 expressions".to_string(),
1625 syn.span,
1626 None,
1627 ))
1628 } else {
1629 Ok(ret_value)
1630 }
1631}
1632
1633#[inline]
1634pub(crate) fn parse_define<I>(
1635 mut value_iter: I,
1636 syn: SyntaxObject,
1637) -> std::result::Result<ExprKind, ParseError>
1638where
1639 I: Iterator<Item = ExprKind>,
1640{
1641 value_iter.next();
1642
1643 match value_iter.next().ok_or_else(|| {
1644 ParseError::SyntaxError(
1645 "define expects an identifier, found none".to_string(),
1646 syn.span,
1647 None,
1648 )
1649 })? {
1650 ExprKind::List(l) => {
1653 let name_ref = l.args.first().ok_or_else(|| {
1654 ParseError::SyntaxError(
1655 "define expected a function name, found none".to_string(),
1656 syn.span,
1657 None,
1658 )
1659 })?;
1660
1661 if let ExprKind::Atom(Atom {
1662 syn:
1663 SyntaxObject {
1664 ty: TokenType::Identifier(datum_syntax),
1665 ..
1666 },
1667 }) = name_ref
1668 {
1669 if *datum_syntax == *DATUM_SYNTAX {
1670 return Ok(ExprKind::Define(Box::new(Define::new(
1671 ExprKind::List(List::new(l.args)),
1672 {
1673 let v = value_iter.next().ok_or_else(|| {
1674 ParseError::SyntaxError(
1675 "define statement expected a body, found none".to_string(),
1676 syn.span,
1677 None,
1678 )
1679 })?;
1680 if value_iter.next().is_some() {
1681 return Err(ParseError::SyntaxError(
1682 "Define expected only one expression after the identifier"
1683 .to_string(),
1684 syn.span,
1685 None,
1686 ));
1687 }
1688 v
1689 },
1690 syn,
1691 ))));
1692 }
1693 }
1694
1695 let mut args = l.args.into_iter();
1696
1697 let name = args.next().ok_or_else(|| {
1698 ParseError::SyntaxError(
1699 "define expected a function name, found none".to_string(),
1700 syn.span,
1701 None,
1702 )
1703 })?;
1704
1705 let args = args.collect();
1706
1707 let body_exprs: Vec<_> = value_iter.collect();
1708
1709 if body_exprs.is_empty() {
1710 return Err(ParseError::SyntaxError(
1711 "Function body cannot be empty".to_string(),
1712 syn.span,
1713 None,
1714 ));
1715 }
1716
1717 let body = if body_exprs.len() == 1 {
1718 body_exprs[0].clone()
1719 } else {
1720 ExprKind::Begin(Box::new(Begin::new(
1721 body_exprs,
1722 SyntaxObject::default(TokenType::Begin),
1723 )))
1724 };
1725
1726 let rest = l.improper;
1727 let lambda = ExprKind::LambdaFunction(Box::new(LambdaFunction::new_maybe_rest(
1728 args,
1729 body,
1730 SyntaxObject::new(TokenType::Lambda, syn.span),
1731 rest,
1732 )));
1733
1734 Ok(ExprKind::Define(Box::new(Define::new(name, lambda, syn))))
1735 }
1736 ExprKind::Atom(a) => Ok(ExprKind::Define(Box::new(Define::new(
1737 ExprKind::Atom(a),
1738 {
1739 let v = value_iter.next().ok_or_else(|| {
1740 ParseError::SyntaxError(
1741 "define statement expected a body, found none".to_string(),
1742 syn.span,
1743 None,
1744 )
1745 })?;
1746 if value_iter.next().is_some() {
1747 return Err(ParseError::SyntaxError(
1748 "Define expected only one expression after the identifier".to_string(),
1749 syn.span,
1750 None,
1751 ));
1752 }
1753 v
1754 },
1755 syn,
1756 )))),
1757
1758 _ => Err(ParseError::SyntaxError(
1759 "Define expects either an identifier or a list with the function name and arguments"
1760 .to_string(),
1761 syn.span,
1762 None,
1763 )),
1764 }
1765}
1766
1767#[inline]
1768pub(crate) fn parse_new_let<I>(
1769 mut value_iter: I,
1770 syn: SyntaxObject,
1771) -> std::result::Result<ExprKind, ParseError>
1772where
1773 I: Iterator<Item = ExprKind>,
1774{
1775 value_iter.next();
1776
1777 let let_pairs = if let ExprKind::List(l) = value_iter.next().ok_or_else(|| {
1778 ParseError::SyntaxError(
1779 "let expected a list of variable bindings pairs in the second position, found none"
1780 .to_string(),
1781 syn.span,
1782 None,
1783 )
1784 })? {
1785 l.args
1786 } else {
1787 return Err(ParseError::SyntaxError(
1788 "let expects a list of variable bindings pairs in the second position".to_string(),
1789 syn.span,
1790 None,
1791 ));
1792 };
1793
1794 let body_exprs: Vec<_> = value_iter.collect();
1795
1796 if body_exprs.is_empty() {
1797 return Err(ParseError::SyntaxError(
1798 "let expects an expression, found none".to_string(),
1799 syn.span,
1800 None,
1801 ));
1802 }
1803
1804 let body = if body_exprs.len() == 1 {
1805 body_exprs[0].clone()
1806 } else {
1807 ExprKind::Begin(Box::new(Begin::new(
1808 body_exprs,
1809 SyntaxObject::default(TokenType::Begin),
1810 )))
1811 };
1812
1813 let mut pairs = Vec::with_capacity(let_pairs.len());
1814
1815 for pair in let_pairs {
1816 if let ExprKind::List(l) = pair {
1817 let pair = l.args;
1818
1819 if pair.len() != 2 {
1820 return Err(ParseError::SyntaxError(
1821 format!("let expected a list of variable binding pairs, found a pair with length {}",
1822 pair.len()),
1823 syn.span, None
1824 ));
1825 }
1826
1827 let mut iter = pair.into_iter();
1828
1829 let identifier = iter.next().unwrap();
1830 let application_arg = iter.next().unwrap();
1831 pairs.push((identifier, application_arg))
1832 } else {
1833 return Err(ParseError::SyntaxError(
1834 "let expected a list of variable binding pairs".to_string(),
1835 syn.span,
1836 None,
1837 ));
1838 }
1839 }
1840
1841 Ok(ExprKind::Let(Let::new(pairs, body, syn).into()))
1842}
1843
1844#[inline]
1845fn parse_named_let<I>(
1846 mut value_iter: I,
1847 syn: SyntaxObject,
1848 name: ExprKind,
1849) -> std::result::Result<ExprKind, ParseError>
1850where
1851 I: Iterator<Item = ExprKind>,
1852{
1853 let pairs = if let ExprKind::List(l) = value_iter.next().ok_or_else(|| {
1854 ParseError::SyntaxError(
1855 "named let expects a list of argument id and init expr pairs, found none".to_string(),
1856 syn.span,
1857 None,
1858 )
1859 })? {
1860 l.args
1861 } else {
1862 return Err(ParseError::SyntaxError(
1863 "named let expects a list of variable bindings pairs in the second position"
1864 .to_string(),
1865 syn.span,
1866 None,
1867 ));
1868 };
1869
1870 let body_exprs: Vec<_> = value_iter.collect();
1871
1872 if body_exprs.is_empty() {
1873 return Err(ParseError::SyntaxError(
1874 "let expects an expression, found none".to_string(),
1875 syn.span,
1876 None,
1877 ));
1878 }
1879
1880 let body = if body_exprs.len() == 1 {
1881 body_exprs[0].clone()
1882 } else {
1883 ExprKind::Begin(Box::new(Begin::new(
1884 body_exprs,
1885 SyntaxObject::default(TokenType::Begin),
1886 )))
1887 };
1888
1889 let mut arguments = Vec::with_capacity(pairs.len());
1890
1891 let mut application_args = Vec::with_capacity(pairs.len());
1894
1895 for pair in pairs {
1896 if let ExprKind::List(l) = pair {
1897 let pair = l.args;
1898
1899 if pair.len() != 2 {
1900 return Err(ParseError::SyntaxError(
1901 format!("let expected a list of variable binding pairs, found a pair with length {}",
1902 pair.len()),
1903 syn.span, None
1904 ));
1905 }
1906
1907 let identifier = pair[0].clone();
1908 let application_arg = pair[1].clone();
1909
1910 arguments.push(identifier);
1911 application_args.push(application_arg);
1912 } else {
1913 return Err(ParseError::SyntaxError(
1914 "let expected a list of variable binding pairs".to_string(),
1915 syn.span,
1916 None,
1917 ));
1918 }
1919 }
1920
1921 let function: ExprKind = LambdaFunction::new(arguments, body, syn.clone()).into();
1923
1924 let define: ExprKind = Define::new(name.clone(), function, syn.clone()).into();
1925
1926 let application: ExprKind = {
1927 let mut application = vec![name];
1928 application.append(&mut application_args);
1929 List::new(application).into()
1930 };
1931
1932 let begin = ExprKind::Begin(Box::new(Begin::new(vec![define, application], syn.clone())));
1933
1934 Ok(List::new(vec![LambdaFunction::new(vec![], begin, syn).into()]).into())
1937}
1938
1939#[inline]
1940pub(crate) fn parse_let<I>(
1941 mut value_iter: I,
1942 mut syn: SyntaxObject,
1943) -> std::result::Result<ExprKind, ParseError>
1944where
1945 I: Iterator<Item = ExprKind>,
1946{
1947 value_iter.next();
1948
1949 let let_pairs = match value_iter.next().ok_or_else(|| {
1950 ParseError::SyntaxError(
1951 "let expected a list of variable bindings pairs in the second position, found none"
1952 .to_string(),
1953 syn.span,
1954 None,
1955 )
1956 })? {
1957 ExprKind::List(l) => l.args,
1959 name @ ExprKind::Atom(_) => return parse_named_let(value_iter, syn, name),
1961 _ => {
1962 return Err(ParseError::SyntaxError(
1963 "let expects a list of variable bindings pairs in the second position".to_string(),
1964 syn.span,
1965 None,
1966 ));
1967 }
1968 };
1969
1970 let body_exprs: Vec<_> = value_iter.collect();
1971
1972 if body_exprs.is_empty() {
1973 return Err(ParseError::SyntaxError(
1974 "let expects an expression, found none".to_string(),
1975 syn.span,
1976 None,
1977 ));
1978 }
1979
1980 let body = if body_exprs.len() == 1 {
1981 body_exprs[0].clone()
1982 } else {
1983 ExprKind::Begin(Box::new(Begin::new(
1984 body_exprs,
1985 SyntaxObject::default(TokenType::Begin),
1986 )))
1987 };
1988
1989 let mut arguments = Vec::with_capacity(let_pairs.len());
1990
1991 let mut application_args = Vec::with_capacity(let_pairs.len());
1994
1995 for pair in let_pairs {
1996 if let ExprKind::List(l) = pair {
1997 let pair = l.args;
1998
1999 if pair.len() != 2 {
2000 return Err(ParseError::SyntaxError(
2001 format!("let expected a list of variable binding pairs, found a pair with length {}",
2002 pair.len()),
2003 syn.span, None
2004 ));
2005 }
2006
2007 let identifier = pair[0].clone();
2008 let application_arg = pair[1].clone();
2009
2010 arguments.push(identifier);
2011 application_args.push(application_arg);
2012 } else {
2013 return Err(ParseError::SyntaxError(
2014 "let expected a list of variable binding pairs".to_string(),
2015 syn.span,
2016 None,
2017 ));
2018 }
2019 }
2020
2021 syn.ty = TokenType::Lambda;
2023
2024 let mut function: Vec<ExprKind> = vec![LambdaFunction::new(arguments, body, syn).into()];
2025
2026 function.append(&mut application_args);
2027
2028 Ok(ExprKind::List(List::new(function)))
2029}
2030
2031#[inline]
2032pub(crate) fn parse_single_argument<I>(
2033 mut value_iter: I,
2034 syn: SyntaxObject,
2035 name: &'static str,
2036 constructor: fn(ExprKind, SyntaxObject) -> ExprKind,
2037) -> Result<ExprKind, ParseError>
2038where
2039 I: Iterator<Item = ExprKind>,
2040{
2041 value_iter.next();
2042
2043 let func = value_iter.next().ok_or_else(|| {
2044 ParseError::ArityMismatch(
2045 format!("{name} expected one argument, found none"),
2046 syn.span,
2047 None,
2048 )
2049 })?;
2050
2051 if value_iter.next().is_some() {
2052 Err(ParseError::SyntaxError(
2053 format!("{name} expects only one argument"),
2054 syn.span,
2055 None,
2056 ))
2057 } else {
2058 Ok(constructor(func, syn))
2059 }
2060}
2061
2062impl TryFrom<Vec<ExprKind>> for ExprKind {
2063 type Error = ParseError;
2064 fn try_from(value: Vec<ExprKind>) -> std::result::Result<Self, Self::Error> {
2065 if let Some(f) = value.first().cloned() {
2069 match f {
2070 ExprKind::Atom(a) => {
2071 match &a.syn.ty {
2074 TokenType::If => parse_if(value.into_iter(), a.syn.clone()),
2077 TokenType::Identifier(expr) if *expr == *IF => {
2078 parse_if(value.into_iter(), a.syn.clone())
2079 }
2080
2081 TokenType::Define => parse_define(value.into_iter(), a.syn.clone()),
2082 TokenType::Identifier(expr) if *expr == *DEFINE => {
2083 parse_define(value.into_iter(), a.syn.clone())
2084 }
2085
2086 TokenType::Let => parse_let(value.into_iter(), a.syn.clone()),
2087 TokenType::Identifier(expr) if *expr == *LET => {
2088 parse_let(value.into_iter(), a.syn.clone())
2089 }
2090
2091 TokenType::TestLet => parse_new_let(value.into_iter(), a.syn.clone()),
2093 TokenType::Identifier(expr) if *expr == *PLAIN_LET => {
2094 parse_new_let(value.into_iter(), a.syn.clone())
2095 }
2096
2097 TokenType::Quote => parse_single_argument(
2098 value.into_iter(),
2099 a.syn.clone(),
2100 "quote",
2101 |expr, syn| Quote::new(expr, syn).into(),
2102 ),
2103 TokenType::Identifier(expr) if *expr == *QUOTE => parse_single_argument(
2104 value.into_iter(),
2105 a.syn.clone(),
2106 "quote",
2107 |expr, syn| Quote::new(expr, syn).into(),
2108 ),
2109
2110 TokenType::Return => parse_single_argument(
2111 value.into_iter(),
2112 a.syn.clone(),
2113 "return!",
2114 |expr, syn| Return::new(expr, syn).into(),
2115 ),
2116 TokenType::Identifier(expr) if *expr == *RETURN => parse_single_argument(
2117 value.into_iter(),
2118 a.syn.clone(),
2119 "return!",
2120 |expr, syn| Return::new(expr, syn).into(),
2121 ),
2122
2123 TokenType::Require => parse_require(&a, value),
2124 TokenType::Identifier(expr) if *expr == *REQUIRE => {
2125 parse_require(&a, value)
2126 }
2127
2128 TokenType::Set => parse_set(&a, value),
2129 TokenType::Identifier(expr) if *expr == *SET => parse_set(&a, value),
2130
2131 TokenType::Begin => parse_begin(a, value),
2132 TokenType::Identifier(expr) if *expr == *BEGIN => parse_begin(a, value),
2133
2134 TokenType::Lambda => parse_lambda(a, value),
2135 TokenType::Identifier(expr)
2136 if *expr == *LAMBDA
2137 || *expr == *LAMBDA_FN
2138 || *expr == *LAMBDA_SYMBOL =>
2139 {
2140 parse_lambda(a, value)
2141 }
2142
2143 TokenType::Identifier(expr) if *expr == *DEFINE_SYNTAX => {
2144 let syn = a.syn.clone();
2145
2146 if value.len() < 3 {
2147 return Err(ParseError::SyntaxError(
2148 format!("define-syntax expects 2 arguments - the name of the macro and the syntax-rules, found {}", value.len()), syn.span, None
2149 ));
2150 }
2151
2152 let mut value_iter = value.into_iter();
2155 value_iter.next();
2156
2157 let name = value_iter.next().unwrap();
2158
2159 let syntax = value_iter.next();
2160
2161 let syntax_rules = if let Some(ExprKind::SyntaxRules(s)) = syntax {
2164 s
2165 } else {
2166 return Err(ParseError::SyntaxError(
2167 "define-syntax expected a syntax-rules object".to_string(),
2168 syn.span,
2169 None,
2170 ));
2171 };
2172
2173 Ok(ExprKind::Macro(Box::new(Macro::new(
2174 name,
2175 syntax_rules,
2176 syn,
2177 ))))
2178 }
2179
2180 TokenType::DefineSyntax => {
2181 let syn = a.syn.clone();
2182
2183 if value.len() < 3 {
2184 return Err(ParseError::SyntaxError(
2185 format!("define-syntax expects 2 arguments - the name of the macro and the syntax-rules, found {}", value.len()), syn.span, None
2186 ));
2187 }
2188
2189 let mut value_iter = value.into_iter();
2192 value_iter.next();
2193
2194 let name = value_iter.next().unwrap();
2195
2196 let syntax = value_iter.next();
2197
2198 let syntax_rules = if let Some(ExprKind::SyntaxRules(s)) = syntax {
2201 s
2202 } else {
2203 return Err(ParseError::SyntaxError(
2204 "define-syntax expected a syntax-rules object".to_string(),
2205 syn.span,
2206 None,
2207 ));
2208 };
2209
2210 Ok(ExprKind::Macro(Box::new(Macro::new(
2211 name,
2212 syntax_rules,
2213 syn,
2214 ))))
2215 }
2216 TokenType::SyntaxRules => {
2217 let syn = a.syn.clone();
2218
2219 if value.len() < 3 {
2220 return Err(ParseError::SyntaxError(
2221 format!("syntax-rules expects a list of introduced syntax, and at least one pattern-body pair, found {} arguments", value.len()), syn.span, None
2222 ));
2223 }
2224
2225 let mut value_iter = value.into_iter();
2226 value_iter.next();
2227
2228 let syntax_vec = if let Some(ExprKind::List(l)) = value_iter.next() {
2229 l.args
2230 } else {
2231 return Err(ParseError::SyntaxError(
2232 "syntax-rules expects a list of new syntax forms used in the macro".to_string(), syn.span, None));
2233 };
2234
2235 let mut pairs = Vec::new();
2236 let rest: Vec<_> = value_iter.collect();
2237
2238 for pair in rest {
2239 if let ExprKind::List(l) = pair {
2240 if l.args.len() != 2 {
2241 return Err(ParseError::SyntaxError(
2242 "syntax-rules requires only one pattern to one body"
2243 .to_string(),
2244 syn.span,
2245 None,
2246 ));
2247 }
2248
2249 let mut pair_iter = l.args.into_iter();
2250 let pair_object = PatternPair::new(
2251 pair_iter.next().unwrap(),
2252 pair_iter.next().unwrap(),
2253 );
2254 pairs.push(pair_object);
2255 } else {
2256 return Err(ParseError::SyntaxError(
2257 "syntax-rules requires pattern to expressions to be in a list".to_string(), syn.span, None
2258 ));
2259 }
2260 }
2261
2262 Ok(ExprKind::SyntaxRules(Box::new(SyntaxRules::new(
2263 syntax_vec, pairs, syn,
2264 ))))
2265 }
2266
2267 TokenType::Identifier(expr) if *expr == *SYNTAX_RULES => {
2268 let syn = a.syn.clone();
2269
2270 if value.len() < 3 {
2271 return Err(ParseError::SyntaxError(
2272 format!("syntax-rules expects a list of introduced syntax, and at least one pattern-body pair, found {} arguments", value.len()), syn.span, None
2273 ));
2274 }
2275
2276 let mut value_iter = value.into_iter();
2277 value_iter.next();
2278
2279 let syntax_vec = if let Some(ExprKind::List(l)) = value_iter.next() {
2280 l.args
2281 } else {
2282 return Err(ParseError::SyntaxError(
2283 "syntax-rules expects a list of new syntax forms used in the macro".to_string(), syn.span, None));
2284 };
2285
2286 let mut pairs = Vec::new();
2287 let rest: Vec<_> = value_iter.collect();
2288
2289 for pair in rest {
2290 if let ExprKind::List(l) = pair {
2291 if l.args.len() != 2 {
2292 return Err(ParseError::SyntaxError(
2293 "syntax-rules requires only one pattern to one body"
2294 .to_string(),
2295 syn.span,
2296 None,
2297 ));
2298 }
2299
2300 let mut pair_iter = l.args.into_iter();
2301 let pair_object = PatternPair::new(
2302 pair_iter.next().unwrap(),
2303 pair_iter.next().unwrap(),
2304 );
2305 pairs.push(pair_object);
2306 } else {
2307 return Err(ParseError::SyntaxError(
2308 "syntax-rules requires pattern to expressions to be in a list".to_string(), syn.span, None
2309 ));
2310 }
2311 }
2312
2313 Ok(ExprKind::SyntaxRules(Box::new(SyntaxRules::new(
2314 syntax_vec, pairs, syn,
2315 ))))
2316 }
2317 _ => Ok(ExprKind::List(List::new(value))),
2318 }
2319 }
2320 _ => Ok(ExprKind::List(List::new(value))),
2321 }
2322 } else {
2323 Ok(ExprKind::List(List::new(vec![])))
2324 }
2325 }
2326}
2327
2328pub fn parse_lambda(a: Atom, value: Vec<ExprKind>) -> Result<ExprKind, ParseError> {
2329 let syn = a.syn;
2330 if value.len() < 3 {
2331 return Err(ParseError::SyntaxError(
2332 format!(
2333 "lambda expected at least 2 arguments - the bindings list and one or more expressions, found {} instead",
2334 value.len()
2335 ),
2336 syn.span, None
2337 ));
2338 }
2339 let mut value_iter = value.into_iter();
2340 value_iter.next();
2341 let arguments = value_iter.next();
2342 match arguments {
2343 Some(ExprKind::List(l)) => {
2344 let args = l.args;
2345
2346 let body_exprs: Vec<_> = value_iter.collect();
2362
2363 let body = if body_exprs.len() == 1 {
2364 body_exprs.into_iter().next().unwrap()
2365 } else {
2366 ExprKind::Begin(Box::new(Begin::new(
2367 body_exprs,
2368 SyntaxObject::default(TokenType::Begin),
2369 )))
2370 };
2371
2372 let rest = l.improper;
2373
2374 Ok(ExprKind::LambdaFunction(Box::new(
2375 LambdaFunction::new_maybe_rest(args, body, syn, rest),
2376 )))
2377 }
2378 Some(ExprKind::Atom(a)) => {
2379 let body_exprs: Vec<_> = value_iter.collect();
2380
2381 let body = if body_exprs.len() == 1 {
2382 body_exprs.into_iter().next().unwrap()
2383 } else {
2384 ExprKind::Begin(Box::new(Begin::new(
2385 body_exprs,
2386 SyntaxObject::default(TokenType::Begin),
2387 )))
2388 };
2389
2390 Ok(ExprKind::LambdaFunction(Box::new(
2392 LambdaFunction::new_with_rest_arg(vec![ExprKind::Atom(a)], body, syn),
2393 )))
2394 }
2395 _ => {
2396 Err(ParseError::SyntaxError(
2401 format!("lambda function expected a list of identifiers, found: {arguments:?}"),
2402 syn.span,
2403 None,
2404 ))
2405 }
2406 }
2407}
2408
2409pub(crate) fn parse_set(a: &Atom, value: Vec<ExprKind>) -> Result<ExprKind, ParseError> {
2410 let syn = a.syn.clone();
2411 if value.len() != 3 {
2412 return Err(ParseError::ArityMismatch(
2413 "set! expects an identifier and an expression".to_string(),
2414 syn.span,
2415 None,
2416 ));
2417 }
2418 let mut value_iter = value.into_iter();
2419 value_iter.next();
2420 let identifier = value_iter.next().unwrap();
2421 let expression = value_iter.next().unwrap();
2422 Ok(ExprKind::Set(Box::new(Set::new(
2423 identifier, expression, syn,
2424 ))))
2425}
2426
2427pub(crate) fn parse_require(a: &Atom, value: Vec<ExprKind>) -> Result<ExprKind, ParseError> {
2428 let syn = a.syn.clone();
2429 if value.len() < 2 {
2430 return Err(ParseError::ArityMismatch(
2431 "require expects at least one identifier or string".to_string(),
2432 syn.span,
2433 None,
2434 ));
2435 }
2436 let mut value_iter = value.into_iter();
2437 value_iter.next();
2438 let expressions = value_iter
2439 .map(|x| {
2440 match &x {
2441 ExprKind::Atom(_) | ExprKind::List(_) => Ok(x),
2442 _ => Err(ParseError::SyntaxError(
2443 "require expects atoms".to_string(),
2444 syn.span,
2445 None,
2446 )),
2447 }
2448
2449 })
2455 .collect::<Result<Vec<_>, ParseError>>()?;
2456 Ok(ExprKind::Require(Box::new(Require::new(expressions, syn))))
2457}
2458
2459pub(crate) fn parse_begin(a: Atom, value: Vec<ExprKind>) -> Result<ExprKind, ParseError> {
2460 let syn = a.syn;
2461 let mut value_iter = value.into_iter();
2462 value_iter.next();
2463 Ok(ExprKind::Begin(Box::new(Begin::new(
2464 value_iter.collect(),
2465 syn,
2466 ))))
2467}
2468
2469#[cfg(test)]
2470mod display_tests {
2471
2472 use super::*;
2473 use crate::parser::{Parser, Result, SourceId};
2474
2475 fn parse(expr: &str) -> ExprKind {
2476 let a: Result<Vec<ExprKind>> = Parser::new(expr, SourceId::none()).collect();
2477
2478 a.unwrap()[0].clone()
2479 }
2480
2481 #[test]
2482 fn display_lambda_quote() {
2483 let expression = "(lambda (x) (quote x))";
2484 let parsed_expr = parse(expression);
2485 let expected = "(lambda (x) (quote x))";
2486 assert_eq!(parsed_expr.to_string(), expected);
2487 }
2488
2489 #[test]
2490 fn display_list() {
2491 let expression = "(list 1 2 3 4)";
2492 let parsed_expr = parse(expression);
2493 let expected = "(list 1 2 3 4)";
2494 assert_eq!(parsed_expr.to_string(), expected);
2495 }
2496
2497 #[test]
2498 fn display_lambda() {
2499 let expression = "(lambda (x) (+ x 10))";
2500 let parsed_expr = parse(expression);
2501 let expected = "(lambda (x) (+ x 10))";
2502 assert_eq!(parsed_expr.to_string(), expected);
2503 }
2504
2505 #[test]
2506 fn display_set() {
2507 let expression = "(set! x 10)";
2508 let parsed_expr = parse(expression);
2509 let expected = "(set! x 10)";
2510 assert_eq!(parsed_expr.to_string(), expected);
2511 }
2512
2513 #[test]
2514 fn display_panic() {
2515 let expression = "(panic! 12345)";
2516 let parsed_expr = parse(expression);
2517 let expected = "(panic! 12345)";
2518 assert_eq!(parsed_expr.to_string(), expected);
2519 }
2520
2521 #[test]
2522 fn display_begin() {
2523 let expression = "(begin 1 2 3 4 5)";
2524 let parsed_expr = parse(expression);
2525 let expected = "(begin 1 2 3 4 5)";
2526 assert_eq!(parsed_expr.to_string(), expected);
2527 }
2528
2529 #[test]
2530 fn display_define_normal() {
2531 let expression = "(define a 10)";
2532 let parsed_expr = parse(expression);
2533 let expected = "(define a 10)";
2534 assert_eq!(parsed_expr.to_string(), expected);
2535 }
2536
2537 #[test]
2538 fn display_define_function() {
2539 let expression = "(define (applesauce x y z) (+ x y z))";
2540 let parsed_expr = parse(expression);
2541 let expected = "(define applesauce (lambda (x y z) (+ x y z)))";
2542 assert_eq!(parsed_expr.to_string(), expected);
2543 }
2544
2545 #[test]
2546 fn display_let() {
2547 let expression = "(let ((x 10)) (+ x 10))";
2548 let parsed_expr = parse(expression);
2549 let expected = "((lambda (x) (+ x 10)) 10)";
2550 assert_eq!(parsed_expr.to_string(), expected);
2551 }
2552
2553 #[test]
2554 fn display_apply() {
2555 let expression = "(apply + (list 1 2 3 4))";
2556 let parsed_expr = parse(expression);
2557 let expected = "(apply + (list 1 2 3 4))";
2558 assert_eq!(parsed_expr.to_string(), expected);
2559 }
2560
2561 #[test]
2562 fn display_transduce() {
2563 let expression = "(transduce 1 2 3 4)";
2564 let parsed_expr = parse(expression);
2565 let expected = "(transduce 1 2 3 4)";
2566 assert_eq!(parsed_expr.to_string(), expected);
2567 }
2568
2569 #[test]
2570 fn display_execute_two_args() {
2571 let expression = "(execute 1 2)";
2572 let parsed_expr = parse(expression);
2573 let expected = "(execute 1 2)";
2574 assert_eq!(parsed_expr.to_string(), expected);
2575 }
2576
2577 #[test]
2578 fn display_execute_three_args() {
2579 let expression = "(execute 1 2 3)";
2580 let parsed_expr = parse(expression);
2581 let expected = "(execute 1 2 3)";
2582 assert_eq!(parsed_expr.to_string(), expected);
2583 }
2584
2585 #[test]
2586 fn display_if() {
2587 let expression = "(if 1 2 3)";
2588 let parsed_expr = parse(expression);
2589 let expected = "(if 1 2 3)";
2590 assert_eq!(parsed_expr.to_string(), expected);
2591 }
2592
2593 #[test]
2594 fn display_quote() {
2595 let expression = "'(1 2 3 4)";
2596 let parsed_expr = parse(expression);
2597 let expected = "(quote (1 2 3 4))";
2598 assert_eq!(parsed_expr.to_string(), expected);
2599 }
2600
2601 #[test]
2602 fn display_read() {
2603 let expression = "(read '(1 2 3 4))";
2604 let parsed_expr = parse(expression);
2605 let expected = "(read (quote (1 2 3 4)))";
2606 assert_eq!(parsed_expr.to_string(), expected);
2607 }
2608
2609 #[test]
2610 fn display_return() {
2611 let expression = "(return! 10)";
2612 let parsed_expr = parse(expression);
2613 let expected = "(return! 10)";
2614 assert_eq!(parsed_expr.to_string(), expected);
2615 }
2616
2617 #[test]
2618 fn display_struct() {
2619 let expression = "(struct Apple (a b c))";
2620 let parsed_expr = parse(expression);
2621 let expected = "(struct Apple (a b c))";
2622 assert_eq!(parsed_expr.to_string(), expected);
2623 }
2624
2625 #[test]
2626 fn display_eval() {
2627 let expression = "(eval 'a)";
2628 let parsed_expr = parse(expression);
2629 let expected = "(eval (quote a))";
2630 assert_eq!(parsed_expr.to_string(), expected);
2631 }
2632}
2633
2634#[cfg(test)]
2635mod pretty_print_tests {
2636 use super::*;
2637 use crate::parser::{Parser, Result, SourceId};
2638
2639 fn parse(expr: &str) -> ExprKind {
2640 let a: Result<Vec<ExprKind>> = Parser::new(expr, SourceId::none()).collect();
2641
2642 a.unwrap()[0].clone()
2643 }
2644
2645 #[test]
2646 fn pretty_set() {
2647 let expression = r#"
2648 (define test-function
2649 (lambda (a b c)
2650 (begin
2651 (set! bananas 10)
2652 (if applesauce 100 #f)
2653 (if applesauce 100 (if applesauce 100 #f)))))"#;
2654 let parsed_expr = parse(expression);
2655 let _output = parsed_expr.to_pretty(45);
2656
2657 assert!(true)
2658 }
2659}