1mod clause;
55mod common;
56mod modal;
57mod noun;
58mod pragmatics;
59mod quantifier;
60mod question;
61mod verb;
62
63#[cfg(test)]
64mod tests;
65
66pub use clause::ClauseParsing;
67pub use modal::ModalParsing;
68pub use noun::NounParsing;
69pub use pragmatics::PragmaticsParsing;
70pub use quantifier::QuantifierParsing;
71pub use question::QuestionParsing;
72pub use verb::{LogicVerbParsing, ImperativeVerbParsing};
73
74use crate::analysis::TypeRegistry;
75use crate::arena_ctx::AstContext;
76use crate::ast::{AspectOperator, LogicExpr, NeoEventData, NumberKind, QuantifierKind, TemporalOperator, Term, ThematicRole, Stmt, Expr, Literal, TypeExpr, BinaryOpKind, MatchArm};
77use crate::ast::stmt::{ReadSource, Pattern};
78use crate::drs::{Case, Gender, Number, ReferentSource};
79use crate::drs::{Drs, BoxType, WorldState};
80use crate::error::{ParseError, ParseErrorKind};
81use logicaffeine_base::{Interner, Symbol, SymbolEq};
82use crate::lexer::Lexer;
83use crate::lexicon::{self, Aspect, Definiteness, Time, VerbClass};
84use crate::token::{BlockType, FocusKind, Token, TokenType};
85
86pub(super) type ParseResult<T> = Result<T, ParseError>;
87
88use std::ops::{Deref, DerefMut};
89
90#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
92pub enum ParserMode {
93 #[default]
95 Declarative,
96 Imperative,
98}
99
100#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
105pub enum NegativeScopeMode {
106 #[default]
109 Narrow,
110 Wide,
113}
114
115#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
123pub enum ModalPreference {
124 #[default]
126 Default,
127 Epistemic,
129 Deontic,
131}
132
133#[derive(Debug, Clone, Copy)]
138pub enum ResolvedPronoun {
139 Variable(Symbol),
141 Constant(Symbol),
143}
144
145#[derive(Clone)]
146struct ParserCheckpoint {
147 pos: usize,
148 var_counter: usize,
149 bindings_len: usize,
150 island: u32,
151 time: Option<Time>,
152 negative_depth: u32,
153}
154
155pub struct ParserGuard<'p, 'a, 'ctx, 'int> {
188 parser: &'p mut Parser<'a, 'ctx, 'int>,
189 checkpoint: ParserCheckpoint,
190 committed: bool,
191}
192
193impl<'p, 'a, 'ctx, 'int> ParserGuard<'p, 'a, 'ctx, 'int> {
194 pub fn commit(mut self) {
196 self.committed = true;
197 }
198}
199
200impl<'p, 'a, 'ctx, 'int> Drop for ParserGuard<'p, 'a, 'ctx, 'int> {
201 fn drop(&mut self) {
202 if !self.committed {
203 self.parser.restore(self.checkpoint.clone());
204 }
205 }
206}
207
208impl<'p, 'a, 'ctx, 'int> Deref for ParserGuard<'p, 'a, 'ctx, 'int> {
209 type Target = Parser<'a, 'ctx, 'int>;
210 fn deref(&self) -> &Self::Target {
211 self.parser
212 }
213}
214
215impl<'p, 'a, 'ctx, 'int> DerefMut for ParserGuard<'p, 'a, 'ctx, 'int> {
216 fn deref_mut(&mut self) -> &mut Self::Target {
217 self.parser
218 }
219}
220
221#[derive(Clone, Debug)]
226pub struct EventTemplate<'a> {
227 pub verb: Symbol,
229 pub non_agent_roles: Vec<(ThematicRole, Term<'a>)>,
231 pub modifiers: Vec<Symbol>,
233}
234
235pub struct Parser<'a, 'ctx, 'int> {
252 pub(super) tokens: Vec<Token>,
254 pub(super) current: usize,
256 pub(super) var_counter: usize,
258 pub(super) pending_time: Option<Time>,
260 pub(super) donkey_bindings: Vec<(Symbol, Symbol, bool, bool)>,
262 pub(super) interner: &'int mut Interner,
264 pub(super) ctx: AstContext<'a>,
266 pub(super) current_island: u32,
268 pub(super) pp_attach_to_noun: bool,
270 pub(super) filler_gap: Option<Symbol>,
272 pub(super) negative_depth: u32,
274 pub(super) discourse_event_var: Option<Symbol>,
276 pub(super) last_event_template: Option<EventTemplate<'a>>,
278 pub(super) noun_priority_mode: bool,
280 pub(super) collective_mode: bool,
282 pub(super) pending_cardinal: Option<u32>,
284 pub(super) mode: ParserMode,
286 pub(super) type_registry: Option<TypeRegistry>,
288 pub(super) event_reading_mode: bool,
290 pub(super) drs: Drs,
292 pub(super) negative_scope_mode: NegativeScopeMode,
294 pub(super) modal_preference: ModalPreference,
296 pub(super) world_state: &'ctx mut WorldState,
298 pub(super) in_negative_quantifier: bool,
300}
301
302impl<'a, 'ctx, 'int> Parser<'a, 'ctx, 'int> {
303 pub fn new(
307 tokens: Vec<Token>,
308 world_state: &'ctx mut WorldState,
309 interner: &'int mut Interner,
310 ctx: AstContext<'a>,
311 types: TypeRegistry,
312 ) -> Self {
313 Parser {
314 tokens,
315 current: 0,
316 var_counter: 0,
317 pending_time: None,
318 donkey_bindings: Vec::new(),
319 interner,
320 ctx,
321 current_island: 0,
322 pp_attach_to_noun: false,
323 filler_gap: None,
324 negative_depth: 0,
325 discourse_event_var: None,
326 last_event_template: None,
327 noun_priority_mode: false,
328 collective_mode: false,
329 pending_cardinal: None,
330 mode: ParserMode::Declarative,
331 type_registry: Some(types),
332 event_reading_mode: false,
333 drs: Drs::new(), negative_scope_mode: NegativeScopeMode::default(),
335 modal_preference: ModalPreference::default(),
336 world_state,
337 in_negative_quantifier: false,
338 }
339 }
340
341 pub fn set_discourse_event_var(&mut self, var: Symbol) {
342 self.discourse_event_var = Some(var);
343 }
344
345 pub fn drs_mut(&mut self) -> &mut Drs {
347 &mut self.world_state.drs
348 }
349
350 pub fn drs_ref(&self) -> &Drs {
352 &self.world_state.drs
353 }
354
355 pub fn swap_drs_with_world_state(&mut self) {
359 std::mem::swap(&mut self.drs, &mut self.world_state.drs);
360 }
361
362 pub fn has_world_state(&self) -> bool {
364 true
365 }
366
367 pub fn mode(&self) -> ParserMode {
368 self.mode
369 }
370
371 pub fn is_known_type(&self, sym: Symbol) -> bool {
374 self.type_registry
375 .as_ref()
376 .map(|r| r.is_type(sym))
377 .unwrap_or(false)
378 }
379
380 pub fn is_generic_type(&self, sym: Symbol) -> bool {
383 self.type_registry
384 .as_ref()
385 .map(|r| r.is_generic(sym))
386 .unwrap_or(false)
387 }
388
389 fn get_generic_param_count(&self, sym: Symbol) -> Option<usize> {
391 use crate::analysis::TypeDef;
392 self.type_registry.as_ref().and_then(|r| {
393 match r.get(sym) {
394 Some(TypeDef::Generic { param_count }) => Some(*param_count),
395 _ => None,
396 }
397 })
398 }
399
400 fn find_variant(&self, sym: Symbol) -> Option<Symbol> {
402 self.type_registry
403 .as_ref()
404 .and_then(|r| r.find_variant(sym).map(|(enum_name, _)| enum_name))
405 }
406
407 fn consume_type_name(&mut self) -> ParseResult<Symbol> {
409 let t = self.advance().clone();
410 match t.kind {
411 TokenType::Noun(s) | TokenType::Adjective(s) => Ok(s),
412 TokenType::ProperName(s) => Ok(s),
413 TokenType::Verb { .. } => Ok(t.lexeme),
415 TokenType::Tally => Ok(self.interner.intern("Tally")),
417 TokenType::SharedSet => Ok(self.interner.intern("SharedSet")),
418 TokenType::SharedSequence => Ok(self.interner.intern("SharedSequence")),
419 TokenType::CollaborativeSequence => Ok(self.interner.intern("CollaborativeSequence")),
420 TokenType::SharedMap => Ok(self.interner.intern("SharedMap")),
421 TokenType::Divergent => Ok(self.interner.intern("Divergent")),
422 other => Err(ParseError {
423 kind: ParseErrorKind::ExpectedContentWord { found: other },
424 span: self.current_span(),
425 }),
426 }
427 }
428
429 fn parse_type_expression(&mut self) -> ParseResult<TypeExpr<'a>> {
434 use noun::NounParsing;
435
436 if self.check_word("fn") {
438 if let Some(next) = self.tokens.get(self.current + 1) {
439 if matches!(next.kind, TokenType::LParen) {
440 self.advance(); self.advance(); let mut inputs = Vec::new();
445 if !self.check(&TokenType::RParen) {
446 inputs.push(self.parse_type_expression()?);
447 while self.check(&TokenType::Comma) {
448 self.advance(); inputs.push(self.parse_type_expression()?);
450 }
451 }
452
453 if !self.check(&TokenType::RParen) {
454 return Err(ParseError {
455 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
456 span: self.current_span(),
457 });
458 }
459 self.advance(); if !self.check(&TokenType::Arrow) {
463 return Err(ParseError {
464 kind: ParseErrorKind::ExpectedKeyword { keyword: "->".to_string() },
465 span: self.current_span(),
466 });
467 }
468 self.advance(); let output = self.parse_type_expression()?;
471 let output_ref = self.ctx.alloc_type_expr(output);
472 let inputs_ref = self.ctx.alloc_type_exprs(inputs);
473 return Ok(TypeExpr::Function { inputs: inputs_ref, output: output_ref });
474 }
475 }
476 }
477
478 if self.check(&TokenType::LParen) {
480 self.advance(); let inner = self.parse_type_expression()?;
482 if !self.check(&TokenType::RParen) {
483 return Err(ParseError {
484 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
485 span: self.current_span(),
486 });
487 }
488 self.advance(); return Ok(inner);
490 }
491
492 if self.check(&TokenType::Persistent) {
494 self.advance(); let inner = self.parse_type_expression()?;
496 let inner_ref = self.ctx.alloc_type_expr(inner);
497 return Ok(TypeExpr::Persistent { inner: inner_ref });
498 }
499
500 let mut base = self.consume_type_name()?;
502
503 let base_name = self.interner.resolve(base);
505 if base_name == "SharedSet" || base_name == "ORSet" {
506 if self.check(&TokenType::LParen) {
507 self.advance(); if self.check(&TokenType::RemoveWins) {
509 self.advance(); base = self.interner.intern("SharedSet_RemoveWins");
511 } else if self.check(&TokenType::AddWins) {
512 self.advance(); base = self.interner.intern("SharedSet_AddWins");
515 }
516 if !self.check(&TokenType::RParen) {
517 return Err(ParseError {
518 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
519 span: self.current_span(),
520 });
521 }
522 self.advance(); }
524 }
525
526 let base_name = self.interner.resolve(base);
528 if base_name == "SharedSequence" || base_name == "RGA" {
529 if self.check(&TokenType::LParen) {
530 self.advance(); if self.check(&TokenType::YATA) {
532 self.advance(); base = self.interner.intern("SharedSequence_YATA");
534 }
535 if !self.check(&TokenType::RParen) {
536 return Err(ParseError {
537 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
538 span: self.current_span(),
539 });
540 }
541 self.advance(); }
543 }
544
545 let base_type = if self.check(&TokenType::From) {
547 self.advance(); let module_name = self.consume_type_name()?;
549 let module_str = self.interner.resolve(module_name);
550 let base_str = self.interner.resolve(base);
551 let qualified = format!("{}::{}", module_str, base_str);
552 let qualified_sym = self.interner.intern(&qualified);
553 TypeExpr::Named(qualified_sym)
554 } else {
555 let base_name = self.interner.resolve(base);
557 let param_count = self.get_generic_param_count(base)
558 .or_else(|| match base_name {
559 "Result" => Some(2), "Option" | "Maybe" => Some(1), "Seq" | "List" | "Vec" => Some(1), "Set" | "HashSet" => Some(1), "Map" | "HashMap" => Some(2), "Pair" => Some(2), "Triple" => Some(3), "SharedSet" | "ORSet" | "SharedSet_AddWins" | "SharedSet_RemoveWins" => Some(1),
569 "SharedSequence" | "RGA" | "SharedSequence_YATA" | "CollaborativeSequence" => Some(1),
570 "SharedMap" | "ORMap" => Some(2), "Divergent" | "MVRegister" => Some(1), _ => None,
573 });
574
575 if let Some(count) = param_count {
577 let has_preposition = self.check_of_preposition() || self.check_preposition_is("from");
578 let maybe_direct = !has_preposition && base_name == "Maybe" && matches!(
580 self.peek().kind,
581 TokenType::Noun(_) | TokenType::Adjective(_) | TokenType::ProperName(_) | TokenType::Verb { .. }
582 );
583 if has_preposition || maybe_direct {
584 if has_preposition {
585 self.advance(); }
587
588 let mut params = Vec::new();
589 for i in 0..count {
590 if i > 0 {
591 if self.check(&TokenType::And) || self.check_to_preposition() || self.check(&TokenType::Comma) {
593 self.advance();
594 }
595 }
596 let param = self.parse_type_expression()?;
597 params.push(param);
598 }
599
600 let params_slice = self.ctx.alloc_type_exprs(params);
601 TypeExpr::Generic { base, params: params_slice }
602 } else {
603 let is_primitive = self.type_registry.as_ref().map(|r| r.is_type(base)).unwrap_or(false)
605 || matches!(base_name, "Int" | "Nat" | "Text" | "Bool" | "Boolean" | "Real" | "Unit");
606 if is_primitive {
607 TypeExpr::Primitive(base)
608 } else {
609 TypeExpr::Named(base)
610 }
611 }
612 } else {
613 let is_primitive = self.type_registry.as_ref().map(|r| r.is_type(base)).unwrap_or(false)
615 || matches!(base_name, "Int" | "Nat" | "Text" | "Bool" | "Boolean" | "Real" | "Unit");
616 if is_primitive {
617 TypeExpr::Primitive(base)
618 } else {
619 TypeExpr::Named(base)
621 }
622 }
623 };
624
625 if self.check(&TokenType::Where) {
627 self.advance(); let predicate_expr = self.parse_condition()?;
631
632 let bound_var = self.extract_bound_var(&predicate_expr)
634 .unwrap_or_else(|| self.interner.intern("it"));
635
636 let predicate = self.expr_to_logic_predicate(&predicate_expr, bound_var)
638 .ok_or_else(|| ParseError {
639 kind: ParseErrorKind::InvalidRefinementPredicate,
640 span: self.peek().span,
641 })?;
642
643 let base_alloc = self.ctx.alloc_type_expr(base_type);
645
646 return Ok(TypeExpr::Refinement { base: base_alloc, var: bound_var, predicate });
647 }
648
649 Ok(base_type)
650 }
651
652 fn extract_bound_var(&self, expr: &Expr<'a>) -> Option<Symbol> {
654 match expr {
655 Expr::Identifier(sym) => Some(*sym),
656 Expr::BinaryOp { left, .. } => self.extract_bound_var(left),
657 _ => None,
658 }
659 }
660
661 fn expr_to_logic_predicate(&mut self, expr: &Expr<'a>, bound_var: Symbol) -> Option<&'a LogicExpr<'a>> {
664 match expr {
665 Expr::BinaryOp { op, left, right } => {
666 let pred_name = match op {
668 BinaryOpKind::Gt => "Greater",
669 BinaryOpKind::Lt => "Less",
670 BinaryOpKind::GtEq => "GreaterEqual",
671 BinaryOpKind::LtEq => "LessEqual",
672 BinaryOpKind::Eq => "Equal",
673 BinaryOpKind::NotEq => "NotEqual",
674 BinaryOpKind::And => {
675 let left_logic = self.expr_to_logic_predicate(left, bound_var)?;
677 let right_logic = self.expr_to_logic_predicate(right, bound_var)?;
678 return Some(self.ctx.exprs.alloc(LogicExpr::BinaryOp {
679 left: left_logic,
680 op: TokenType::And,
681 right: right_logic,
682 }));
683 }
684 BinaryOpKind::Or => {
685 let left_logic = self.expr_to_logic_predicate(left, bound_var)?;
686 let right_logic = self.expr_to_logic_predicate(right, bound_var)?;
687 return Some(self.ctx.exprs.alloc(LogicExpr::BinaryOp {
688 left: left_logic,
689 op: TokenType::Or,
690 right: right_logic,
691 }));
692 }
693 _ => return None, };
695 let pred_sym = self.interner.intern(pred_name);
696
697 let left_term = self.expr_to_term(left)?;
699 let right_term = self.expr_to_term(right)?;
700
701 let args = self.ctx.terms.alloc_slice([left_term, right_term]);
702 Some(self.ctx.exprs.alloc(LogicExpr::Predicate { name: pred_sym, args, world: None }))
703 }
704 _ => None,
705 }
706 }
707
708 fn expr_to_term(&mut self, expr: &Expr<'a>) -> Option<Term<'a>> {
710 match expr {
711 Expr::Identifier(sym) => Some(Term::Variable(*sym)),
712 Expr::Literal(lit) => {
713 match lit {
714 Literal::Number(n) => Some(Term::Value {
715 kind: NumberKind::Integer(*n),
716 unit: None,
717 dimension: None,
718 }),
719 Literal::Boolean(b) => {
720 let sym = self.interner.intern(if *b { "true" } else { "false" });
721 Some(Term::Constant(sym))
722 }
723 _ => None, }
725 }
726 _ => None,
727 }
728 }
729
730 pub fn process_block_headers(&mut self) {
731 use crate::token::BlockType;
732
733 while self.current < self.tokens.len() {
734 if let TokenType::BlockHeader { block_type } = &self.tokens[self.current].kind {
735 self.mode = match block_type {
736 BlockType::Main | BlockType::Function => ParserMode::Imperative,
737 BlockType::Theorem | BlockType::Definition | BlockType::Proof |
738 BlockType::Example | BlockType::Logic | BlockType::Note | BlockType::TypeDef |
739 BlockType::Policy | BlockType::Requires => ParserMode::Declarative,
740 };
741 self.current += 1;
742 } else {
743 break;
744 }
745 }
746 }
747
748 pub fn get_event_var(&mut self) -> Symbol {
749 self.discourse_event_var.unwrap_or_else(|| self.interner.intern("e"))
750 }
751
752 pub fn capture_event_template(&mut self, verb: Symbol, roles: &[(ThematicRole, Term<'a>)], modifiers: &[Symbol]) {
753 let non_agent_roles: Vec<_> = roles.iter()
754 .filter(|(role, _)| *role != ThematicRole::Agent)
755 .cloned()
756 .collect();
757 self.last_event_template = Some(EventTemplate {
758 verb,
759 non_agent_roles,
760 modifiers: modifiers.to_vec(),
761 });
762 }
763
764 fn parse_embedded_wh_clause(&mut self) -> ParseResult<&'a LogicExpr<'a>> {
765 let var_name = self.interner.intern("x");
767 let var_term = Term::Variable(var_name);
768
769 if self.check_verb() {
770 let verb = self.consume_verb();
772 let body = self.ctx.exprs.alloc(LogicExpr::Predicate {
773 name: verb,
774 args: self.ctx.terms.alloc_slice([var_term]),
775 world: None,
776 });
777 return Ok(body);
778 }
779
780 if self.check_content_word() || self.check_article() {
781 let subject = self.parse_noun_phrase(true)?;
783 if self.check_verb() {
784 let verb = self.consume_verb();
785 let body = self.ctx.exprs.alloc(LogicExpr::Predicate {
786 name: verb,
787 args: self.ctx.terms.alloc_slice([
788 Term::Constant(subject.noun),
789 var_term,
790 ]),
791 world: None,
792 });
793 return Ok(body);
794 }
795 }
796
797 Ok(self.ctx.exprs.alloc(LogicExpr::Atom(var_name)))
799 }
800
801 pub fn set_pp_attachment_mode(&mut self, attach_to_noun: bool) {
802 self.pp_attach_to_noun = attach_to_noun;
803 }
804
805 pub fn set_noun_priority_mode(&mut self, mode: bool) {
806 self.noun_priority_mode = mode;
807 }
808
809 pub fn set_collective_mode(&mut self, mode: bool) {
810 self.collective_mode = mode;
811 }
812
813 pub fn set_event_reading_mode(&mut self, mode: bool) {
814 self.event_reading_mode = mode;
815 }
816
817 pub fn set_negative_scope_mode(&mut self, mode: NegativeScopeMode) {
818 self.negative_scope_mode = mode;
819 }
820
821 pub fn set_modal_preference(&mut self, pref: ModalPreference) {
822 self.modal_preference = pref;
823 }
824
825 fn checkpoint(&self) -> ParserCheckpoint {
826 ParserCheckpoint {
827 pos: self.current,
828 var_counter: self.var_counter,
829 bindings_len: self.donkey_bindings.len(),
830 island: self.current_island,
831 time: self.pending_time,
832 negative_depth: self.negative_depth,
833 }
834 }
835
836 fn restore(&mut self, cp: ParserCheckpoint) {
837 self.current = cp.pos;
838 self.var_counter = cp.var_counter;
839 self.donkey_bindings.truncate(cp.bindings_len);
840 self.current_island = cp.island;
841 self.pending_time = cp.time;
842 self.negative_depth = cp.negative_depth;
843 }
844
845 fn is_negative_context(&self) -> bool {
846 self.negative_depth % 2 == 1
847 }
848
849 pub fn guard(&mut self) -> ParserGuard<'_, 'a, 'ctx, 'int> {
850 ParserGuard {
851 checkpoint: self.checkpoint(),
852 parser: self,
853 committed: false,
854 }
855 }
856
857 pub(super) fn try_parse<F, T>(&mut self, op: F) -> Option<T>
858 where
859 F: FnOnce(&mut Self) -> ParseResult<T>,
860 {
861 let cp = self.checkpoint();
862 match op(self) {
863 Ok(res) => Some(res),
864 Err(_) => {
865 self.restore(cp);
866 None
867 }
868 }
869 }
870
871 fn resolve_pronoun(&mut self, gender: Gender, number: Number) -> ParseResult<ResolvedPronoun> {
872 if self.world_state.in_discourse_mode() && self.world_state.has_prior_modal_context() {
877 if let Some(candidate) = self.world_state.resolve_via_telescope(gender) {
880 return Ok(ResolvedPronoun::Variable(candidate.variable));
881 }
882 let blocked_candidates: Vec<_> = self.world_state.telescope_candidates()
886 .iter()
887 .filter(|c| c.in_modal_scope)
888 .collect();
889 if !blocked_candidates.is_empty() {
890 let has_upcoming_modal = self.has_modal_subordination_ahead();
893 if has_upcoming_modal {
894 if let Some(candidate) = blocked_candidates.into_iter().find(|c| {
896 c.gender == gender || gender == Gender::Unknown || c.gender == Gender::Unknown
897 }) {
898 return Ok(ResolvedPronoun::Variable(candidate.variable));
899 }
900 }
901 return Err(ParseError {
903 kind: ParseErrorKind::ScopeViolation(
904 "Cannot access hypothetical entity from reality. Use modal subordination (e.g., 'would') to continue a hypothetical context.".to_string()
905 ),
906 span: self.current_span(),
907 });
908 }
909 }
911
912 let current_box = self.drs.current_box_index();
914 match self.drs.resolve_pronoun(current_box, gender, number) {
915 Ok(sym) => return Ok(ResolvedPronoun::Variable(sym)),
916 Err(crate::drs::ScopeError::InaccessibleReferent { gender: g, reason, .. }) => {
917 if self.world_state.in_discourse_mode() {
921 if let Some(candidate) = self.world_state.resolve_via_telescope(g) {
922 return Ok(ResolvedPronoun::Variable(candidate.variable));
923 }
924 }
925 return Err(ParseError {
927 kind: ParseErrorKind::ScopeViolation(reason),
928 span: self.current_span(),
929 });
930 }
931 Err(crate::drs::ScopeError::NoMatchingReferent { gender: g, number: n }) => {
932 if !self.world_state.has_prior_modal_context() {
934 if let Some(candidate) = self.world_state.resolve_via_telescope(g) {
935 return Ok(ResolvedPronoun::Variable(candidate.variable));
936 }
937 }
938
939 if self.world_state.in_discourse_mode() {
941 return Err(ParseError {
942 kind: ParseErrorKind::UnresolvedPronoun {
943 gender: g,
944 number: n,
945 },
946 span: self.current_span(),
947 });
948 }
949
950 let deictic_name = match (g, n) {
953 (Gender::Male, Number::Singular) => "Him",
954 (Gender::Female, Number::Singular) => "Her",
955 (Gender::Neuter, Number::Singular) => "It",
956 (Gender::Male, Number::Plural) | (Gender::Female, Number::Plural) => "Them",
957 (Gender::Neuter, Number::Plural) => "Them",
958 (Gender::Unknown, _) => "Someone",
959 };
960 let sym = self.interner.intern(deictic_name);
961 self.drs.introduce_referent(sym, sym, g, n);
963 return Ok(ResolvedPronoun::Constant(sym));
964 }
965 }
966 }
967
968 fn resolve_donkey_pronoun(&mut self, gender: Gender) -> Option<Symbol> {
969 for (noun_class, var_name, used, _wide_neg) in self.donkey_bindings.iter_mut().rev() {
970 let noun_str = self.interner.resolve(*noun_class);
971 let noun_gender = Self::infer_noun_gender(noun_str);
972 if noun_gender == gender || gender == Gender::Neuter || noun_gender == Gender::Unknown {
973 *used = true; return Some(*var_name);
975 }
976 }
977 None
978 }
979
980 fn infer_noun_gender(noun: &str) -> Gender {
981 let lower = noun.to_lowercase();
982 if lexicon::is_female_noun(&lower) {
983 Gender::Female
984 } else if lexicon::is_male_noun(&lower) {
985 Gender::Male
986 } else if lexicon::is_neuter_noun(&lower) {
987 Gender::Neuter
988 } else {
989 Gender::Unknown
990 }
991 }
992
993 fn is_plural_noun(noun: &str) -> bool {
994 let lower = noun.to_lowercase();
995 if lexicon::is_proper_name(&lower) {
997 return false;
998 }
999 if lexicon::is_irregular_plural(&lower) {
1000 return true;
1001 }
1002 lower.ends_with('s') && !lower.ends_with("ss") && lower.len() > 2
1003 }
1004
1005 fn singularize_noun(noun: &str) -> String {
1006 let lower = noun.to_lowercase();
1007 if let Some(singular) = lexicon::singularize(&lower) {
1008 return singular.to_string();
1009 }
1010 if lower.ends_with('s') && !lower.ends_with("ss") && lower.len() > 2 {
1011 let base = &lower[..lower.len() - 1];
1012 let mut chars: Vec<char> = base.chars().collect();
1013 if !chars.is_empty() {
1014 chars[0] = chars[0].to_uppercase().next().unwrap();
1015 }
1016 return chars.into_iter().collect();
1017 }
1018 let mut chars: Vec<char> = lower.chars().collect();
1019 if !chars.is_empty() {
1020 chars[0] = chars[0].to_uppercase().next().unwrap();
1021 }
1022 chars.into_iter().collect()
1023 }
1024
1025 fn infer_gender(name: &str) -> Gender {
1026 let lower = name.to_lowercase();
1027 if lexicon::is_male_name(&lower) {
1028 Gender::Male
1029 } else if lexicon::is_female_name(&lower) {
1030 Gender::Female
1031 } else {
1032 Gender::Unknown
1033 }
1034 }
1035
1036
1037 fn next_var_name(&mut self) -> Symbol {
1038 const VARS: &[&str] = &["x", "y", "z", "w", "v", "u"];
1039 let idx = self.var_counter;
1040 self.var_counter += 1;
1041 if idx < VARS.len() {
1042 self.interner.intern(VARS[idx])
1043 } else {
1044 let name = format!("x{}", idx - VARS.len() + 1);
1045 self.interner.intern(&name)
1046 }
1047 }
1048
1049 pub fn parse(&mut self) -> ParseResult<&'a LogicExpr<'a>> {
1066 let mut result = self.parse_sentence()?;
1067
1068 while self.check(&TokenType::Period) || self.check(&TokenType::Exclamation) {
1071 self.advance(); if !self.is_at_end() {
1073 let next = self.parse_sentence()?;
1074 result = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
1075 left: result,
1076 op: TokenType::And,
1077 right: next,
1078 });
1079 }
1080 }
1081
1082 Ok(result)
1083 }
1084
1085 pub fn parse_program(&mut self) -> ParseResult<Vec<Stmt<'a>>> {
1103 let mut statements = Vec::new();
1104 let mut in_definition_block = false;
1105
1106 if self.mode == ParserMode::Declarative {
1108 }
1112
1113 while !self.is_at_end() {
1114 if let Some(Token { kind: TokenType::BlockHeader { block_type }, .. }) = self.tokens.get(self.current) {
1116 match block_type {
1117 BlockType::Definition => {
1118 in_definition_block = true;
1119 self.mode = ParserMode::Declarative;
1120 self.advance();
1121 continue;
1122 }
1123 BlockType::Main => {
1124 in_definition_block = false;
1125 self.mode = ParserMode::Imperative;
1126 self.advance();
1127 continue;
1128 }
1129 BlockType::Function => {
1130 in_definition_block = false;
1131 self.mode = ParserMode::Imperative;
1132 self.advance();
1133 let func_def = self.parse_function_def()?;
1135 statements.push(func_def);
1136 continue;
1137 }
1138 BlockType::TypeDef => {
1139 self.advance();
1142 self.skip_type_def_content();
1143 continue;
1144 }
1145 BlockType::Policy => {
1146 in_definition_block = true; self.mode = ParserMode::Declarative;
1150 self.advance();
1151 continue;
1152 }
1153 BlockType::Theorem => {
1154 in_definition_block = false;
1156 self.mode = ParserMode::Declarative;
1157 self.advance();
1158 let theorem = self.parse_theorem_block()?;
1159 statements.push(theorem);
1160 continue;
1161 }
1162 BlockType::Requires => {
1163 in_definition_block = false;
1164 self.mode = ParserMode::Declarative;
1165 self.advance();
1166 let deps = self.parse_requires_block()?;
1167 statements.extend(deps);
1168 continue;
1169 }
1170 _ => {
1171 in_definition_block = false;
1173 self.mode = ParserMode::Declarative;
1174 self.advance();
1175 continue;
1176 }
1177 }
1178 }
1179
1180 if in_definition_block {
1182 self.advance();
1183 continue;
1184 }
1185
1186 if self.check(&TokenType::Indent) || self.check(&TokenType::Dedent) || self.check(&TokenType::Newline) {
1188 self.advance();
1189 continue;
1190 }
1191
1192 if self.mode == ParserMode::Imperative {
1194 let stmt = self.parse_statement()?;
1195 statements.push(stmt);
1196
1197 if self.check(&TokenType::Period) {
1198 self.advance();
1199 }
1200 } else {
1201 self.advance();
1203 }
1204 }
1205
1206 Ok(statements)
1207 }
1208
1209 fn parse_statement(&mut self) -> ParseResult<Stmt<'a>> {
1210 if self.check(&TokenType::To) || self.check_preposition_is("to") {
1213 return self.parse_function_def();
1214 }
1215 if self.check(&TokenType::Let) {
1216 return self.parse_let_statement();
1217 }
1218 if self.check(&TokenType::Mut) {
1221 return self.parse_equals_assignment(true);
1222 }
1223 if self.peek_equals_assignment() {
1226 return self.parse_equals_assignment(false);
1227 }
1228 if self.check(&TokenType::Set) {
1229 return self.parse_set_statement();
1230 }
1231 if self.check(&TokenType::Return) {
1232 return self.parse_return_statement();
1233 }
1234 if self.check(&TokenType::If) {
1235 return self.parse_if_statement();
1236 }
1237 if self.check(&TokenType::Assert) {
1238 return self.parse_assert_statement();
1239 }
1240 if self.check(&TokenType::Trust) {
1242 return self.parse_trust_statement();
1243 }
1244 if self.check(&TokenType::Check) {
1246 return self.parse_check_statement();
1247 }
1248 if self.check(&TokenType::Listen) {
1250 return self.parse_listen_statement();
1251 }
1252 if self.check(&TokenType::NetConnect) {
1253 return self.parse_connect_statement();
1254 }
1255 if self.check(&TokenType::Sleep) {
1256 return self.parse_sleep_statement();
1257 }
1258 if self.check(&TokenType::Sync) {
1260 return self.parse_sync_statement();
1261 }
1262 if self.check(&TokenType::Mount) {
1264 return self.parse_mount_statement();
1265 }
1266 if self.check(&TokenType::While) {
1267 return self.parse_while_statement();
1268 }
1269 if self.check(&TokenType::Repeat) {
1270 return self.parse_repeat_statement();
1271 }
1272 if self.check(&TokenType::For) {
1274 return self.parse_for_statement();
1275 }
1276 if self.check(&TokenType::Call) {
1277 return self.parse_call_statement();
1278 }
1279 if self.check(&TokenType::Give) {
1280 return self.parse_give_statement();
1281 }
1282 if self.check(&TokenType::Show) {
1283 return self.parse_show_statement();
1284 }
1285 if self.check(&TokenType::Inspect) {
1287 return self.parse_inspect_statement();
1288 }
1289
1290 if self.check(&TokenType::Push) {
1292 return self.parse_push_statement();
1293 }
1294 if self.check(&TokenType::Pop) {
1295 return self.parse_pop_statement();
1296 }
1297 if self.check(&TokenType::Add) {
1299 return self.parse_add_statement();
1300 }
1301 if self.check(&TokenType::Remove) {
1302 return self.parse_remove_statement();
1303 }
1304
1305 if self.check(&TokenType::Inside) {
1307 return self.parse_zone_statement();
1308 }
1309
1310 if self.check(&TokenType::Attempt) {
1312 return self.parse_concurrent_block();
1313 }
1314 if self.check(&TokenType::Simultaneously) {
1315 return self.parse_parallel_block();
1316 }
1317
1318 if self.check(&TokenType::Read) {
1320 return self.parse_read_statement();
1321 }
1322 if self.check(&TokenType::Write) {
1323 return self.parse_write_statement();
1324 }
1325
1326 if self.check(&TokenType::Spawn) {
1328 return self.parse_spawn_statement();
1329 }
1330 if self.check(&TokenType::Send) {
1331 if self.lookahead_contains_into() {
1333 return self.parse_send_pipe_statement();
1334 }
1335 return self.parse_send_statement();
1336 }
1337 if self.check(&TokenType::Await) {
1338 if self.lookahead_is_first_of() {
1340 return self.parse_select_statement();
1341 }
1342 return self.parse_await_statement();
1343 }
1344
1345 if self.check(&TokenType::Merge) {
1347 return self.parse_merge_statement();
1348 }
1349 if self.check(&TokenType::Increase) {
1350 return self.parse_increase_statement();
1351 }
1352 if self.check(&TokenType::Decrease) {
1354 return self.parse_decrease_statement();
1355 }
1356 if self.check(&TokenType::Append) {
1357 return self.parse_append_statement();
1358 }
1359 if self.check(&TokenType::Resolve) {
1360 return self.parse_resolve_statement();
1361 }
1362
1363 if self.check(&TokenType::Launch) {
1365 return self.parse_launch_statement();
1366 }
1367 if self.check(&TokenType::Stop) {
1368 return self.parse_stop_statement();
1369 }
1370 if self.check(&TokenType::Try) {
1371 return self.parse_try_statement();
1372 }
1373 if self.check(&TokenType::Receive) {
1374 return self.parse_receive_pipe_statement();
1375 }
1376
1377 if self.check(&TokenType::Escape) {
1379 return self.parse_escape_statement();
1380 }
1381
1382 if self.tokens.get(self.current + 1)
1386 .map(|t| matches!(t.kind, TokenType::LParen))
1387 .unwrap_or(false)
1388 {
1389 let function = self.peek().lexeme;
1391 self.advance(); let expr = self.parse_call_expr(function)?;
1395 if let Expr::Call { function, args } = expr {
1396 return Ok(Stmt::Call { function: *function, args: args.clone() });
1397 }
1398 }
1399
1400 Err(ParseError {
1401 kind: ParseErrorKind::ExpectedStatement,
1402 span: self.current_span(),
1403 })
1404 }
1405
1406 fn parse_if_statement(&mut self) -> ParseResult<Stmt<'a>> {
1407 self.advance(); let cond = self.parse_condition()?;
1411
1412 if self.check(&TokenType::Then) {
1414 self.advance();
1415 }
1416
1417 if !self.check(&TokenType::Colon) {
1419 return Err(ParseError {
1420 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
1421 span: self.current_span(),
1422 });
1423 }
1424 self.advance(); if !self.check(&TokenType::Indent) {
1428 return Err(ParseError {
1429 kind: ParseErrorKind::ExpectedStatement,
1430 span: self.current_span(),
1431 });
1432 }
1433 self.advance(); let mut then_stmts = Vec::new();
1437 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
1438 let stmt = self.parse_statement()?;
1439 then_stmts.push(stmt);
1440 if self.check(&TokenType::Period) {
1441 self.advance();
1442 }
1443 }
1444
1445 if self.check(&TokenType::Dedent) {
1447 self.advance();
1448 }
1449
1450 let then_block = self.ctx.stmts.expect("imperative arenas not initialized")
1452 .alloc_slice(then_stmts.into_iter());
1453
1454 let else_block = if self.check(&TokenType::Otherwise) || self.check(&TokenType::Else) {
1456 self.advance(); if self.check(&TokenType::If) {
1460 let nested_if = self.parse_if_statement()?;
1462 let nested_slice = self.ctx.stmts.expect("imperative arenas not initialized")
1463 .alloc_slice(std::iter::once(nested_if));
1464 Some(nested_slice)
1465 } else {
1466 if !self.check(&TokenType::Colon) {
1468 return Err(ParseError {
1469 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
1470 span: self.current_span(),
1471 });
1472 }
1473 self.advance(); if !self.check(&TokenType::Indent) {
1476 return Err(ParseError {
1477 kind: ParseErrorKind::ExpectedStatement,
1478 span: self.current_span(),
1479 });
1480 }
1481 self.advance(); let mut else_stmts = Vec::new();
1484 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
1485 let stmt = self.parse_statement()?;
1486 else_stmts.push(stmt);
1487 if self.check(&TokenType::Period) {
1488 self.advance();
1489 }
1490 }
1491
1492 if self.check(&TokenType::Dedent) {
1493 self.advance();
1494 }
1495
1496 Some(self.ctx.stmts.expect("imperative arenas not initialized")
1497 .alloc_slice(else_stmts.into_iter()))
1498 }
1499 } else if self.check(&TokenType::Elif) {
1500 self.advance(); let nested_if = self.parse_elif_as_if()?;
1504 let nested_slice = self.ctx.stmts.expect("imperative arenas not initialized")
1505 .alloc_slice(std::iter::once(nested_if));
1506 Some(nested_slice)
1507 } else {
1508 None
1509 };
1510
1511 Ok(Stmt::If {
1512 cond,
1513 then_block,
1514 else_block,
1515 })
1516 }
1517
1518 fn parse_elif_as_if(&mut self) -> ParseResult<Stmt<'a>> {
1521 let cond = self.parse_condition()?;
1523
1524 if !self.check(&TokenType::Colon) {
1526 return Err(ParseError {
1527 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
1528 span: self.current_span(),
1529 });
1530 }
1531 self.advance(); if !self.check(&TokenType::Indent) {
1535 return Err(ParseError {
1536 kind: ParseErrorKind::ExpectedStatement,
1537 span: self.current_span(),
1538 });
1539 }
1540 self.advance(); let mut then_stmts = Vec::new();
1544 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
1545 let stmt = self.parse_statement()?;
1546 then_stmts.push(stmt);
1547 if self.check(&TokenType::Period) {
1548 self.advance();
1549 }
1550 }
1551
1552 if self.check(&TokenType::Dedent) {
1554 self.advance();
1555 }
1556
1557 let then_block = self.ctx.stmts.expect("imperative arenas not initialized")
1559 .alloc_slice(then_stmts.into_iter());
1560
1561 let else_block = if self.check(&TokenType::Otherwise) || self.check(&TokenType::Else) {
1563 self.advance(); if self.check(&TokenType::If) {
1567 let nested_if = self.parse_if_statement()?;
1568 let nested_slice = self.ctx.stmts.expect("imperative arenas not initialized")
1569 .alloc_slice(std::iter::once(nested_if));
1570 Some(nested_slice)
1571 } else {
1572 if !self.check(&TokenType::Colon) {
1574 return Err(ParseError {
1575 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
1576 span: self.current_span(),
1577 });
1578 }
1579 self.advance(); if !self.check(&TokenType::Indent) {
1582 return Err(ParseError {
1583 kind: ParseErrorKind::ExpectedStatement,
1584 span: self.current_span(),
1585 });
1586 }
1587 self.advance(); let mut else_stmts = Vec::new();
1590 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
1591 let stmt = self.parse_statement()?;
1592 else_stmts.push(stmt);
1593 if self.check(&TokenType::Period) {
1594 self.advance();
1595 }
1596 }
1597
1598 if self.check(&TokenType::Dedent) {
1599 self.advance();
1600 }
1601
1602 Some(self.ctx.stmts.expect("imperative arenas not initialized")
1603 .alloc_slice(else_stmts.into_iter()))
1604 }
1605 } else if self.check(&TokenType::Elif) {
1606 self.advance(); let nested_if = self.parse_elif_as_if()?;
1608 let nested_slice = self.ctx.stmts.expect("imperative arenas not initialized")
1609 .alloc_slice(std::iter::once(nested_if));
1610 Some(nested_slice)
1611 } else {
1612 None
1613 };
1614
1615 Ok(Stmt::If {
1616 cond,
1617 then_block,
1618 else_block,
1619 })
1620 }
1621
1622 fn parse_while_statement(&mut self) -> ParseResult<Stmt<'a>> {
1623 self.advance(); let cond = self.parse_condition()?;
1626
1627 let decreasing = if self.check(&TokenType::LParen) {
1629 self.advance(); if !self.check_word("decreasing") {
1633 return Err(ParseError {
1634 kind: ParseErrorKind::ExpectedKeyword { keyword: "decreasing".to_string() },
1635 span: self.current_span(),
1636 });
1637 }
1638 self.advance(); let variant = self.parse_imperative_expr()?;
1641
1642 if !self.check(&TokenType::RParen) {
1643 return Err(ParseError {
1644 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
1645 span: self.current_span(),
1646 });
1647 }
1648 self.advance(); Some(variant)
1651 } else {
1652 None
1653 };
1654
1655 if !self.check(&TokenType::Colon) {
1656 return Err(ParseError {
1657 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
1658 span: self.current_span(),
1659 });
1660 }
1661 self.advance(); if !self.check(&TokenType::Indent) {
1664 return Err(ParseError {
1665 kind: ParseErrorKind::ExpectedStatement,
1666 span: self.current_span(),
1667 });
1668 }
1669 self.advance(); let mut body_stmts = Vec::new();
1672 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
1673 let stmt = self.parse_statement()?;
1674 body_stmts.push(stmt);
1675 if self.check(&TokenType::Period) {
1676 self.advance();
1677 }
1678 }
1679
1680 if self.check(&TokenType::Dedent) {
1681 self.advance();
1682 }
1683
1684 let body = self.ctx.stmts.expect("imperative arenas not initialized")
1685 .alloc_slice(body_stmts.into_iter());
1686
1687 Ok(Stmt::While { cond, body, decreasing })
1688 }
1689
1690 fn parse_loop_pattern(&mut self) -> ParseResult<Pattern> {
1693 use crate::ast::stmt::Pattern;
1694
1695 if self.check(&TokenType::LParen) {
1697 self.advance(); let mut identifiers = Vec::new();
1700 loop {
1701 let id = self.expect_identifier()?;
1702 identifiers.push(id);
1703
1704 if self.check(&TokenType::Comma) {
1706 self.advance(); continue;
1708 }
1709 break;
1710 }
1711
1712 if !self.check(&TokenType::RParen) {
1714 return Err(ParseError {
1715 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
1716 span: self.current_span(),
1717 });
1718 }
1719 self.advance(); Ok(Pattern::Tuple(identifiers))
1722 } else {
1723 let id = self.expect_identifier()?;
1725 Ok(Pattern::Identifier(id))
1726 }
1727 }
1728
1729 fn parse_repeat_statement(&mut self) -> ParseResult<Stmt<'a>> {
1730 self.advance(); if self.check(&TokenType::For) {
1734 self.advance();
1735 }
1736
1737 let pattern = self.parse_loop_pattern()?;
1739
1740 let iterable = if self.check(&TokenType::From) || self.check_preposition_is("from") {
1742 self.advance(); let start = self.parse_imperative_expr()?;
1744
1745 if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
1747 return Err(ParseError {
1748 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
1749 span: self.current_span(),
1750 });
1751 }
1752 self.advance();
1753
1754 let end = self.parse_imperative_expr()?;
1755 self.ctx.alloc_imperative_expr(Expr::Range { start, end })
1756 } else if self.check(&TokenType::In) || self.check_preposition_is("in") {
1757 self.advance(); self.parse_imperative_expr()?
1759 } else {
1760 return Err(ParseError {
1761 kind: ParseErrorKind::ExpectedKeyword { keyword: "in or from".to_string() },
1762 span: self.current_span(),
1763 });
1764 };
1765
1766 if !self.check(&TokenType::Colon) {
1768 return Err(ParseError {
1769 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
1770 span: self.current_span(),
1771 });
1772 }
1773 self.advance();
1774
1775 if !self.check(&TokenType::Indent) {
1777 return Err(ParseError {
1778 kind: ParseErrorKind::ExpectedStatement,
1779 span: self.current_span(),
1780 });
1781 }
1782 self.advance();
1783
1784 let mut body_stmts = Vec::new();
1786 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
1787 let stmt = self.parse_statement()?;
1788 body_stmts.push(stmt);
1789 if self.check(&TokenType::Period) {
1790 self.advance();
1791 }
1792 }
1793
1794 if self.check(&TokenType::Dedent) {
1795 self.advance();
1796 }
1797
1798 let body = self.ctx.stmts.expect("imperative arenas not initialized")
1799 .alloc_slice(body_stmts.into_iter());
1800
1801 Ok(Stmt::Repeat { pattern, iterable, body })
1802 }
1803
1804 fn parse_for_statement(&mut self) -> ParseResult<Stmt<'a>> {
1807 self.advance(); let pattern = self.parse_loop_pattern()?;
1811
1812 let iterable = if self.check(&TokenType::From) || self.check_preposition_is("from") {
1814 self.advance(); let start = self.parse_imperative_expr()?;
1816
1817 if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
1819 return Err(ParseError {
1820 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
1821 span: self.current_span(),
1822 });
1823 }
1824 self.advance();
1825
1826 let end = self.parse_imperative_expr()?;
1827 self.ctx.alloc_imperative_expr(Expr::Range { start, end })
1828 } else if self.check(&TokenType::In) || self.check_preposition_is("in") {
1829 self.advance(); self.parse_imperative_expr()?
1831 } else {
1832 return Err(ParseError {
1833 kind: ParseErrorKind::ExpectedKeyword { keyword: "in or from".to_string() },
1834 span: self.current_span(),
1835 });
1836 };
1837
1838 if !self.check(&TokenType::Colon) {
1840 return Err(ParseError {
1841 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
1842 span: self.current_span(),
1843 });
1844 }
1845 self.advance();
1846
1847 if !self.check(&TokenType::Indent) {
1849 return Err(ParseError {
1850 kind: ParseErrorKind::ExpectedStatement,
1851 span: self.current_span(),
1852 });
1853 }
1854 self.advance();
1855
1856 let mut body_stmts = Vec::new();
1858 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
1859 let stmt = self.parse_statement()?;
1860 body_stmts.push(stmt);
1861 if self.check(&TokenType::Period) {
1862 self.advance();
1863 }
1864 }
1865
1866 if self.check(&TokenType::Dedent) {
1867 self.advance();
1868 }
1869
1870 let body = self.ctx.stmts.expect("imperative arenas not initialized")
1871 .alloc_slice(body_stmts.into_iter());
1872
1873 Ok(Stmt::Repeat { pattern, iterable, body })
1874 }
1875
1876 fn parse_call_statement(&mut self) -> ParseResult<Stmt<'a>> {
1877 self.advance(); let function = match &self.peek().kind {
1883 TokenType::Noun(sym) | TokenType::Adjective(sym) => {
1884 let s = *sym;
1885 self.advance();
1886 s
1887 }
1888 TokenType::Verb { .. } | TokenType::Ambiguous { .. } => {
1889 let s = self.peek().lexeme;
1891 self.advance();
1892 s
1893 }
1894 _ => {
1895 return Err(ParseError {
1896 kind: ParseErrorKind::ExpectedIdentifier,
1897 span: self.current_span(),
1898 });
1899 }
1900 };
1901
1902 let args = if self.check_preposition_is("with") {
1904 self.advance(); self.parse_call_arguments()?
1906 } else {
1907 Vec::new()
1908 };
1909
1910 Ok(Stmt::Call { function, args })
1911 }
1912
1913 fn parse_call_arguments(&mut self) -> ParseResult<Vec<&'a Expr<'a>>> {
1914 let mut args = Vec::new();
1915
1916 let arg = self.parse_call_arg()?;
1918 args.push(arg);
1919
1920 while self.check(&TokenType::And) || self.check(&TokenType::Comma) {
1922 self.advance(); let arg = self.parse_call_arg()?;
1924 args.push(arg);
1925 }
1926
1927 Ok(args)
1928 }
1929
1930 fn parse_call_arg(&mut self) -> ParseResult<&'a Expr<'a>> {
1931 if self.check(&TokenType::Give) {
1933 self.advance(); let value = self.parse_imperative_expr()?;
1935 return Ok(self.ctx.alloc_imperative_expr(Expr::Give { value }));
1936 }
1937
1938 self.parse_imperative_expr()
1940 }
1941
1942 fn parse_condition(&mut self) -> ParseResult<&'a Expr<'a>> {
1943 self.parse_or_condition()
1946 }
1947
1948 fn parse_or_condition(&mut self) -> ParseResult<&'a Expr<'a>> {
1950 let mut left = self.parse_and_condition()?;
1951
1952 while self.check(&TokenType::Or) || self.check_word("or") {
1953 self.advance();
1954 let right = self.parse_and_condition()?;
1955 left = self.ctx.alloc_imperative_expr(Expr::BinaryOp {
1956 op: BinaryOpKind::Or,
1957 left,
1958 right,
1959 });
1960 }
1961
1962 Ok(left)
1963 }
1964
1965 fn parse_and_condition(&mut self) -> ParseResult<&'a Expr<'a>> {
1967 let mut left = self.parse_comparison()?;
1968
1969 while self.check(&TokenType::And) || self.check_word("and") {
1970 self.advance();
1971 let right = self.parse_comparison()?;
1972 left = self.ctx.alloc_imperative_expr(Expr::BinaryOp {
1973 op: BinaryOpKind::And,
1974 left,
1975 right,
1976 });
1977 }
1978
1979 Ok(left)
1980 }
1981
1982 fn parse_comparison(&mut self) -> ParseResult<&'a Expr<'a>> {
1984 if self.check(&TokenType::Not) || self.check_word("not") {
1986 self.advance(); let operand = self.parse_comparison()?; return Ok(self.ctx.alloc_imperative_expr(Expr::BinaryOp {
1990 op: BinaryOpKind::Eq,
1991 left: operand,
1992 right: self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Boolean(false))),
1993 }));
1994 }
1995
1996 let left = self.parse_imperative_expr()?;
1997
1998 let op = if self.check(&TokenType::Equals) {
2000 self.advance();
2001 Some(BinaryOpKind::Eq)
2002 } else if self.check(&TokenType::Identity) {
2003 self.advance();
2005 Some(BinaryOpKind::Eq)
2006 } else if self.check_word("is") {
2007 let saved_pos = self.current;
2009 self.advance(); if self.check_word("greater") {
2012 self.advance(); if self.check_word("than") || self.check_preposition_is("than") {
2014 self.advance(); Some(BinaryOpKind::Gt)
2016 } else {
2017 self.current = saved_pos;
2018 None
2019 }
2020 } else if self.check_word("less") {
2021 self.advance(); if self.check_word("than") || self.check_preposition_is("than") {
2023 self.advance(); Some(BinaryOpKind::Lt)
2025 } else {
2026 self.current = saved_pos;
2027 None
2028 }
2029 } else if self.check_word("at") {
2030 self.advance(); if self.check_word("least") {
2032 self.advance(); Some(BinaryOpKind::GtEq)
2034 } else if self.check_word("most") {
2035 self.advance(); Some(BinaryOpKind::LtEq)
2037 } else {
2038 self.current = saved_pos;
2039 None
2040 }
2041 } else if self.check_word("not") || self.check(&TokenType::Not) {
2042 self.advance(); Some(BinaryOpKind::NotEq)
2045 } else if self.check_word("equal") {
2046 self.advance(); if self.check_preposition_is("to") {
2049 self.advance(); Some(BinaryOpKind::Eq)
2051 } else {
2052 self.current = saved_pos;
2053 None
2054 }
2055 } else {
2056 self.current = saved_pos;
2057 None
2058 }
2059 } else if self.check(&TokenType::Lt) {
2060 self.advance();
2061 Some(BinaryOpKind::Lt)
2062 } else if self.check(&TokenType::Gt) {
2063 self.advance();
2064 Some(BinaryOpKind::Gt)
2065 } else if self.check(&TokenType::LtEq) {
2066 self.advance();
2067 Some(BinaryOpKind::LtEq)
2068 } else if self.check(&TokenType::GtEq) {
2069 self.advance();
2070 Some(BinaryOpKind::GtEq)
2071 } else if self.check(&TokenType::EqEq) || self.check(&TokenType::Assign) {
2072 self.advance();
2073 Some(BinaryOpKind::Eq)
2074 } else if self.check(&TokenType::NotEq) {
2075 self.advance();
2076 Some(BinaryOpKind::NotEq)
2077 } else {
2078 None
2079 };
2080
2081 if let Some(op) = op {
2082 let right = self.parse_imperative_expr()?;
2083 Ok(self.ctx.alloc_imperative_expr(Expr::BinaryOp { op, left, right }))
2084 } else {
2085 Ok(left)
2086 }
2087 }
2088
2089 fn parse_let_statement(&mut self) -> ParseResult<Stmt<'a>> {
2090 self.advance(); let mutable = if self.check_mutable_keyword() {
2094 self.advance();
2095 true
2096 } else {
2097 false
2098 };
2099
2100 let var = self.expect_identifier()?;
2102
2103 let ty = if self.check(&TokenType::Colon) {
2105 self.advance(); let type_expr = self.parse_type_expression()?;
2107 Some(self.ctx.alloc_type_expr(type_expr))
2108 } else {
2109 None
2110 };
2111
2112 if !self.check(&TokenType::Be) && !self.check(&TokenType::Assign) {
2114 return Err(ParseError {
2115 kind: ParseErrorKind::ExpectedKeyword { keyword: "be or =".to_string() },
2116 span: self.current_span(),
2117 });
2118 }
2119 self.advance(); if self.check_word("mounted") {
2123 self.advance(); if !self.check(&TokenType::At) && !self.check_preposition_is("at") {
2125 return Err(ParseError {
2126 kind: ParseErrorKind::ExpectedKeyword { keyword: "at".to_string() },
2127 span: self.current_span(),
2128 });
2129 }
2130 self.advance(); let path = self.parse_imperative_expr()?;
2132 return Ok(Stmt::Mount { var, path });
2133 }
2134
2135 if self.check_article() {
2137 let saved_pos = self.current;
2138 self.advance(); if let TokenType::Noun(sym) | TokenType::ProperName(sym) = self.peek().kind {
2142 let word = self.interner.resolve(sym).to_lowercase();
2143 if word == "peeragent" {
2144 self.advance(); if self.check(&TokenType::At) || self.check_preposition_is("at") {
2148 self.advance(); let address = self.parse_imperative_expr()?;
2152
2153 return Ok(Stmt::LetPeerAgent { var, address });
2154 }
2155 }
2156 }
2157 self.current = saved_pos;
2159 }
2160
2161 if self.check_article() {
2163 let saved_pos = self.current;
2164 self.advance(); if self.check(&TokenType::Pipe) {
2167 self.advance(); if !self.check_word("of") {
2171 return Err(ParseError {
2172 kind: ParseErrorKind::ExpectedKeyword { keyword: "of".to_string() },
2173 span: self.current_span(),
2174 });
2175 }
2176 self.advance(); let element_type = self.expect_identifier()?;
2180
2181 return Ok(Stmt::CreatePipe { var, element_type, capacity: None });
2184 }
2185 self.current = saved_pos;
2187 }
2188
2189 if self.check(&TokenType::Launch) {
2191 self.advance(); if !self.check_article() {
2195 return Err(ParseError {
2196 kind: ParseErrorKind::ExpectedKeyword { keyword: "a".to_string() },
2197 span: self.current_span(),
2198 });
2199 }
2200 self.advance();
2201
2202 if !self.check(&TokenType::Task) {
2204 return Err(ParseError {
2205 kind: ParseErrorKind::ExpectedKeyword { keyword: "task".to_string() },
2206 span: self.current_span(),
2207 });
2208 }
2209 self.advance();
2210
2211 if !self.check(&TokenType::To) && !self.check_word("to") {
2213 return Err(ParseError {
2214 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
2215 span: self.current_span(),
2216 });
2217 }
2218 self.advance();
2219
2220 let function = self.expect_identifier()?;
2222
2223 let args = if self.check_word("with") {
2225 self.advance();
2226 self.parse_call_arguments()?
2227 } else {
2228 vec![]
2229 };
2230
2231 return Ok(Stmt::LaunchTaskWithHandle { handle: var, function, args });
2232 }
2233
2234 let value = self.parse_imperative_expr()?;
2236
2237 if let Some(declared_ty) = &ty {
2239 if let Some(inferred) = self.infer_literal_type(value) {
2240 if !self.check_type_compatibility(declared_ty, inferred) {
2241 let expected = match declared_ty {
2242 TypeExpr::Primitive(sym) | TypeExpr::Named(sym) => {
2243 self.interner.resolve(*sym).to_string()
2244 }
2245 _ => "unknown".to_string(),
2246 };
2247 return Err(ParseError {
2248 kind: ParseErrorKind::TypeMismatch {
2249 expected,
2250 found: inferred.to_string(),
2251 },
2252 span: self.current_span(),
2253 });
2254 }
2255 }
2256 }
2257
2258 let value = if self.check_word("with") {
2260 let saved = self.current;
2261 self.advance(); if self.check_word("capacity") {
2263 self.advance(); let cap_expr = self.parse_imperative_expr()?;
2265 self.ctx.alloc_imperative_expr(Expr::WithCapacity { value, capacity: cap_expr })
2266 } else {
2267 self.current = saved; value
2269 }
2270 } else {
2271 value
2272 };
2273
2274 self.world_state.drs.introduce_referent(var, var, crate::drs::Gender::Unknown, crate::drs::Number::Singular);
2276
2277 Ok(Stmt::Let { var, ty, value, mutable })
2278 }
2279
2280 fn check_mutable_keyword(&self) -> bool {
2281 if matches!(self.peek().kind, TokenType::Mut) {
2283 return true;
2284 }
2285 if let TokenType::Noun(sym) | TokenType::Adjective(sym) = self.peek().kind {
2287 let word = self.interner.resolve(sym).to_lowercase();
2288 word == "mutable" || word == "mut"
2289 } else {
2290 false
2291 }
2292 }
2293
2294 fn infer_literal_type(&self, expr: &Expr<'_>) -> Option<&'static str> {
2296 match expr {
2297 Expr::Literal(lit) => match lit {
2298 crate::ast::Literal::Number(_) => Some("Int"),
2299 crate::ast::Literal::Float(_) => Some("Real"),
2300 crate::ast::Literal::Text(_) => Some("Text"),
2301 crate::ast::Literal::Boolean(_) => Some("Bool"),
2302 crate::ast::Literal::Nothing => Some("Unit"),
2303 crate::ast::Literal::Char(_) => Some("Char"),
2304 crate::ast::Literal::Duration(_) => Some("Duration"),
2305 crate::ast::Literal::Date(_) => Some("Date"),
2306 crate::ast::Literal::Moment(_) => Some("Moment"),
2307 crate::ast::Literal::Span { .. } => Some("Span"),
2308 crate::ast::Literal::Time(_) => Some("Time"),
2309 },
2310 _ => None, }
2312 }
2313
2314 fn check_type_compatibility(&self, declared: &TypeExpr<'_>, inferred: &str) -> bool {
2316 match declared {
2317 TypeExpr::Primitive(sym) | TypeExpr::Named(sym) => {
2318 let declared_name = self.interner.resolve(*sym);
2319 declared_name.eq_ignore_ascii_case(inferred)
2321 || (declared_name.eq_ignore_ascii_case("Nat") && inferred == "Int")
2322 || (declared_name.eq_ignore_ascii_case("Byte") && inferred == "Int")
2323 }
2324 _ => true, }
2326 }
2327
2328 fn peek_equals_assignment(&self) -> bool {
2335 let is_identifier = matches!(
2339 self.peek().kind,
2340 TokenType::Noun(_) | TokenType::ProperName(_) | TokenType::Identifier
2341 | TokenType::Adjective(_) | TokenType::Verb { .. }
2342 | TokenType::Particle(_) | TokenType::Ambiguous { .. }
2343 | TokenType::Pronoun { .. }
2344 );
2345 if !is_identifier {
2346 return false;
2347 }
2348
2349 if self.current + 1 >= self.tokens.len() {
2351 return false;
2352 }
2353
2354 let next = &self.tokens[self.current + 1].kind;
2355
2356 if matches!(next, TokenType::Assign) {
2358 return true;
2359 }
2360
2361 if matches!(next, TokenType::Colon) {
2364 let mut offset = 2;
2365 while self.current + offset < self.tokens.len() {
2366 let tok = &self.tokens[self.current + offset].kind;
2367 if matches!(tok, TokenType::Assign) {
2368 return true;
2369 }
2370 if matches!(tok, TokenType::Period | TokenType::Newline | TokenType::EOF) {
2371 return false;
2372 }
2373 offset += 1;
2374 }
2375 }
2376
2377 false
2378 }
2379
2380 fn parse_equals_assignment(&mut self, explicit_mutable: bool) -> ParseResult<Stmt<'a>> {
2382 if explicit_mutable {
2384 self.advance(); }
2386
2387 let var = self.expect_identifier()?;
2389
2390 let ty = if self.check(&TokenType::Colon) {
2392 self.advance(); let type_expr = self.parse_type_expression()?;
2394 Some(self.ctx.alloc_type_expr(type_expr))
2395 } else {
2396 None
2397 };
2398
2399 if !self.check(&TokenType::Assign) {
2401 return Err(ParseError {
2402 kind: ParseErrorKind::ExpectedKeyword { keyword: "=".to_string() },
2403 span: self.current_span(),
2404 });
2405 }
2406 self.advance(); let value = self.parse_imperative_expr()?;
2410
2411 let value = if self.check_word("with") {
2413 let saved = self.current;
2414 self.advance(); if self.check_word("capacity") {
2416 self.advance(); let cap_expr = self.parse_imperative_expr()?;
2418 self.ctx.alloc_imperative_expr(Expr::WithCapacity { value, capacity: cap_expr })
2419 } else {
2420 self.current = saved; value
2422 }
2423 } else {
2424 value
2425 };
2426
2427 self.world_state.drs.introduce_referent(var, var, crate::drs::Gender::Unknown, crate::drs::Number::Singular);
2429
2430 Ok(Stmt::Let { var, ty, value, mutable: explicit_mutable })
2431 }
2432
2433 fn parse_set_statement(&mut self) -> ParseResult<Stmt<'a>> {
2434 use crate::ast::Expr;
2435 self.advance(); let target_expr = self.parse_imperative_expr()?;
2439
2440 let target_expr = if self.check(&TokenType::At) {
2442 self.advance(); let key = self.parse_imperative_expr()?;
2444 self.ctx.alloc_imperative_expr(Expr::Index { collection: target_expr, index: key })
2445 } else {
2446 target_expr
2447 };
2448
2449 let is_to = self.check(&TokenType::To) || matches!(
2451 &self.peek().kind,
2452 TokenType::Preposition(sym) if self.interner.resolve(*sym) == "to"
2453 );
2454 if !is_to {
2455 return Err(ParseError {
2456 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
2457 span: self.current_span(),
2458 });
2459 }
2460 self.advance(); let value = self.parse_imperative_expr()?;
2464
2465 match target_expr {
2468 Expr::FieldAccess { object, field } => {
2469 Ok(Stmt::SetField { object: *object, field: *field, value })
2470 }
2471 Expr::Identifier(target) => {
2472 Ok(Stmt::Set { target: *target, value })
2473 }
2474 Expr::Index { collection, index } => {
2475 Ok(Stmt::SetIndex { collection: *collection, index: *index, value })
2476 }
2477 _ => Err(ParseError {
2478 kind: ParseErrorKind::ExpectedIdentifier,
2479 span: self.current_span(),
2480 })
2481 }
2482 }
2483
2484 fn parse_return_statement(&mut self) -> ParseResult<Stmt<'a>> {
2485 self.advance(); if self.check(&TokenType::Period) || self.is_at_end() {
2489 return Ok(Stmt::Return { value: None });
2490 }
2491
2492 let value = self.parse_comparison()?;
2494 Ok(Stmt::Return { value: Some(value) })
2495 }
2496
2497 fn parse_assert_statement(&mut self) -> ParseResult<Stmt<'a>> {
2498 self.advance(); if self.check(&TokenType::That) || matches!(self.peek().kind, TokenType::Article(Definiteness::Distal)) {
2502 self.advance();
2503 }
2504
2505 let condition = self.parse_condition()?;
2508
2509 Ok(Stmt::RuntimeAssert { condition })
2510 }
2511
2512 fn parse_trust_statement(&mut self) -> ParseResult<Stmt<'a>> {
2515 self.advance(); if self.check(&TokenType::That) || matches!(self.peek().kind, TokenType::Article(Definiteness::Distal)) {
2519 self.advance();
2520 }
2521
2522 let saved_mode = self.mode;
2524 self.mode = ParserMode::Declarative;
2525
2526 let proposition = self.parse()?;
2528
2529 self.mode = saved_mode;
2531
2532 if !self.check(&TokenType::Because) {
2534 return Err(ParseError {
2535 kind: ParseErrorKind::UnexpectedToken {
2536 expected: TokenType::Because,
2537 found: self.peek().kind.clone(),
2538 },
2539 span: self.current_span(),
2540 });
2541 }
2542 self.advance(); let justification = match &self.peek().kind {
2546 TokenType::StringLiteral(sym) => {
2547 let s = *sym;
2548 self.advance();
2549 s
2550 }
2551 _ => {
2552 return Err(ParseError {
2553 kind: ParseErrorKind::UnexpectedToken {
2554 expected: TokenType::StringLiteral(self.interner.intern("")),
2555 found: self.peek().kind.clone(),
2556 },
2557 span: self.current_span(),
2558 });
2559 }
2560 };
2561
2562 Ok(Stmt::Trust { proposition, justification })
2563 }
2564
2565 fn parse_check_statement(&mut self) -> ParseResult<Stmt<'a>> {
2569 let start_span = self.current_span();
2570 self.advance(); if self.check(&TokenType::That) {
2574 self.advance();
2575 }
2576
2577 if matches!(self.peek().kind, TokenType::Article(_)) {
2579 self.advance();
2580 }
2581
2582 let subject = match &self.peek().kind {
2584 TokenType::Noun(sym) | TokenType::Adjective(sym) | TokenType::ProperName(sym) => {
2585 let s = *sym;
2586 self.advance();
2587 s
2588 }
2589 _ => {
2590 let tok = self.peek();
2592 let s = tok.lexeme;
2593 self.advance();
2594 s
2595 }
2596 };
2597
2598 let is_capability;
2600 let predicate;
2601 let object;
2602
2603 if self.check(&TokenType::Is) || self.check(&TokenType::Are) {
2604 is_capability = false;
2606 self.advance(); predicate = match &self.peek().kind {
2610 TokenType::Noun(sym) | TokenType::Adjective(sym) | TokenType::ProperName(sym) => {
2611 let s = *sym;
2612 self.advance();
2613 s
2614 }
2615 _ => {
2616 let tok = self.peek();
2617 let s = tok.lexeme;
2618 self.advance();
2619 s
2620 }
2621 };
2622 object = None;
2623 } else if self.check(&TokenType::Can) {
2624 is_capability = true;
2626 self.advance(); predicate = match &self.peek().kind {
2630 TokenType::Verb { lemma, .. } => {
2631 let s = *lemma;
2632 self.advance();
2633 s
2634 }
2635 TokenType::Noun(sym) | TokenType::Adjective(sym) | TokenType::ProperName(sym) => {
2636 let s = *sym;
2637 self.advance();
2638 s
2639 }
2640 _ => {
2641 let tok = self.peek();
2642 let s = tok.lexeme;
2643 self.advance();
2644 s
2645 }
2646 };
2647
2648 if matches!(self.peek().kind, TokenType::Article(_)) {
2650 self.advance();
2651 }
2652
2653 let obj = match &self.peek().kind {
2655 TokenType::Noun(sym) | TokenType::Adjective(sym) | TokenType::ProperName(sym) => {
2656 let s = *sym;
2657 self.advance();
2658 s
2659 }
2660 _ => {
2661 let tok = self.peek();
2662 let s = tok.lexeme;
2663 self.advance();
2664 s
2665 }
2666 };
2667 object = Some(obj);
2668 } else {
2669 return Err(ParseError {
2670 kind: ParseErrorKind::ExpectedKeyword { keyword: "is/can".to_string() },
2671 span: self.current_span(),
2672 });
2673 }
2674
2675 let source_text = if is_capability {
2677 let obj_name = self.interner.resolve(object.unwrap());
2678 let pred_name = self.interner.resolve(predicate);
2679 let subj_name = self.interner.resolve(subject);
2680 format!("{} can {} the {}", subj_name, pred_name, obj_name)
2681 } else {
2682 let pred_name = self.interner.resolve(predicate);
2683 let subj_name = self.interner.resolve(subject);
2684 format!("{} is {}", subj_name, pred_name)
2685 };
2686
2687 Ok(Stmt::Check {
2688 subject,
2689 predicate,
2690 is_capability,
2691 object,
2692 source_text,
2693 span: start_span,
2694 })
2695 }
2696
2697 fn parse_listen_statement(&mut self) -> ParseResult<Stmt<'a>> {
2700 self.advance(); if !self.check_preposition_is("on") {
2704 return Err(ParseError {
2705 kind: ParseErrorKind::ExpectedKeyword { keyword: "on".to_string() },
2706 span: self.current_span(),
2707 });
2708 }
2709 self.advance(); let address = self.parse_imperative_expr()?;
2713
2714 Ok(Stmt::Listen { address })
2715 }
2716
2717 fn parse_connect_statement(&mut self) -> ParseResult<Stmt<'a>> {
2720 self.advance(); if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
2724 return Err(ParseError {
2725 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
2726 span: self.current_span(),
2727 });
2728 }
2729 self.advance(); let address = self.parse_imperative_expr()?;
2733
2734 Ok(Stmt::ConnectTo { address })
2735 }
2736
2737 fn parse_sleep_statement(&mut self) -> ParseResult<Stmt<'a>> {
2740 self.advance(); let milliseconds = self.parse_imperative_expr()?;
2744
2745 Ok(Stmt::Sleep { milliseconds })
2746 }
2747
2748 fn parse_sync_statement(&mut self) -> ParseResult<Stmt<'a>> {
2751 self.advance(); let var = match &self.tokens[self.current].kind {
2756 TokenType::ProperName(sym) | TokenType::Noun(sym) | TokenType::Adjective(sym) => {
2757 let s = *sym;
2758 self.advance();
2759 s
2760 }
2761 TokenType::Verb { .. } | TokenType::Ambiguous { .. } => {
2762 let s = self.tokens[self.current].lexeme;
2763 self.advance();
2764 s
2765 }
2766 _ => {
2767 return Err(ParseError {
2768 kind: ParseErrorKind::ExpectedKeyword { keyword: "variable name".to_string() },
2769 span: self.current_span(),
2770 });
2771 }
2772 };
2773
2774 if !self.check_preposition_is("on") {
2776 return Err(ParseError {
2777 kind: ParseErrorKind::ExpectedKeyword { keyword: "on".to_string() },
2778 span: self.current_span(),
2779 });
2780 }
2781 self.advance(); let topic = self.parse_imperative_expr()?;
2785
2786 Ok(Stmt::Sync { var, topic })
2787 }
2788
2789 fn parse_mount_statement(&mut self) -> ParseResult<Stmt<'a>> {
2793 self.advance(); let var = match &self.tokens[self.current].kind {
2798 TokenType::ProperName(sym) | TokenType::Noun(sym) | TokenType::Adjective(sym) => {
2799 let s = *sym;
2800 self.advance();
2801 s
2802 }
2803 TokenType::Verb { .. } | TokenType::Ambiguous { .. } => {
2804 let s = self.tokens[self.current].lexeme;
2805 self.advance();
2806 s
2807 }
2808 _ => {
2809 return Err(ParseError {
2810 kind: ParseErrorKind::ExpectedKeyword { keyword: "variable name".to_string() },
2811 span: self.current_span(),
2812 });
2813 }
2814 };
2815
2816 if !self.check(&TokenType::At) {
2818 return Err(ParseError {
2819 kind: ParseErrorKind::ExpectedKeyword { keyword: "at".to_string() },
2820 span: self.current_span(),
2821 });
2822 }
2823 self.advance(); let path = self.parse_imperative_expr()?;
2827
2828 Ok(Stmt::Mount { var, path })
2829 }
2830
2831 fn lookahead_contains_into(&self) -> bool {
2837 for i in self.current..std::cmp::min(self.current + 5, self.tokens.len()) {
2838 if matches!(self.tokens[i].kind, TokenType::Into) {
2839 return true;
2840 }
2841 }
2842 false
2843 }
2844
2845 fn lookahead_is_first_of(&self) -> bool {
2847 self.current + 3 < self.tokens.len()
2849 && matches!(self.tokens.get(self.current + 1), Some(t) if matches!(t.kind, TokenType::Article(_)))
2850 && self.tokens.get(self.current + 2)
2851 .map(|t| self.interner.resolve(t.lexeme).to_lowercase() == "first")
2852 .unwrap_or(false)
2853 }
2854
2855 fn parse_launch_statement(&mut self) -> ParseResult<Stmt<'a>> {
2858 self.advance(); if !self.check_article() {
2862 return Err(ParseError {
2863 kind: ParseErrorKind::ExpectedKeyword { keyword: "a".to_string() },
2864 span: self.current_span(),
2865 });
2866 }
2867 self.advance();
2868
2869 if !self.check(&TokenType::Task) {
2871 return Err(ParseError {
2872 kind: ParseErrorKind::ExpectedKeyword { keyword: "task".to_string() },
2873 span: self.current_span(),
2874 });
2875 }
2876 self.advance();
2877
2878 if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
2880 return Err(ParseError {
2881 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
2882 span: self.current_span(),
2883 });
2884 }
2885 self.advance();
2886
2887 let function = match &self.tokens[self.current].kind {
2890 TokenType::ProperName(sym) | TokenType::Noun(sym) | TokenType::Adjective(sym) => {
2891 let s = *sym;
2892 self.advance();
2893 s
2894 }
2895 TokenType::Verb { .. } | TokenType::Ambiguous { .. } => {
2896 let s = self.tokens[self.current].lexeme;
2897 self.advance();
2898 s
2899 }
2900 _ => {
2901 return Err(ParseError {
2902 kind: ParseErrorKind::ExpectedKeyword { keyword: "function name".to_string() },
2903 span: self.current_span(),
2904 });
2905 }
2906 };
2907
2908 let args = if self.check(&TokenType::LParen) {
2910 self.parse_call_arguments()?
2911 } else if self.check_word("with") {
2912 self.advance(); let mut args = Vec::new();
2914 let arg = self.parse_imperative_expr()?;
2915 args.push(arg);
2916 while self.check(&TokenType::And) {
2918 self.advance();
2919 let arg = self.parse_imperative_expr()?;
2920 args.push(arg);
2921 }
2922 args
2923 } else {
2924 Vec::new()
2925 };
2926
2927 Ok(Stmt::LaunchTask { function, args })
2928 }
2929
2930 fn parse_send_pipe_statement(&mut self) -> ParseResult<Stmt<'a>> {
2933 self.advance(); let value = self.parse_imperative_expr()?;
2937
2938 if !self.check(&TokenType::Into) {
2940 return Err(ParseError {
2941 kind: ParseErrorKind::ExpectedKeyword { keyword: "into".to_string() },
2942 span: self.current_span(),
2943 });
2944 }
2945 self.advance();
2946
2947 let pipe = self.parse_imperative_expr()?;
2949
2950 Ok(Stmt::SendPipe { value, pipe })
2951 }
2952
2953 fn parse_receive_pipe_statement(&mut self) -> ParseResult<Stmt<'a>> {
2956 self.advance(); let var = self.expect_identifier()?;
2960
2961 if !self.check(&TokenType::From) && !self.check_preposition_is("from") {
2963 return Err(ParseError {
2964 kind: ParseErrorKind::ExpectedKeyword { keyword: "from".to_string() },
2965 span: self.current_span(),
2966 });
2967 }
2968 self.advance();
2969
2970 let pipe = self.parse_imperative_expr()?;
2972
2973 Ok(Stmt::ReceivePipe { var, pipe })
2974 }
2975
2976 fn parse_try_statement(&mut self) -> ParseResult<Stmt<'a>> {
2979 self.advance(); if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
2983 return Err(ParseError {
2984 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
2985 span: self.current_span(),
2986 });
2987 }
2988 self.advance();
2989
2990 if self.check(&TokenType::Send) {
2992 self.advance(); let value = self.parse_imperative_expr()?;
2994
2995 if !self.check(&TokenType::Into) {
2996 return Err(ParseError {
2997 kind: ParseErrorKind::ExpectedKeyword { keyword: "into".to_string() },
2998 span: self.current_span(),
2999 });
3000 }
3001 self.advance();
3002
3003 let pipe = self.parse_imperative_expr()?;
3004 Ok(Stmt::TrySendPipe { value, pipe, result: None })
3005 } else if self.check(&TokenType::Receive) {
3006 self.advance(); let var = self.expect_identifier()?;
3009
3010 if !self.check(&TokenType::From) && !self.check_preposition_is("from") {
3011 return Err(ParseError {
3012 kind: ParseErrorKind::ExpectedKeyword { keyword: "from".to_string() },
3013 span: self.current_span(),
3014 });
3015 }
3016 self.advance();
3017
3018 let pipe = self.parse_imperative_expr()?;
3019 Ok(Stmt::TryReceivePipe { var, pipe })
3020 } else {
3021 Err(ParseError {
3022 kind: ParseErrorKind::ExpectedKeyword { keyword: "send or receive".to_string() },
3023 span: self.current_span(),
3024 })
3025 }
3026 }
3027
3028 fn parse_escape_body(&mut self) -> ParseResult<(crate::intern::Symbol, crate::intern::Symbol, crate::token::Span)> {
3031 let start_span = self.current_span();
3032 self.advance(); if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
3036 return Err(ParseError {
3037 kind: ParseErrorKind::Custom(
3038 "Expected 'to' after 'Escape'. Syntax: Escape to Rust:".to_string()
3039 ),
3040 span: self.current_span(),
3041 });
3042 }
3043 self.advance(); let language = match &self.peek().kind {
3047 TokenType::ProperName(sym) => {
3048 let s = *sym;
3049 self.advance();
3050 s
3051 }
3052 TokenType::Noun(sym) | TokenType::Adjective(sym) => {
3053 let s = *sym;
3054 self.advance();
3055 s
3056 }
3057 _ => {
3058 return Err(ParseError {
3059 kind: ParseErrorKind::Custom(
3060 "Expected language name after 'Escape to'. Currently only 'Rust' is supported.".to_string()
3061 ),
3062 span: self.current_span(),
3063 });
3064 }
3065 };
3066
3067 if !language.is(self.interner, "Rust") {
3069 let lang_str = self.interner.resolve(language);
3070 return Err(ParseError {
3071 kind: ParseErrorKind::Custom(
3072 format!("Unsupported escape target '{}'. Only 'Rust' is supported.", lang_str)
3073 ),
3074 span: self.current_span(),
3075 });
3076 }
3077
3078 if !self.check(&TokenType::Colon) {
3080 return Err(ParseError {
3081 kind: ParseErrorKind::Custom(
3082 "Expected ':' after 'Escape to Rust'. Syntax: Escape to Rust:".to_string()
3083 ),
3084 span: self.current_span(),
3085 });
3086 }
3087 self.advance(); if !self.check(&TokenType::Indent) {
3091 return Err(ParseError {
3092 kind: ParseErrorKind::Custom(
3093 "Expected indented block after 'Escape to Rust:'.".to_string()
3094 ),
3095 span: self.current_span(),
3096 });
3097 }
3098 self.advance(); let code = match &self.peek().kind {
3102 TokenType::EscapeBlock(sym) => {
3103 let s = *sym;
3104 self.advance();
3105 s
3106 }
3107 _ => {
3108 return Err(ParseError {
3109 kind: ParseErrorKind::Custom(
3110 "Escape block body is empty or malformed.".to_string()
3111 ),
3112 span: self.current_span(),
3113 });
3114 }
3115 };
3116
3117 if self.check(&TokenType::Dedent) {
3119 self.advance();
3120 }
3121
3122 let end_span = self.previous().span;
3123 Ok((language, code, crate::token::Span::new(start_span.start, end_span.end)))
3124 }
3125
3126 fn parse_escape_statement(&mut self) -> ParseResult<Stmt<'a>> {
3128 let (language, code, span) = self.parse_escape_body()?;
3129 Ok(Stmt::Escape { language, code, span })
3130 }
3131
3132 fn parse_escape_expr(&mut self) -> ParseResult<&'a Expr<'a>> {
3135 let (language, code, _span) = self.parse_escape_body()?;
3136 Ok(self.ctx.alloc_imperative_expr(Expr::Escape { language, code }))
3137 }
3138
3139 fn parse_requires_block(&mut self) -> ParseResult<Vec<Stmt<'a>>> {
3142 let mut deps = Vec::new();
3143
3144 loop {
3145 if self.is_at_end() {
3147 break;
3148 }
3149 if matches!(self.peek().kind, TokenType::BlockHeader { .. }) {
3150 break;
3151 }
3152
3153 if self.check(&TokenType::Indent)
3155 || self.check(&TokenType::Dedent)
3156 || self.check(&TokenType::Newline)
3157 {
3158 self.advance();
3159 continue;
3160 }
3161
3162 if matches!(self.peek().kind, TokenType::Article(_)) {
3164 let dep = self.parse_require_line()?;
3165 deps.push(dep);
3166 continue;
3167 }
3168
3169 self.advance();
3171 }
3172
3173 Ok(deps)
3174 }
3175
3176 fn parse_require_line(&mut self) -> ParseResult<Stmt<'a>> {
3179 let start_span = self.current_span();
3180
3181 if !matches!(self.peek().kind, TokenType::Article(_)) {
3183 return Err(crate::error::ParseError {
3184 kind: crate::error::ParseErrorKind::Custom(
3185 "Expected 'The' to begin a dependency declaration.".to_string(),
3186 ),
3187 span: self.current_span(),
3188 });
3189 }
3190 self.advance(); let crate_name = if let TokenType::StringLiteral(sym) = self.peek().kind {
3194 let s = sym;
3195 self.advance();
3196 s
3197 } else {
3198 return Err(crate::error::ParseError {
3199 kind: crate::error::ParseErrorKind::Custom(
3200 "Expected a string literal for the crate name, e.g. \"serde\".".to_string(),
3201 ),
3202 span: self.current_span(),
3203 });
3204 };
3205
3206 if !self.check_word("crate") {
3208 return Err(crate::error::ParseError {
3209 kind: crate::error::ParseErrorKind::Custom(
3210 "Expected the word 'crate' after the crate name.".to_string(),
3211 ),
3212 span: self.current_span(),
3213 });
3214 }
3215 self.advance(); if !self.check_word("version") {
3219 return Err(crate::error::ParseError {
3220 kind: crate::error::ParseErrorKind::Custom(
3221 "Expected 'version' after 'crate'.".to_string(),
3222 ),
3223 span: self.current_span(),
3224 });
3225 }
3226 self.advance(); let version = if let TokenType::StringLiteral(sym) = self.peek().kind {
3230 let s = sym;
3231 self.advance();
3232 s
3233 } else {
3234 return Err(crate::error::ParseError {
3235 kind: crate::error::ParseErrorKind::Custom(
3236 "Expected a string literal for the version, e.g. \"1.0\".".to_string(),
3237 ),
3238 span: self.current_span(),
3239 });
3240 };
3241
3242 let mut features = Vec::new();
3244 if self.check_preposition_is("with") {
3245 self.advance(); if !self.check_word("features") {
3249 return Err(crate::error::ParseError {
3250 kind: crate::error::ParseErrorKind::Custom(
3251 "Expected 'features' after 'with'.".to_string(),
3252 ),
3253 span: self.current_span(),
3254 });
3255 }
3256 self.advance(); if let TokenType::StringLiteral(sym) = self.peek().kind {
3260 features.push(sym);
3261 self.advance();
3262 } else {
3263 return Err(crate::error::ParseError {
3264 kind: crate::error::ParseErrorKind::Custom(
3265 "Expected a string literal for a feature name.".to_string(),
3266 ),
3267 span: self.current_span(),
3268 });
3269 }
3270
3271 while self.check(&TokenType::And) {
3273 self.advance(); if let TokenType::StringLiteral(sym) = self.peek().kind {
3275 features.push(sym);
3276 self.advance();
3277 } else {
3278 return Err(crate::error::ParseError {
3279 kind: crate::error::ParseErrorKind::Custom(
3280 "Expected a string literal for a feature name after 'and'.".to_string(),
3281 ),
3282 span: self.current_span(),
3283 });
3284 }
3285 }
3286 }
3287
3288 if self.check(&TokenType::For) {
3290 self.advance(); while !self.check(&TokenType::Period) && !self.check(&TokenType::EOF)
3292 && !self.check(&TokenType::Newline)
3293 && !matches!(self.peek().kind, TokenType::BlockHeader { .. })
3294 {
3295 self.advance();
3296 }
3297 }
3298
3299 if self.check(&TokenType::Period) {
3301 self.advance();
3302 }
3303
3304 let end_span = self.previous().span;
3305
3306 Ok(Stmt::Require {
3307 crate_name,
3308 version,
3309 features,
3310 span: crate::token::Span::new(start_span.start, end_span.end),
3311 })
3312 }
3313
3314 fn parse_stop_statement(&mut self) -> ParseResult<Stmt<'a>> {
3317 self.advance(); let handle = self.parse_imperative_expr()?;
3320
3321 Ok(Stmt::StopTask { handle })
3322 }
3323
3324 fn parse_select_statement(&mut self) -> ParseResult<Stmt<'a>> {
3332 use crate::ast::stmt::SelectBranch;
3333
3334 self.advance(); if !self.check_article() {
3338 return Err(ParseError {
3339 kind: ParseErrorKind::ExpectedKeyword { keyword: "the".to_string() },
3340 span: self.current_span(),
3341 });
3342 }
3343 self.advance();
3344
3345 if !self.check_word("first") {
3347 return Err(ParseError {
3348 kind: ParseErrorKind::ExpectedKeyword { keyword: "first".to_string() },
3349 span: self.current_span(),
3350 });
3351 }
3352 self.advance();
3353
3354 if !self.check_preposition_is("of") {
3356 return Err(ParseError {
3357 kind: ParseErrorKind::ExpectedKeyword { keyword: "of".to_string() },
3358 span: self.current_span(),
3359 });
3360 }
3361 self.advance();
3362
3363 if !self.check(&TokenType::Colon) {
3365 return Err(ParseError {
3366 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
3367 span: self.current_span(),
3368 });
3369 }
3370 self.advance();
3371
3372 if !self.check(&TokenType::Indent) {
3374 return Err(ParseError {
3375 kind: ParseErrorKind::ExpectedStatement,
3376 span: self.current_span(),
3377 });
3378 }
3379 self.advance();
3380
3381 let mut branches = Vec::new();
3383 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
3384 let branch = self.parse_select_branch()?;
3385 branches.push(branch);
3386 }
3387
3388 if self.check(&TokenType::Dedent) {
3390 self.advance();
3391 }
3392
3393 Ok(Stmt::Select { branches })
3394 }
3395
3396 fn parse_select_branch(&mut self) -> ParseResult<crate::ast::stmt::SelectBranch<'a>> {
3398 use crate::ast::stmt::SelectBranch;
3399
3400 if self.check(&TokenType::Receive) {
3401 self.advance(); let var = match &self.tokens[self.current].kind {
3404 TokenType::ProperName(sym) | TokenType::Noun(sym) | TokenType::Adjective(sym) => {
3405 let s = *sym;
3406 self.advance();
3407 s
3408 }
3409 _ => {
3410 return Err(ParseError {
3411 kind: ParseErrorKind::ExpectedKeyword { keyword: "variable name".to_string() },
3412 span: self.current_span(),
3413 });
3414 }
3415 };
3416
3417 if !self.check(&TokenType::From) && !self.check_preposition_is("from") {
3418 return Err(ParseError {
3419 kind: ParseErrorKind::ExpectedKeyword { keyword: "from".to_string() },
3420 span: self.current_span(),
3421 });
3422 }
3423 self.advance();
3424
3425 let pipe = self.parse_imperative_expr()?;
3426
3427 if !self.check(&TokenType::Colon) {
3429 return Err(ParseError {
3430 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
3431 span: self.current_span(),
3432 });
3433 }
3434 self.advance();
3435
3436 let body = self.parse_indented_block()?;
3438
3439 Ok(SelectBranch::Receive { var, pipe, body })
3440 } else if self.check_word("after") {
3441 self.advance(); let milliseconds = self.parse_imperative_expr()?;
3444
3445 if self.check_word("seconds") || self.check_word("milliseconds") {
3447 self.advance();
3448 }
3449
3450 if !self.check(&TokenType::Colon) {
3452 return Err(ParseError {
3453 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
3454 span: self.current_span(),
3455 });
3456 }
3457 self.advance();
3458
3459 let body = self.parse_indented_block()?;
3461
3462 Ok(SelectBranch::Timeout { milliseconds, body })
3463 } else {
3464 Err(ParseError {
3465 kind: ParseErrorKind::ExpectedKeyword { keyword: "Receive or After".to_string() },
3466 span: self.current_span(),
3467 })
3468 }
3469 }
3470
3471 fn parse_indented_block(&mut self) -> ParseResult<crate::ast::stmt::Block<'a>> {
3473 if !self.check(&TokenType::Indent) {
3475 return Err(ParseError {
3476 kind: ParseErrorKind::ExpectedStatement,
3477 span: self.current_span(),
3478 });
3479 }
3480 self.advance();
3481
3482 let mut stmts = Vec::new();
3483 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
3484 let stmt = self.parse_statement()?;
3485 stmts.push(stmt);
3486 if self.check(&TokenType::Period) {
3487 self.advance();
3488 }
3489 }
3490
3491 if self.check(&TokenType::Dedent) {
3493 self.advance();
3494 }
3495
3496 let block = self.ctx.stmts.expect("imperative arenas not initialized")
3497 .alloc_slice(stmts.into_iter());
3498
3499 Ok(block)
3500 }
3501
3502 fn parse_give_statement(&mut self) -> ParseResult<Stmt<'a>> {
3503 self.advance(); let object = self.parse_imperative_expr()?;
3507
3508 if !self.check_to_preposition() {
3510 return Err(ParseError {
3511 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
3512 span: self.current_span(),
3513 });
3514 }
3515 self.advance(); let recipient = self.parse_imperative_expr()?;
3519
3520 if let Expr::Identifier(sym) = object {
3522 self.world_state.set_ownership_by_var(*sym, crate::drs::OwnershipState::Moved);
3523 }
3524
3525 Ok(Stmt::Give { object, recipient })
3526 }
3527
3528 fn parse_show_statement(&mut self) -> ParseResult<Stmt<'a>> {
3529 self.advance(); let object = self.parse_condition()?;
3534
3535 let recipient = if self.check_to_preposition() {
3539 self.advance(); if self.check_article() {
3544 self.advance(); }
3546 if self.check(&TokenType::Console) {
3547 self.advance(); let show_sym = self.interner.intern("show");
3549 self.ctx.alloc_imperative_expr(Expr::Identifier(show_sym))
3550 } else {
3551 self.parse_imperative_expr()?
3553 }
3554 } else {
3555 let show_sym = self.interner.intern("show");
3557 self.ctx.alloc_imperative_expr(Expr::Identifier(show_sym))
3558 };
3559
3560 if let Expr::Identifier(sym) = object {
3562 self.world_state.set_ownership_by_var(*sym, crate::drs::OwnershipState::Borrowed);
3563 }
3564
3565 Ok(Stmt::Show { object, recipient })
3566 }
3567
3568 fn parse_push_statement(&mut self) -> ParseResult<Stmt<'a>> {
3571 self.advance(); let value = self.parse_imperative_expr()?;
3575
3576 if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
3578 return Err(ParseError {
3579 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
3580 span: self.current_span(),
3581 });
3582 }
3583 self.advance(); let collection = self.parse_imperative_expr()?;
3587
3588 Ok(Stmt::Push { value, collection })
3589 }
3590
3591 fn parse_pop_statement(&mut self) -> ParseResult<Stmt<'a>> {
3594 self.advance(); if !self.check(&TokenType::From) && !self.check_preposition_is("from") {
3598 return Err(ParseError {
3599 kind: ParseErrorKind::ExpectedKeyword { keyword: "from".to_string() },
3600 span: self.current_span(),
3601 });
3602 }
3603 self.advance(); let collection = self.parse_imperative_expr()?;
3607
3608 let into = if self.check(&TokenType::Into) || self.check_preposition_is("into") {
3610 self.advance(); if let TokenType::Noun(sym) | TokenType::ProperName(sym) = &self.peek().kind {
3614 let sym = *sym;
3615 self.advance();
3616 Some(sym)
3617 } else if let Some(token) = self.tokens.get(self.current) {
3618 let sym = token.lexeme;
3620 self.advance();
3621 Some(sym)
3622 } else {
3623 return Err(ParseError {
3624 kind: ParseErrorKind::ExpectedIdentifier,
3625 span: self.current_span(),
3626 });
3627 }
3628 } else {
3629 None
3630 };
3631
3632 Ok(Stmt::Pop { collection, into })
3633 }
3634
3635 fn parse_add_statement(&mut self) -> ParseResult<Stmt<'a>> {
3638 self.advance(); let value = self.parse_imperative_expr()?;
3642
3643 if !self.check_preposition_is("to") && !self.check(&TokenType::To) {
3645 return Err(ParseError {
3646 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
3647 span: self.current_span(),
3648 });
3649 }
3650 self.advance(); let collection = self.parse_imperative_expr()?;
3654
3655 Ok(Stmt::Add { value, collection })
3656 }
3657
3658 fn parse_remove_statement(&mut self) -> ParseResult<Stmt<'a>> {
3661 self.advance(); let value = self.parse_imperative_expr()?;
3665
3666 if !self.check(&TokenType::From) && !self.check_preposition_is("from") {
3668 return Err(ParseError {
3669 kind: ParseErrorKind::ExpectedKeyword { keyword: "from".to_string() },
3670 span: self.current_span(),
3671 });
3672 }
3673 self.advance(); let collection = self.parse_imperative_expr()?;
3677
3678 Ok(Stmt::Remove { value, collection })
3679 }
3680
3681 fn parse_read_statement(&mut self) -> ParseResult<Stmt<'a>> {
3685 self.advance(); let var = self.expect_identifier()?;
3689
3690 if !self.check(&TokenType::From) && !self.check_preposition_is("from") {
3692 return Err(ParseError {
3693 kind: ParseErrorKind::ExpectedKeyword { keyword: "from".to_string() },
3694 span: self.current_span(),
3695 });
3696 }
3697 self.advance(); if self.check_article() {
3701 self.advance();
3702 }
3703
3704 let source = if self.check(&TokenType::Console) {
3706 self.advance(); ReadSource::Console
3708 } else if self.check(&TokenType::File) {
3709 self.advance(); let path = self.parse_imperative_expr()?;
3711 ReadSource::File(path)
3712 } else {
3713 return Err(ParseError {
3714 kind: ParseErrorKind::ExpectedKeyword { keyword: "console or file".to_string() },
3715 span: self.current_span(),
3716 });
3717 };
3718
3719 Ok(Stmt::ReadFrom { var, source })
3720 }
3721
3722 fn parse_write_statement(&mut self) -> ParseResult<Stmt<'a>> {
3725 self.advance(); let content = self.parse_imperative_expr()?;
3729
3730 if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
3732 return Err(ParseError {
3733 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
3734 span: self.current_span(),
3735 });
3736 }
3737 self.advance(); if !self.check(&TokenType::File) {
3741 return Err(ParseError {
3742 kind: ParseErrorKind::ExpectedKeyword { keyword: "file".to_string() },
3743 span: self.current_span(),
3744 });
3745 }
3746 self.advance(); let path = self.parse_imperative_expr()?;
3750
3751 Ok(Stmt::WriteFile { content, path })
3752 }
3753
3754 fn parse_zone_statement(&mut self) -> ParseResult<Stmt<'a>> {
3760 self.advance(); if self.check_article() {
3764 self.advance();
3765 }
3766
3767 if self.check(&TokenType::New) {
3769 self.advance();
3770 }
3771
3772 if !self.check(&TokenType::Zone) {
3774 return Err(ParseError {
3775 kind: ParseErrorKind::ExpectedKeyword { keyword: "zone".to_string() },
3776 span: self.current_span(),
3777 });
3778 }
3779 self.advance(); if !self.check(&TokenType::Called) {
3783 return Err(ParseError {
3784 kind: ParseErrorKind::ExpectedKeyword { keyword: "called".to_string() },
3785 span: self.current_span(),
3786 });
3787 }
3788 self.advance(); let name = match &self.peek().kind {
3792 TokenType::StringLiteral(sym) => {
3793 let s = *sym;
3794 self.advance();
3795 s
3796 }
3797 TokenType::ProperName(sym) | TokenType::Noun(sym) | TokenType::Adjective(sym) => {
3798 let s = *sym;
3799 self.advance();
3800 s
3801 }
3802 _ => {
3803 let token = self.peek().clone();
3805 self.advance();
3806 token.lexeme
3807 }
3808 };
3809
3810 let mut capacity = None;
3811 let mut source_file = None;
3812
3813 if self.check(&TokenType::Mapped) {
3815 self.advance(); if !self.check(&TokenType::From) && !self.check_preposition_is("from") {
3819 return Err(ParseError {
3820 kind: ParseErrorKind::ExpectedKeyword { keyword: "from".to_string() },
3821 span: self.current_span(),
3822 });
3823 }
3824 self.advance(); if let TokenType::StringLiteral(path) = &self.peek().kind {
3828 source_file = Some(*path);
3829 self.advance();
3830 } else {
3831 return Err(ParseError {
3832 kind: ParseErrorKind::ExpectedKeyword { keyword: "file path string".to_string() },
3833 span: self.current_span(),
3834 });
3835 }
3836 }
3837 else if self.check_of_preposition() {
3839 self.advance(); if !self.check(&TokenType::Size) {
3843 return Err(ParseError {
3844 kind: ParseErrorKind::ExpectedKeyword { keyword: "size".to_string() },
3845 span: self.current_span(),
3846 });
3847 }
3848 self.advance(); let size_value = match &self.peek().kind {
3852 TokenType::Number(sym) => {
3853 let num_str = self.interner.resolve(*sym);
3854 let val = num_str.replace('_', "").parse::<usize>().unwrap_or(0);
3855 self.advance();
3856 val
3857 }
3858 TokenType::Cardinal(n) => {
3859 let val = *n as usize;
3860 self.advance();
3861 val
3862 }
3863 _ => {
3864 return Err(ParseError {
3865 kind: ParseErrorKind::ExpectedNumber,
3866 span: self.current_span(),
3867 });
3868 }
3869 };
3870
3871 let unit_multiplier = self.parse_size_unit()?;
3873 capacity = Some(size_value * unit_multiplier);
3874 }
3875
3876 if !self.check(&TokenType::Colon) {
3878 return Err(ParseError {
3879 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
3880 span: self.current_span(),
3881 });
3882 }
3883 self.advance(); if !self.check(&TokenType::Indent) {
3887 return Err(ParseError {
3888 kind: ParseErrorKind::ExpectedStatement,
3889 span: self.current_span(),
3890 });
3891 }
3892 self.advance(); let mut body_stmts = Vec::new();
3896 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
3897 let stmt = self.parse_statement()?;
3898 body_stmts.push(stmt);
3899 if self.check(&TokenType::Period) {
3900 self.advance();
3901 }
3902 }
3903
3904 if self.check(&TokenType::Dedent) {
3906 self.advance();
3907 }
3908
3909 let body = self.ctx.stmts.expect("imperative arenas not initialized")
3910 .alloc_slice(body_stmts.into_iter());
3911
3912 Ok(Stmt::Zone { name, capacity, source_file, body })
3913 }
3914
3915 fn parse_size_unit(&mut self) -> ParseResult<usize> {
3917 let token = self.peek().clone();
3918 let unit_str = self.interner.resolve(token.lexeme).to_uppercase();
3919 self.advance();
3920
3921 match unit_str.as_str() {
3922 "B" | "BYTES" | "BYTE" => Ok(1),
3923 "KB" | "KILOBYTE" | "KILOBYTES" => Ok(1024),
3924 "MB" | "MEGABYTE" | "MEGABYTES" => Ok(1024 * 1024),
3925 "GB" | "GIGABYTE" | "GIGABYTES" => Ok(1024 * 1024 * 1024),
3926 _ => Err(ParseError {
3927 kind: ParseErrorKind::ExpectedKeyword {
3928 keyword: "size unit (B, KB, MB, GB)".to_string(),
3929 },
3930 span: token.span,
3931 }),
3932 }
3933 }
3934
3935 fn parse_concurrent_block(&mut self) -> ParseResult<Stmt<'a>> {
3944 self.advance(); if !self.check(&TokenType::All) {
3948 return Err(ParseError {
3949 kind: ParseErrorKind::ExpectedKeyword { keyword: "all".to_string() },
3950 span: self.current_span(),
3951 });
3952 }
3953 self.advance(); if !self.check_of_preposition() {
3957 return Err(ParseError {
3958 kind: ParseErrorKind::ExpectedKeyword { keyword: "of".to_string() },
3959 span: self.current_span(),
3960 });
3961 }
3962 self.advance(); if !self.check_article() {
3966 return Err(ParseError {
3967 kind: ParseErrorKind::ExpectedKeyword { keyword: "the".to_string() },
3968 span: self.current_span(),
3969 });
3970 }
3971 self.advance(); if !self.check(&TokenType::Following) {
3975 return Err(ParseError {
3976 kind: ParseErrorKind::ExpectedKeyword { keyword: "following".to_string() },
3977 span: self.current_span(),
3978 });
3979 }
3980 self.advance(); if !self.check(&TokenType::Colon) {
3984 return Err(ParseError {
3985 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
3986 span: self.current_span(),
3987 });
3988 }
3989 self.advance(); if !self.check(&TokenType::Indent) {
3993 return Err(ParseError {
3994 kind: ParseErrorKind::ExpectedStatement,
3995 span: self.current_span(),
3996 });
3997 }
3998 self.advance(); let mut task_stmts = Vec::new();
4002 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
4003 let stmt = self.parse_statement()?;
4004 task_stmts.push(stmt);
4005 if self.check(&TokenType::Period) {
4006 self.advance();
4007 }
4008 }
4009
4010 if self.check(&TokenType::Dedent) {
4012 self.advance();
4013 }
4014
4015 let tasks = self.ctx.stmts.expect("imperative arenas not initialized")
4016 .alloc_slice(task_stmts.into_iter());
4017
4018 Ok(Stmt::Concurrent { tasks })
4019 }
4020
4021 fn parse_parallel_block(&mut self) -> ParseResult<Stmt<'a>> {
4030 self.advance(); if !self.check(&TokenType::Colon) {
4034 return Err(ParseError {
4035 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
4036 span: self.current_span(),
4037 });
4038 }
4039 self.advance(); if !self.check(&TokenType::Indent) {
4043 return Err(ParseError {
4044 kind: ParseErrorKind::ExpectedStatement,
4045 span: self.current_span(),
4046 });
4047 }
4048 self.advance(); let mut task_stmts = Vec::new();
4052 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
4053 let stmt = self.parse_statement()?;
4054 task_stmts.push(stmt);
4055 if self.check(&TokenType::Period) {
4056 self.advance();
4057 }
4058 }
4059
4060 if self.check(&TokenType::Dedent) {
4062 self.advance();
4063 }
4064
4065 let tasks = self.ctx.stmts.expect("imperative arenas not initialized")
4066 .alloc_slice(task_stmts.into_iter());
4067
4068 Ok(Stmt::Parallel { tasks })
4069 }
4070
4071 fn parse_inspect_statement(&mut self) -> ParseResult<Stmt<'a>> {
4078 self.advance(); let target = self.parse_imperative_expr()?;
4082
4083 if !self.check(&TokenType::Colon) {
4085 return Err(ParseError {
4086 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
4087 span: self.current_span(),
4088 });
4089 }
4090 self.advance(); if !self.check(&TokenType::Indent) {
4094 return Err(ParseError {
4095 kind: ParseErrorKind::ExpectedStatement,
4096 span: self.current_span(),
4097 });
4098 }
4099 self.advance(); let mut arms = Vec::new();
4102 let mut has_otherwise = false;
4103
4104 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
4106 if self.check(&TokenType::Otherwise) {
4107 self.advance(); if !self.check(&TokenType::Colon) {
4111 return Err(ParseError {
4112 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
4113 span: self.current_span(),
4114 });
4115 }
4116 self.advance(); let body_stmts = if self.check(&TokenType::Indent) {
4120 self.advance(); let mut stmts = Vec::new();
4122 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
4123 let stmt = self.parse_statement()?;
4124 stmts.push(stmt);
4125 if self.check(&TokenType::Period) {
4126 self.advance();
4127 }
4128 }
4129 if self.check(&TokenType::Dedent) {
4130 self.advance();
4131 }
4132 stmts
4133 } else {
4134 let stmt = self.parse_statement()?;
4136 if self.check(&TokenType::Period) {
4137 self.advance();
4138 }
4139 vec![stmt]
4140 };
4141
4142 let body = self.ctx.stmts.expect("imperative arenas not initialized")
4143 .alloc_slice(body_stmts.into_iter());
4144
4145 arms.push(MatchArm { enum_name: None, variant: None, bindings: vec![], body });
4146 has_otherwise = true;
4147 break;
4148 }
4149
4150 if self.check(&TokenType::If) {
4151 let arm = self.parse_match_arm()?;
4153 arms.push(arm);
4154 } else if self.check(&TokenType::When) || self.check_word("When") {
4155 let arm = self.parse_when_arm()?;
4157 arms.push(arm);
4158 } else if self.check(&TokenType::Newline) {
4159 self.advance();
4161 } else {
4162 self.advance();
4164 }
4165 }
4166
4167 if self.check(&TokenType::Dedent) {
4169 self.advance();
4170 }
4171
4172 Ok(Stmt::Inspect { target, arms, has_otherwise })
4173 }
4174
4175 fn parse_match_arm(&mut self) -> ParseResult<MatchArm<'a>> {
4177 self.advance(); if !self.check_word("it") {
4181 return Err(ParseError {
4182 kind: ParseErrorKind::ExpectedKeyword { keyword: "it".to_string() },
4183 span: self.current_span(),
4184 });
4185 }
4186 self.advance(); if !self.check(&TokenType::Is) {
4190 return Err(ParseError {
4191 kind: ParseErrorKind::ExpectedKeyword { keyword: "is".to_string() },
4192 span: self.current_span(),
4193 });
4194 }
4195 self.advance(); if self.check_article() {
4199 self.advance();
4200 }
4201
4202 let variant = self.expect_identifier()?;
4204
4205 let enum_name = self.find_variant(variant);
4207
4208 let bindings = if self.check(&TokenType::LParen) {
4210 self.parse_pattern_bindings()?
4211 } else {
4212 vec![]
4213 };
4214
4215 if !self.check(&TokenType::Colon) {
4217 return Err(ParseError {
4218 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
4219 span: self.current_span(),
4220 });
4221 }
4222 self.advance(); if !self.check(&TokenType::Indent) {
4226 return Err(ParseError {
4227 kind: ParseErrorKind::ExpectedStatement,
4228 span: self.current_span(),
4229 });
4230 }
4231 self.advance(); let mut body_stmts = Vec::new();
4235 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
4236 let stmt = self.parse_statement()?;
4237 body_stmts.push(stmt);
4238 if self.check(&TokenType::Period) {
4239 self.advance();
4240 }
4241 }
4242
4243 if self.check(&TokenType::Dedent) {
4245 self.advance();
4246 }
4247
4248 let body = self.ctx.stmts.expect("imperative arenas not initialized")
4249 .alloc_slice(body_stmts.into_iter());
4250
4251 Ok(MatchArm { enum_name, variant: Some(variant), bindings, body })
4252 }
4253
4254 fn parse_when_arm(&mut self) -> ParseResult<MatchArm<'a>> {
4256 self.advance(); let variant = self.expect_identifier()?;
4260
4261 let (enum_name, variant_fields) = self.type_registry
4263 .as_ref()
4264 .and_then(|r| r.find_variant(variant).map(|(enum_name, vdef)| {
4265 let fields: Vec<_> = vdef.fields.iter().map(|f| f.name).collect();
4266 (Some(enum_name), fields)
4267 }))
4268 .unwrap_or((None, vec![]));
4269
4270 let bindings = if self.check(&TokenType::LParen) {
4272 let raw_bindings = self.parse_when_bindings()?;
4273 raw_bindings.into_iter().enumerate().map(|(i, binding)| {
4275 let field = variant_fields.get(i).copied().unwrap_or(binding);
4276 (field, binding)
4277 }).collect()
4278 } else {
4279 vec![]
4280 };
4281
4282 if !self.check(&TokenType::Colon) {
4284 return Err(ParseError {
4285 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
4286 span: self.current_span(),
4287 });
4288 }
4289 self.advance(); let body_stmts = if self.check(&TokenType::Indent) {
4293 self.advance(); let mut stmts = Vec::new();
4295 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
4296 let stmt = self.parse_statement()?;
4297 stmts.push(stmt);
4298 if self.check(&TokenType::Period) {
4299 self.advance();
4300 }
4301 }
4302 if self.check(&TokenType::Dedent) {
4303 self.advance();
4304 }
4305 stmts
4306 } else {
4307 let stmt = self.parse_statement()?;
4309 if self.check(&TokenType::Period) {
4310 self.advance();
4311 }
4312 vec![stmt]
4313 };
4314
4315 let body = self.ctx.stmts.expect("imperative arenas not initialized")
4316 .alloc_slice(body_stmts.into_iter());
4317
4318 Ok(MatchArm { enum_name, variant: Some(variant), bindings, body })
4319 }
4320
4321 fn parse_when_bindings(&mut self) -> ParseResult<Vec<Symbol>> {
4323 self.advance(); let mut bindings = Vec::new();
4325
4326 loop {
4327 let binding = self.expect_identifier()?;
4328 bindings.push(binding);
4329
4330 if !self.check(&TokenType::Comma) {
4331 break;
4332 }
4333 self.advance(); }
4335
4336 if !self.check(&TokenType::RParen) {
4337 return Err(ParseError {
4338 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
4339 span: self.current_span(),
4340 });
4341 }
4342 self.advance(); Ok(bindings)
4345 }
4346
4347 fn parse_pattern_bindings(&mut self) -> ParseResult<Vec<(Symbol, Symbol)>> {
4349 self.advance(); let mut bindings = Vec::new();
4351
4352 loop {
4353 let field = self.expect_identifier()?;
4354 let binding = if self.check(&TokenType::Colon) {
4355 self.advance(); self.expect_identifier()?
4357 } else {
4358 field };
4360 bindings.push((field, binding));
4361
4362 if !self.check(&TokenType::Comma) {
4363 break;
4364 }
4365 self.advance(); }
4367
4368 if !self.check(&TokenType::RParen) {
4369 return Err(ParseError {
4370 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
4371 span: self.current_span(),
4372 });
4373 }
4374 self.advance(); Ok(bindings)
4377 }
4378
4379 fn parse_constructor_fields(&mut self) -> ParseResult<Vec<(Symbol, &'a Expr<'a>)>> {
4383 use crate::ast::Expr;
4384 let mut fields = Vec::new();
4385
4386 self.advance();
4388
4389 loop {
4390 let field_name = self.expect_identifier()?;
4392
4393 let value = self.parse_imperative_expr()?;
4395
4396 fields.push((field_name, value));
4397
4398 if self.check(&TokenType::And) {
4400 self.advance(); continue;
4402 }
4403 break;
4404 }
4405
4406 Ok(fields)
4407 }
4408
4409 fn parse_variant_constructor_fields(&mut self) -> ParseResult<Vec<(Symbol, &'a Expr<'a>)>> {
4411 self.parse_constructor_fields()
4412 }
4413
4414 fn parse_struct_init_fields(&mut self) -> ParseResult<Vec<(Symbol, &'a Expr<'a>)>> {
4416 self.parse_constructor_fields()
4417 }
4418
4419 fn parse_generic_type_args(&mut self, type_name: Symbol) -> ParseResult<Vec<TypeExpr<'a>>> {
4423 if !self.is_generic_type(type_name) {
4425 return Ok(vec![]);
4426 }
4427
4428 if !self.check_preposition_is("of") {
4430 return Ok(vec![]); }
4432 self.advance(); let mut type_args = Vec::new();
4435 loop {
4436 let type_arg = self.parse_type_expression()?;
4438 type_args.push(type_arg);
4439
4440 if self.check(&TokenType::And) || self.check_to_preposition() {
4442 self.advance(); continue;
4444 }
4445 break;
4446 }
4447
4448 Ok(type_args)
4449 }
4450
4451 fn skip_type_def_content(&mut self) {
4455 while !self.is_at_end() {
4456 if matches!(
4458 self.tokens.get(self.current),
4459 Some(Token { kind: TokenType::BlockHeader { .. }, .. })
4460 ) {
4461 break;
4462 }
4463 self.advance();
4464 }
4465 }
4466
4467 fn parse_theorem_block(&mut self) -> ParseResult<Stmt<'a>> {
4475 use crate::ast::theorem::{TheoremBlock, ProofStrategy};
4476
4477 self.skip_whitespace_tokens();
4479
4480 if self.check(&TokenType::Colon) {
4485 self.advance();
4486 }
4487
4488 self.skip_whitespace_tokens();
4490
4491 let name = if let Some(token) = self.tokens.get(self.current) {
4493 match &token.kind {
4494 TokenType::Noun(_)
4495 | TokenType::ProperName(_)
4496 | TokenType::Verb { .. }
4497 | TokenType::Adjective(_) => {
4498 let name = self.interner.resolve(token.lexeme).to_string();
4499 self.advance();
4500 name
4501 }
4502 _ => {
4503 let lexeme = self.interner.resolve(token.lexeme);
4505 if !lexeme.is_empty() && lexeme.chars().next().map(|c| c.is_alphanumeric()).unwrap_or(false) {
4506 let name = lexeme.to_string();
4507 self.advance();
4508 name
4509 } else {
4510 "Anonymous".to_string()
4511 }
4512 }
4513 }
4514 } else {
4515 "Anonymous".to_string()
4516 };
4517
4518 self.skip_whitespace_tokens();
4519
4520 if self.check(&TokenType::Period) {
4522 self.advance();
4523 }
4524
4525 self.skip_whitespace_tokens();
4526
4527 let mut premises = Vec::new();
4530 while self.check(&TokenType::Given) {
4531 self.advance(); if self.check(&TokenType::Colon) {
4535 self.advance();
4536 }
4537
4538 self.skip_whitespace_tokens();
4539
4540 let premise_expr = self.parse_sentence()?;
4542 premises.push(premise_expr);
4543
4544 self.world_state.end_sentence();
4547
4548 if self.check(&TokenType::Period) {
4550 self.advance();
4551 }
4552
4553 self.skip_whitespace_tokens();
4554 }
4555
4556 let goal = if self.check(&TokenType::Prove) {
4558 self.advance(); if self.check(&TokenType::Colon) {
4561 self.advance();
4562 }
4563
4564 self.skip_whitespace_tokens();
4565
4566 let goal_expr = self.parse_sentence()?;
4567
4568 if self.check(&TokenType::Period) {
4569 self.advance();
4570 }
4571
4572 goal_expr
4573 } else {
4574 return Err(ParseError {
4575 kind: ParseErrorKind::ExpectedKeyword { keyword: "Prove".to_string() },
4576 span: self.current_span(),
4577 });
4578 };
4579
4580 self.skip_whitespace_tokens();
4581
4582 let strategy = if self.check(&TokenType::BlockHeader { block_type: crate::token::BlockType::Proof }) {
4584 self.advance();
4585 self.skip_whitespace_tokens();
4586
4587 if self.check(&TokenType::Colon) {
4588 self.advance();
4589 }
4590
4591 self.skip_whitespace_tokens();
4592
4593 if self.check(&TokenType::Auto) {
4594 self.advance();
4595 ProofStrategy::Auto
4596 } else {
4597 ProofStrategy::Auto
4599 }
4600 } else {
4601 ProofStrategy::Auto
4603 };
4604
4605 if self.check(&TokenType::Period) {
4607 self.advance();
4608 }
4609
4610 let theorem = TheoremBlock {
4611 name,
4612 premises,
4613 goal,
4614 strategy,
4615 };
4616
4617 Ok(Stmt::Theorem(theorem))
4618 }
4619
4620 fn skip_whitespace_tokens(&mut self) {
4622 while self.check(&TokenType::Newline) || self.check(&TokenType::Indent) || self.check(&TokenType::Dedent) {
4623 self.advance();
4624 }
4625 }
4626
4627 fn parse_function_def(&mut self) -> ParseResult<Stmt<'a>> {
4632 if self.check(&TokenType::To) || self.check_preposition_is("to") {
4634 self.advance();
4635 }
4636
4637 let mut is_native = if self.check(&TokenType::Native) {
4639 self.advance(); true
4641 } else {
4642 false
4643 };
4644
4645 let name = self.expect_identifier()?;
4647
4648 let mut params = Vec::new();
4650 while self.check(&TokenType::LParen) {
4651 self.advance(); if self.check(&TokenType::RParen) {
4655 self.advance(); break;
4657 }
4658
4659 loop {
4661 let param_name = self.expect_identifier()?;
4662
4663 if !self.check(&TokenType::Colon) {
4665 return Err(ParseError {
4666 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
4667 span: self.current_span(),
4668 });
4669 }
4670 self.advance(); let param_type_expr = self.parse_type_expression()?;
4674 let param_type = self.ctx.alloc_type_expr(param_type_expr);
4675
4676 params.push((param_name, param_type));
4677
4678 if self.check(&TokenType::Comma) {
4680 self.advance(); continue;
4682 }
4683 break;
4684 }
4685
4686 if !self.check(&TokenType::RParen) {
4688 return Err(ParseError {
4689 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
4690 span: self.current_span(),
4691 });
4692 }
4693 self.advance(); if self.check_word("and") || self.check_preposition() || self.check(&TokenType::From) {
4698 self.advance();
4699 }
4700 }
4701
4702 let return_type = if self.check(&TokenType::Arrow) {
4704 self.advance(); let ret_type_expr = self.parse_type_expression()?;
4706 Some(self.ctx.alloc_type_expr(ret_type_expr))
4707 } else {
4708 None
4709 };
4710
4711 let mut native_path: Option<Symbol> = None;
4713 let mut is_exported = false;
4714 let mut export_target: Option<Symbol> = None;
4715
4716 if self.check_word("is") {
4717 self.advance(); if self.check(&TokenType::Native) {
4719 self.advance(); is_native = true;
4722 if let TokenType::StringLiteral(sym) = self.peek().kind {
4723 native_path = Some(sym);
4724 self.advance(); } else {
4726 return Err(ParseError {
4727 kind: ParseErrorKind::Custom(
4728 "Expected a string literal for native function path (e.g., is native \"reqwest::blocking::get\")".to_string()
4729 ),
4730 span: self.current_span(),
4731 });
4732 }
4733 } else if self.check_word("exported") {
4734 self.advance(); is_exported = true;
4737 if self.check_word("for") {
4738 self.advance(); let target_sym = self.expect_identifier()?;
4740 let target_str = self.interner.resolve(target_sym);
4741 if !target_str.eq_ignore_ascii_case("c") && !target_str.eq_ignore_ascii_case("wasm") {
4742 return Err(ParseError {
4743 kind: ParseErrorKind::Custom(
4744 format!("Unsupported export target \"{}\". Supported targets are \"c\" and \"wasm\".", target_str)
4745 ),
4746 span: self.current_span(),
4747 });
4748 }
4749 export_target = Some(target_sym);
4750 }
4751 }
4752 }
4753
4754 if is_native {
4756 if self.check(&TokenType::Period) {
4758 self.advance();
4759 }
4760 if self.check(&TokenType::Newline) {
4761 self.advance();
4762 }
4763
4764 let empty_body = self.ctx.stmts.expect("imperative arenas not initialized")
4766 .alloc_slice(std::iter::empty());
4767
4768 return Ok(Stmt::FunctionDef {
4769 name,
4770 params,
4771 body: empty_body,
4772 return_type,
4773 is_native: true,
4774 native_path,
4775 is_exported: false,
4776 export_target: None,
4777 });
4778 }
4779
4780 if !self.check(&TokenType::Colon) {
4782 return Err(ParseError {
4783 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
4784 span: self.current_span(),
4785 });
4786 }
4787 self.advance(); if !self.check(&TokenType::Indent) {
4791 return Err(ParseError {
4792 kind: ParseErrorKind::ExpectedStatement,
4793 span: self.current_span(),
4794 });
4795 }
4796 self.advance(); let mut body_stmts = Vec::new();
4800 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
4801 if self.check(&TokenType::Newline) {
4803 self.advance();
4804 continue;
4805 }
4806 if matches!(self.peek().kind, TokenType::BlockHeader { .. }) {
4808 break;
4809 }
4810 let stmt = self.parse_statement()?;
4811 body_stmts.push(stmt);
4812 if self.check(&TokenType::Period) {
4813 self.advance();
4814 }
4815 }
4816
4817 if self.check(&TokenType::Dedent) {
4819 self.advance();
4820 }
4821
4822 let body = self.ctx.stmts.expect("imperative arenas not initialized")
4824 .alloc_slice(body_stmts.into_iter());
4825
4826 Ok(Stmt::FunctionDef {
4827 name,
4828 params,
4829 body,
4830 return_type,
4831 is_native: false,
4832 native_path: None,
4833 is_exported,
4834 export_target,
4835 })
4836 }
4837
4838 fn parse_primary_expr(&mut self) -> ParseResult<&'a Expr<'a>> {
4840 use crate::ast::{Expr, Literal};
4841
4842 let token = self.peek().clone();
4843 match &token.kind {
4844 TokenType::New => {
4848 self.advance(); let base_type_name = self.expect_identifier()?;
4850
4851 let type_name = if self.check(&TokenType::From) {
4853 self.advance(); let module_name = self.expect_identifier()?;
4855 let module_str = self.interner.resolve(module_name);
4856 let base_str = self.interner.resolve(base_type_name);
4857 let qualified = format!("{}::{}", module_str, base_str);
4858 self.interner.intern(&qualified)
4859 } else {
4860 base_type_name
4861 };
4862
4863 if let Some(enum_name) = self.find_variant(type_name) {
4865 let fields = if self.check_word("with") {
4867 self.parse_variant_constructor_fields()?
4868 } else {
4869 vec![]
4870 };
4871 let base = self.ctx.alloc_imperative_expr(Expr::NewVariant {
4872 enum_name,
4873 variant: type_name,
4874 fields,
4875 });
4876 return self.parse_field_access_chain(base);
4877 }
4878
4879 let type_args = self.parse_generic_type_args(type_name)?;
4881
4882 let init_fields = if self.check_word("with") && !self.peek_word_at(1, "capacity") {
4885 self.parse_struct_init_fields()?
4886 } else {
4887 vec![]
4888 };
4889
4890 let base = self.ctx.alloc_imperative_expr(Expr::New { type_name, type_args, init_fields });
4891 return self.parse_field_access_chain(base);
4892 }
4893
4894 TokenType::Article(_) => {
4898 if let Some(next) = self.tokens.get(self.current + 1) {
4901 if matches!(next.kind, TokenType::Manifest) {
4902 self.advance(); return self.parse_primary_expr();
4905 }
4906 if matches!(next.kind, TokenType::Chunk) {
4907 self.advance(); return self.parse_primary_expr();
4910 }
4911 if matches!(next.kind, TokenType::Length) {
4912 self.advance(); return self.parse_primary_expr();
4914 }
4915 }
4916 if let Some(next) = self.tokens.get(self.current + 1) {
4918 if matches!(next.kind, TokenType::New) {
4919 self.advance(); self.advance(); let base_type_name = self.expect_identifier()?;
4922
4923 let type_name = if self.check(&TokenType::From) {
4925 self.advance(); let module_name = self.expect_identifier()?;
4927 let module_str = self.interner.resolve(module_name);
4928 let base_str = self.interner.resolve(base_type_name);
4929 let qualified = format!("{}::{}", module_str, base_str);
4930 self.interner.intern(&qualified)
4931 } else {
4932 base_type_name
4933 };
4934
4935 if let Some(enum_name) = self.find_variant(type_name) {
4937 let fields = if self.check_word("with") {
4939 self.parse_variant_constructor_fields()?
4940 } else {
4941 vec![]
4942 };
4943 let base = self.ctx.alloc_imperative_expr(Expr::NewVariant {
4944 enum_name,
4945 variant: type_name,
4946 fields,
4947 });
4948 return self.parse_field_access_chain(base);
4949 }
4950
4951 let type_args = self.parse_generic_type_args(type_name)?;
4953
4954 let init_fields = if self.check_word("with") && !self.peek_word_at(1, "capacity") {
4957 self.parse_struct_init_fields()?
4958 } else {
4959 vec![]
4960 };
4961
4962 let base = self.ctx.alloc_imperative_expr(Expr::New { type_name, type_args, init_fields });
4963 return self.parse_field_access_chain(base);
4964 }
4965 }
4966 let sym = token.lexeme;
4968 self.advance();
4969 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
4970 return self.parse_field_access_chain(base);
4971 }
4972
4973 TokenType::Item => {
4975 self.advance(); let index = if let TokenType::Number(sym) = &self.peek().kind {
4979 let sym = *sym;
4981 self.advance();
4982 let num_str = self.interner.resolve(sym);
4983 let index_val = num_str.parse::<i64>().unwrap_or(0);
4984
4985 if index_val == 0 {
4987 return Err(ParseError {
4988 kind: ParseErrorKind::ZeroIndex,
4989 span: self.current_span(),
4990 });
4991 }
4992
4993 self.ctx.alloc_imperative_expr(
4994 Expr::Literal(crate::ast::Literal::Number(index_val))
4995 )
4996 } else if self.check(&TokenType::LParen) {
4997 self.advance(); let inner = self.parse_imperative_expr()?;
5000 if !self.check(&TokenType::RParen) {
5001 return Err(ParseError {
5002 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
5003 span: self.current_span(),
5004 });
5005 }
5006 self.advance(); inner
5008 } else if let TokenType::StringLiteral(sym) = self.peek().kind {
5009 let sym = sym;
5011 self.advance();
5012 self.ctx.alloc_imperative_expr(Expr::Literal(crate::ast::Literal::Text(sym)))
5013 } else if !self.check_preposition_is("of") {
5014 let word = self.interner.resolve(self.peek().lexeme);
5016 if word == "true" {
5017 self.advance();
5018 self.ctx.alloc_imperative_expr(Expr::Literal(crate::ast::Literal::Boolean(true)))
5019 } else if word == "false" {
5020 self.advance();
5021 self.ctx.alloc_imperative_expr(Expr::Literal(crate::ast::Literal::Boolean(false)))
5022 } else {
5023 let sym = self.peek().lexeme;
5025 self.advance();
5026 self.ctx.alloc_imperative_expr(Expr::Identifier(sym))
5027 }
5028 } else {
5029 return Err(ParseError {
5030 kind: ParseErrorKind::ExpectedExpression,
5031 span: self.current_span(),
5032 });
5033 };
5034
5035 if !self.check_preposition_is("of") {
5037 return Err(ParseError {
5038 kind: ParseErrorKind::ExpectedKeyword { keyword: "of".to_string() },
5039 span: self.current_span(),
5040 });
5041 }
5042 self.advance(); let collection = self.parse_primary_expr()?;
5047
5048 Ok(self.ctx.alloc_imperative_expr(Expr::Index {
5049 collection,
5050 index,
5051 }))
5052 }
5053
5054 TokenType::Items => {
5057 let is_slice_syntax = if let Some(next) = self.tokens.get(self.current + 1) {
5061 matches!(next.kind, TokenType::Number(_) | TokenType::LParen)
5062 } else {
5063 false
5064 };
5065
5066 if !is_slice_syntax {
5067 let sym = token.lexeme;
5069 self.advance();
5070 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5071 return self.parse_field_access_chain(base);
5072 }
5073
5074 self.advance(); let start = if let TokenType::Number(sym) = &self.peek().kind {
5078 let sym = *sym;
5080 self.advance();
5081 let num_str = self.interner.resolve(sym);
5082 let start_val = num_str.parse::<i64>().unwrap_or(0);
5083
5084 if start_val == 0 {
5086 return Err(ParseError {
5087 kind: ParseErrorKind::ZeroIndex,
5088 span: self.current_span(),
5089 });
5090 }
5091
5092 self.ctx.alloc_imperative_expr(
5093 Expr::Literal(crate::ast::Literal::Number(start_val))
5094 )
5095 } else if self.check(&TokenType::LParen) {
5096 self.advance(); let inner = self.parse_imperative_expr()?;
5099 if !self.check(&TokenType::RParen) {
5100 return Err(ParseError {
5101 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
5102 span: self.current_span(),
5103 });
5104 }
5105 self.advance(); inner
5107 } else if !self.check_preposition_is("through") {
5108 let sym = self.peek().lexeme;
5110 self.advance();
5111 self.ctx.alloc_imperative_expr(Expr::Identifier(sym))
5112 } else {
5113 return Err(ParseError {
5114 kind: ParseErrorKind::ExpectedExpression,
5115 span: self.current_span(),
5116 });
5117 };
5118
5119 if !self.check_preposition_is("through") {
5121 return Err(ParseError {
5122 kind: ParseErrorKind::ExpectedKeyword { keyword: "through".to_string() },
5123 span: self.current_span(),
5124 });
5125 }
5126 self.advance(); let end = if let TokenType::Number(sym) = &self.peek().kind {
5130 let sym = *sym;
5132 self.advance();
5133 let num_str = self.interner.resolve(sym);
5134 let end_val = num_str.parse::<i64>().unwrap_or(0);
5135
5136 if end_val == 0 {
5138 return Err(ParseError {
5139 kind: ParseErrorKind::ZeroIndex,
5140 span: self.current_span(),
5141 });
5142 }
5143
5144 self.ctx.alloc_imperative_expr(
5145 Expr::Literal(crate::ast::Literal::Number(end_val))
5146 )
5147 } else if self.check(&TokenType::LParen) {
5148 self.advance(); let inner = self.parse_imperative_expr()?;
5151 if !self.check(&TokenType::RParen) {
5152 return Err(ParseError {
5153 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
5154 span: self.current_span(),
5155 });
5156 }
5157 self.advance(); inner
5159 } else if !self.check_preposition_is("of") {
5160 let sym = self.peek().lexeme;
5162 self.advance();
5163 self.ctx.alloc_imperative_expr(Expr::Identifier(sym))
5164 } else {
5165 return Err(ParseError {
5166 kind: ParseErrorKind::ExpectedExpression,
5167 span: self.current_span(),
5168 });
5169 };
5170
5171 let collection = if self.check_preposition_is("of") {
5174 self.advance(); self.parse_imperative_expr()?
5176 } else {
5177 let items_sym = self.interner.intern("items");
5180 self.ctx.alloc_imperative_expr(Expr::Identifier(items_sym))
5181 };
5182
5183 Ok(self.ctx.alloc_imperative_expr(Expr::Slice {
5184 collection,
5185 start,
5186 end,
5187 }))
5188 }
5189
5190 TokenType::LBracket => {
5192 self.advance(); let mut items = Vec::new();
5195 if !self.check(&TokenType::RBracket) {
5196 loop {
5197 items.push(self.parse_imperative_expr()?);
5198 if !self.check(&TokenType::Comma) {
5199 break;
5200 }
5201 self.advance(); }
5203 }
5204
5205 if !self.check(&TokenType::RBracket) {
5206 return Err(ParseError {
5207 kind: ParseErrorKind::ExpectedKeyword { keyword: "]".to_string() },
5208 span: self.current_span(),
5209 });
5210 }
5211 self.advance(); if items.is_empty() && self.check_word("of") {
5215 self.advance(); let type_name = self.expect_identifier()?;
5217 let seq_sym = self.interner.intern("Seq");
5219 return Ok(self.ctx.alloc_imperative_expr(Expr::New {
5220 type_name: seq_sym,
5221 type_args: vec![TypeExpr::Named(type_name)],
5222 init_fields: vec![],
5223 }));
5224 }
5225
5226 Ok(self.ctx.alloc_imperative_expr(Expr::List(items)))
5227 }
5228
5229 TokenType::Number(sym) => {
5230 let num_str = self.interner.resolve(*sym).to_string();
5231 self.advance();
5232
5233 if let TokenType::CalendarUnit(unit) = self.peek().kind {
5235 return self.parse_span_literal_from_num(&num_str);
5236 }
5237
5238 if num_str.contains('.') {
5240 let num = num_str.parse::<f64>().unwrap_or(0.0);
5241 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Float(num))))
5242 } else {
5243 let num = num_str.parse::<i64>().unwrap_or(0);
5244 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Number(num))))
5245 }
5246 }
5247
5248 TokenType::StringLiteral(sym) => {
5250 self.advance();
5251 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Text(*sym))))
5252 }
5253
5254 TokenType::CharLiteral(sym) => {
5256 let char_str = self.interner.resolve(*sym);
5257 let ch = char_str.chars().next().unwrap_or('\0');
5258 self.advance();
5259 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Char(ch))))
5260 }
5261
5262 TokenType::DurationLiteral { nanos, .. } => {
5264 let nanos = *nanos;
5265 self.advance();
5266 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Duration(nanos))))
5267 }
5268
5269 TokenType::DateLiteral { days } => {
5272 let days = *days;
5273 self.advance();
5274
5275 if self.check(&TokenType::At) {
5277 self.advance(); if let TokenType::TimeLiteral { nanos_from_midnight } = self.peek().kind {
5281 let time_nanos = nanos_from_midnight;
5282 self.advance(); let moment_nanos = (days as i64) * 86_400_000_000_000 + time_nanos;
5286 return Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Moment(moment_nanos))));
5287 } else {
5288 return Err(ParseError {
5289 kind: ParseErrorKind::ExpectedExpression,
5290 span: self.current_span(),
5291 });
5292 }
5293 }
5294
5295 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Date(days))))
5296 }
5297
5298 TokenType::TimeLiteral { nanos_from_midnight } => {
5300 let nanos = *nanos_from_midnight;
5301 self.advance();
5302 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Time(nanos))))
5303 }
5304
5305 TokenType::Nothing => {
5307 self.advance();
5308 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Nothing)))
5309 }
5310
5311 TokenType::Some => {
5313 self.advance(); let value = self.parse_imperative_expr()?;
5315 Ok(self.ctx.alloc_imperative_expr(Expr::OptionSome { value }))
5316 }
5317
5318 TokenType::Length => {
5320 let func_name = self.peek().lexeme;
5321
5322 if self.tokens.get(self.current + 1)
5324 .map(|t| matches!(t.kind, TokenType::LParen))
5325 .unwrap_or(false)
5326 {
5327 self.advance(); return self.parse_call_expr(func_name);
5329 }
5330
5331 self.advance(); if !self.check_preposition_is("of") {
5335 return Err(ParseError {
5336 kind: ParseErrorKind::ExpectedKeyword { keyword: "of".to_string() },
5337 span: self.current_span(),
5338 });
5339 }
5340 self.advance(); let collection = self.parse_imperative_expr()?;
5343 Ok(self.ctx.alloc_imperative_expr(Expr::Length { collection }))
5344 }
5345
5346 TokenType::Copy => {
5348 let func_name = self.peek().lexeme;
5349
5350 if self.tokens.get(self.current + 1)
5352 .map(|t| matches!(t.kind, TokenType::LParen))
5353 .unwrap_or(false)
5354 {
5355 self.advance(); return self.parse_call_expr(func_name);
5357 }
5358
5359 self.advance(); if !self.check_preposition_is("of") {
5363 return Err(ParseError {
5364 kind: ParseErrorKind::ExpectedKeyword { keyword: "of".to_string() },
5365 span: self.current_span(),
5366 });
5367 }
5368 self.advance(); let expr = self.parse_imperative_expr()?;
5371 Ok(self.ctx.alloc_imperative_expr(Expr::Copy { expr }))
5372 }
5373
5374 TokenType::Manifest => {
5376 self.advance(); if !self.check_preposition_is("of") {
5380 return Err(ParseError {
5381 kind: ParseErrorKind::ExpectedKeyword { keyword: "of".to_string() },
5382 span: self.current_span(),
5383 });
5384 }
5385 self.advance(); let zone = self.parse_imperative_expr()?;
5388 Ok(self.ctx.alloc_imperative_expr(Expr::ManifestOf { zone }))
5389 }
5390
5391 TokenType::Chunk => {
5393 self.advance(); if !self.check(&TokenType::At) {
5397 return Err(ParseError {
5398 kind: ParseErrorKind::ExpectedKeyword { keyword: "at".to_string() },
5399 span: self.current_span(),
5400 });
5401 }
5402 self.advance(); let index = self.parse_imperative_expr()?;
5405
5406 if !self.check_preposition_is("in") && !self.check(&TokenType::In) {
5408 return Err(ParseError {
5409 kind: ParseErrorKind::ExpectedKeyword { keyword: "in".to_string() },
5410 span: self.current_span(),
5411 });
5412 }
5413 self.advance(); let zone = self.parse_imperative_expr()?;
5416 Ok(self.ctx.alloc_imperative_expr(Expr::ChunkAt { index, zone }))
5417 }
5418
5419 TokenType::Verb { lemma, .. } => {
5423 let word = self.interner.resolve(*lemma).to_lowercase();
5424 if word == "empty" {
5425 self.advance();
5426 return Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Nothing)));
5427 }
5428 let sym = token.lexeme;
5430 self.advance();
5431 if self.check(&TokenType::LParen) {
5432 return self.parse_call_expr(sym);
5433 }
5434 self.verify_identifier_access(sym)?;
5436 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5437 self.parse_field_access_chain(base)
5438 }
5439
5440 TokenType::TemporalAdverb(_) | TokenType::ScopalAdverb(_) | TokenType::Adverb(_) => {
5442 let sym = token.lexeme;
5443 self.advance();
5444 if self.check(&TokenType::LParen) {
5445 return self.parse_call_expr(sym);
5446 }
5447 self.verify_identifier_access(sym)?;
5449 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5450 self.parse_field_access_chain(base)
5451 }
5452
5453 TokenType::Read | TokenType::Write | TokenType::File | TokenType::Console |
5456 TokenType::Add | TokenType::Remove => {
5457 let sym = token.lexeme;
5458 self.advance();
5459 if self.check(&TokenType::LParen) {
5460 return self.parse_call_expr(sym);
5461 }
5462 self.verify_identifier_access(sym)?;
5464 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5465 self.parse_field_access_chain(base)
5466 }
5467
5468 TokenType::Noun(sym) | TokenType::ProperName(sym) | TokenType::Adjective(sym) => {
5471 let sym = *sym;
5472 let word = self.interner.resolve(sym);
5473
5474 if word == "true" {
5476 self.advance();
5477 return Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Boolean(true))));
5478 }
5479 if word == "false" {
5480 self.advance();
5481 return Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Boolean(false))));
5482 }
5483
5484 if word == "empty" {
5486 self.advance();
5487 return Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Nothing)));
5488 }
5489
5490 if word == "none" {
5492 self.advance();
5493 return Ok(self.ctx.alloc_imperative_expr(Expr::OptionNone));
5494 }
5495
5496 self.advance();
5498
5499 if self.check(&TokenType::LParen) {
5501 return self.parse_call_expr(sym);
5502 }
5503
5504 if let Some(enum_name) = self.find_variant(sym) {
5506 let fields = if self.check_word("with") {
5507 self.parse_variant_constructor_fields()?
5508 } else {
5509 vec![]
5510 };
5511 let base = self.ctx.alloc_imperative_expr(Expr::NewVariant {
5512 enum_name,
5513 variant: sym,
5514 fields,
5515 });
5516 return self.parse_field_access_chain(base);
5517 }
5518
5519 self.verify_identifier_access(sym)?;
5521 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5522 self.parse_field_access_chain(base)
5524 }
5525
5526 TokenType::Pronoun { .. } => {
5528 let sym = token.lexeme;
5529 self.advance();
5530 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5531 self.parse_field_access_chain(base)
5533 }
5534
5535 TokenType::Merge | TokenType::Increase => {
5537 let sym = token.lexeme;
5538 self.advance();
5539
5540 if self.check(&TokenType::LParen) {
5542 return self.parse_call_expr(sym);
5543 }
5544
5545 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5546 self.parse_field_access_chain(base)
5547 }
5548
5549 TokenType::Escape => {
5553 if self.tokens.get(self.current + 1).map_or(false, |t|
5554 matches!(t.kind, TokenType::To) || {
5555 if let TokenType::Preposition(sym) = t.kind {
5556 sym.is(self.interner, "to")
5557 } else {
5558 false
5559 }
5560 }
5561 ) {
5562 return self.parse_escape_expr();
5563 }
5564 let sym = token.lexeme;
5566 self.advance();
5567 if self.check(&TokenType::LParen) {
5568 return self.parse_call_expr(sym);
5569 }
5570 self.verify_identifier_access(sym)?;
5571 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5572 self.parse_field_access_chain(base)
5573 }
5574
5575 TokenType::Values | TokenType::Both | TokenType::Either | TokenType::Combined | TokenType::Shared => { let sym = token.lexeme;
5584 self.advance();
5585
5586 if self.check(&TokenType::LParen) {
5588 return self.parse_call_expr(sym);
5589 }
5590
5591 self.verify_identifier_access(sym)?;
5592 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5593 self.parse_field_access_chain(base)
5594 }
5595
5596 TokenType::Ambiguous { primary, alternatives } => {
5598 let sym = token.lexeme;
5601
5602 let is_identifier_token = match &**primary {
5604 TokenType::Noun(_) | TokenType::Adjective(_) | TokenType::ProperName(_) |
5605 TokenType::Verb { .. } => true,
5606 _ => alternatives.iter().any(|t| matches!(t,
5607 TokenType::Noun(_) | TokenType::Adjective(_) | TokenType::ProperName(_) |
5608 TokenType::Verb { .. }
5609 ))
5610 };
5611
5612 if is_identifier_token {
5613 self.advance();
5614
5615 if self.check(&TokenType::LParen) {
5617 return self.parse_call_expr(sym);
5618 }
5619
5620 self.verify_identifier_access(sym)?;
5621 let base = self.ctx.alloc_imperative_expr(Expr::Identifier(sym));
5622 self.parse_field_access_chain(base)
5624 } else {
5625 Err(ParseError {
5626 kind: ParseErrorKind::ExpectedExpression,
5627 span: self.current_span(),
5628 })
5629 }
5630 }
5631
5632 TokenType::LParen => {
5634 if let Some(closure) = self.try_parse(|p| p.parse_closure_expr()) {
5637 return Ok(closure);
5638 }
5639
5640 self.advance(); let first = self.parse_imperative_expr()?;
5643
5644 if self.check(&TokenType::Comma) {
5646 let mut items = vec![first];
5648 while self.check(&TokenType::Comma) {
5649 self.advance(); items.push(self.parse_imperative_expr()?);
5651 }
5652
5653 if !self.check(&TokenType::RParen) {
5654 return Err(ParseError {
5655 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
5656 span: self.current_span(),
5657 });
5658 }
5659 self.advance(); let base = self.ctx.alloc_imperative_expr(Expr::Tuple(items));
5662 self.parse_field_access_chain(base)
5663 } else {
5664 if !self.check(&TokenType::RParen) {
5666 return Err(ParseError {
5667 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
5668 span: self.current_span(),
5669 });
5670 }
5671 self.advance(); Ok(first)
5673 }
5674 }
5675
5676 TokenType::Call => {
5678 self.advance(); let function = match &self.peek().kind {
5680 TokenType::Noun(sym) | TokenType::Adjective(sym) => {
5681 let s = *sym;
5682 self.advance();
5683 s
5684 }
5685 TokenType::Verb { .. } | TokenType::Ambiguous { .. } => {
5686 let s = self.peek().lexeme;
5687 self.advance();
5688 s
5689 }
5690 _ => {
5691 return Err(ParseError {
5692 kind: ParseErrorKind::ExpectedIdentifier,
5693 span: self.current_span(),
5694 });
5695 }
5696 };
5697 let args = if self.check_preposition_is("with") {
5698 self.advance(); self.parse_call_arguments()?
5700 } else {
5701 Vec::new()
5702 };
5703 Ok(self.ctx.alloc_imperative_expr(Expr::Call { function, args }))
5704 }
5705
5706 _ => {
5707 Err(ParseError {
5708 kind: ParseErrorKind::ExpectedExpression,
5709 span: self.current_span(),
5710 })
5711 }
5712 }
5713 }
5714
5715 fn parse_closure_expr(&mut self) -> ParseResult<&'a Expr<'a>> {
5718 use crate::ast::stmt::ClosureBody;
5719
5720 if !self.check(&TokenType::LParen) {
5722 return Err(ParseError {
5723 kind: ParseErrorKind::ExpectedExpression,
5724 span: self.current_span(),
5725 });
5726 }
5727 self.advance(); let mut params = Vec::new();
5731 if !self.check(&TokenType::RParen) {
5732 let name = self.expect_identifier()?;
5734 if !self.check(&TokenType::Colon) {
5735 return Err(ParseError {
5736 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
5737 span: self.current_span(),
5738 });
5739 }
5740 self.advance(); let ty = self.parse_type_expression()?;
5742 let ty_ref = self.ctx.alloc_type_expr(ty);
5743 params.push((name, ty_ref));
5744
5745 while self.check(&TokenType::Comma) {
5747 self.advance(); let name = self.expect_identifier()?;
5749 if !self.check(&TokenType::Colon) {
5750 return Err(ParseError {
5751 kind: ParseErrorKind::ExpectedKeyword { keyword: ":".to_string() },
5752 span: self.current_span(),
5753 });
5754 }
5755 self.advance(); let ty = self.parse_type_expression()?;
5757 let ty_ref = self.ctx.alloc_type_expr(ty);
5758 params.push((name, ty_ref));
5759 }
5760 }
5761
5762 if !self.check(&TokenType::RParen) {
5764 return Err(ParseError {
5765 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
5766 span: self.current_span(),
5767 });
5768 }
5769 self.advance(); if !self.check(&TokenType::Arrow) {
5773 return Err(ParseError {
5774 kind: ParseErrorKind::ExpectedKeyword { keyword: "->".to_string() },
5775 span: self.current_span(),
5776 });
5777 }
5778 self.advance(); let body = if self.check(&TokenType::Colon) {
5782 self.advance(); if !self.check(&TokenType::Indent) {
5785 return Err(ParseError {
5786 kind: ParseErrorKind::ExpectedStatement,
5787 span: self.current_span(),
5788 });
5789 }
5790 self.advance(); let mut block_stmts = Vec::new();
5793 while !self.check(&TokenType::Dedent) && !self.is_at_end() {
5794 let stmt = self.parse_statement()?;
5795 block_stmts.push(stmt);
5796 if self.check(&TokenType::Period) {
5797 self.advance();
5798 }
5799 }
5800 if self.check(&TokenType::Dedent) {
5801 self.advance(); }
5803
5804 let block = self.ctx.stmts.expect("imperative arenas not initialized")
5805 .alloc_slice(block_stmts.into_iter());
5806 ClosureBody::Block(block)
5807 } else {
5808 let expr = self.parse_condition()?;
5810 ClosureBody::Expression(expr)
5811 };
5812
5813 Ok(self.ctx.alloc_imperative_expr(Expr::Closure {
5814 params,
5815 body,
5816 return_type: None,
5817 }))
5818 }
5819
5820 fn parse_imperative_expr(&mut self) -> ParseResult<&'a Expr<'a>> {
5823 self.parse_additive_expr()
5824 }
5825
5826 fn parse_additive_expr(&mut self) -> ParseResult<&'a Expr<'a>> {
5828 let mut left = self.parse_multiplicative_expr()?;
5829
5830 loop {
5831 match &self.peek().kind {
5832 TokenType::Plus => {
5833 self.advance();
5834 let right = self.parse_multiplicative_expr()?;
5835 left = self.ctx.alloc_imperative_expr(Expr::BinaryOp {
5836 op: BinaryOpKind::Add,
5837 left,
5838 right,
5839 });
5840 }
5841 TokenType::Minus => {
5842 self.advance();
5843 let right = self.parse_multiplicative_expr()?;
5844 left = self.ctx.alloc_imperative_expr(Expr::BinaryOp {
5845 op: BinaryOpKind::Subtract,
5846 left,
5847 right,
5848 });
5849 }
5850 TokenType::Combined => {
5852 self.advance(); if !self.check_preposition_is("with") {
5855 return Err(ParseError {
5856 kind: ParseErrorKind::ExpectedKeyword { keyword: "with".to_string() },
5857 span: self.current_span(),
5858 });
5859 }
5860 self.advance(); let right = self.parse_multiplicative_expr()?;
5862 left = self.ctx.alloc_imperative_expr(Expr::BinaryOp {
5863 op: BinaryOpKind::Concat,
5864 left,
5865 right,
5866 });
5867 }
5868 TokenType::Union => {
5870 self.advance(); let right = self.parse_multiplicative_expr()?;
5872 left = self.ctx.alloc_imperative_expr(Expr::Union {
5873 left,
5874 right,
5875 });
5876 }
5877 TokenType::Intersection => {
5878 self.advance(); let right = self.parse_multiplicative_expr()?;
5880 left = self.ctx.alloc_imperative_expr(Expr::Intersection {
5881 left,
5882 right,
5883 });
5884 }
5885 TokenType::Contains => {
5887 self.advance(); let value = self.parse_multiplicative_expr()?;
5889 left = self.ctx.alloc_imperative_expr(Expr::Contains {
5890 collection: left,
5891 value,
5892 });
5893 }
5894 _ => break,
5895 }
5896 }
5897
5898 Ok(left)
5899 }
5900
5901 fn parse_unary_expr(&mut self) -> ParseResult<&'a Expr<'a>> {
5903 use crate::ast::{Expr, Literal};
5904
5905 if self.check(&TokenType::Minus) {
5906 self.advance(); let operand = self.parse_unary_expr()?; return Ok(self.ctx.alloc_imperative_expr(Expr::BinaryOp {
5910 op: BinaryOpKind::Subtract,
5911 left: self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Number(0))),
5912 right: operand,
5913 }));
5914 }
5915 self.parse_primary_expr()
5916 }
5917
5918 fn parse_multiplicative_expr(&mut self) -> ParseResult<&'a Expr<'a>> {
5920 let mut left = self.parse_unary_expr()?;
5921
5922 loop {
5923 let op = match &self.peek().kind {
5924 TokenType::Star => {
5925 self.advance();
5926 BinaryOpKind::Multiply
5927 }
5928 TokenType::Slash => {
5929 self.advance();
5930 BinaryOpKind::Divide
5931 }
5932 TokenType::Percent => {
5933 self.advance();
5934 BinaryOpKind::Modulo
5935 }
5936 _ => break,
5937 };
5938 let right = self.parse_unary_expr()?;
5939 left = self.ctx.alloc_imperative_expr(Expr::BinaryOp {
5940 op,
5941 left,
5942 right,
5943 });
5944 }
5945
5946 Ok(left)
5947 }
5948
5949 fn try_parse_binary_op(&mut self) -> Option<BinaryOpKind> {
5951 match &self.peek().kind {
5952 TokenType::Plus => {
5953 self.advance();
5954 Some(BinaryOpKind::Add)
5955 }
5956 TokenType::Minus => {
5957 self.advance();
5958 Some(BinaryOpKind::Subtract)
5959 }
5960 TokenType::Star => {
5961 self.advance();
5962 Some(BinaryOpKind::Multiply)
5963 }
5964 TokenType::Slash => {
5965 self.advance();
5966 Some(BinaryOpKind::Divide)
5967 }
5968 _ => None,
5969 }
5970 }
5971
5972 fn parse_span_literal_from_num(&mut self, first_num_str: &str) -> ParseResult<&'a Expr<'a>> {
5975 use crate::ast::Literal;
5976 use crate::token::CalendarUnit;
5977
5978 let first_num = first_num_str.parse::<i32>().unwrap_or(0);
5979
5980 let unit = match self.peek().kind {
5982 TokenType::CalendarUnit(u) => u,
5983 _ => {
5984 return Err(ParseError {
5985 kind: ParseErrorKind::ExpectedKeyword { keyword: "calendar unit (day, week, month, year)".to_string() },
5986 span: self.current_span(),
5987 });
5988 }
5989 };
5990 self.advance(); let mut total_months: i32 = 0;
5994 let mut total_days: i32 = 0;
5995
5996 match unit {
5998 CalendarUnit::Day => total_days += first_num,
5999 CalendarUnit::Week => total_days += first_num * 7,
6000 CalendarUnit::Month => total_months += first_num,
6001 CalendarUnit::Year => total_months += first_num * 12,
6002 }
6003
6004 while self.check(&TokenType::And) {
6006 self.advance(); let next_num = match &self.peek().kind {
6010 TokenType::Number(sym) => {
6011 let num_str = self.interner.resolve(*sym).to_string();
6012 self.advance();
6013 num_str.parse::<i32>().unwrap_or(0)
6014 }
6015 _ => break, };
6017
6018 let next_unit = match self.peek().kind {
6020 TokenType::CalendarUnit(u) => {
6021 self.advance();
6022 u
6023 }
6024 _ => break, };
6026
6027 match next_unit {
6029 CalendarUnit::Day => total_days += next_num,
6030 CalendarUnit::Week => total_days += next_num * 7,
6031 CalendarUnit::Month => total_months += next_num,
6032 CalendarUnit::Year => total_months += next_num * 12,
6033 }
6034 }
6035
6036 Ok(self.ctx.alloc_imperative_expr(Expr::Literal(Literal::Span {
6037 months: total_months,
6038 days: total_days,
6039 })))
6040 }
6041
6042 fn parse_call_expr(&mut self, function: Symbol) -> ParseResult<&'a Expr<'a>> {
6044 use crate::ast::Expr;
6045
6046 self.advance(); let mut args = Vec::new();
6049 if !self.check(&TokenType::RParen) {
6050 loop {
6051 args.push(self.parse_imperative_expr()?);
6052 if !self.check(&TokenType::Comma) {
6053 break;
6054 }
6055 self.advance(); }
6057 }
6058
6059 if !self.check(&TokenType::RParen) {
6060 return Err(ParseError {
6061 kind: ParseErrorKind::ExpectedKeyword { keyword: ")".to_string() },
6062 span: self.current_span(),
6063 });
6064 }
6065 self.advance(); Ok(self.ctx.alloc_imperative_expr(Expr::Call { function, args }))
6068 }
6069
6070 fn parse_field_access_chain(&mut self, base: &'a Expr<'a>) -> ParseResult<&'a Expr<'a>> {
6073 use crate::ast::Expr;
6074
6075 let mut result = base;
6076
6077 loop {
6079 if self.check(&TokenType::Possessive) {
6080 self.advance(); let field = self.expect_identifier()?;
6083 result = self.ctx.alloc_imperative_expr(Expr::FieldAccess {
6084 object: result,
6085 field,
6086 });
6087 } else if self.check(&TokenType::LBracket) {
6088 self.advance(); let index = self.parse_imperative_expr()?;
6091
6092 if !self.check(&TokenType::RBracket) {
6093 return Err(ParseError {
6094 kind: ParseErrorKind::ExpectedKeyword { keyword: "]".to_string() },
6095 span: self.current_span(),
6096 });
6097 }
6098 self.advance(); result = self.ctx.alloc_imperative_expr(Expr::Index {
6101 collection: result,
6102 index,
6103 });
6104 } else {
6105 break;
6106 }
6107 }
6108
6109 Ok(result)
6110 }
6111
6112 fn verify_identifier_access(&self, sym: Symbol) -> ParseResult<()> {
6115 if self.mode != ParserMode::Imperative {
6116 return Ok(());
6117 }
6118
6119 if let Some(crate::drs::OwnershipState::Moved) = self.world_state.get_ownership_by_var(sym) {
6121 return Err(ParseError {
6122 kind: ParseErrorKind::UseAfterMove {
6123 name: self.interner.resolve(sym).to_string()
6124 },
6125 span: self.current_span(),
6126 });
6127 }
6128
6129 Ok(())
6130 }
6131
6132 fn expect_identifier(&mut self) -> ParseResult<Symbol> {
6133 let token = self.peek().clone();
6134 match &token.kind {
6135 TokenType::Noun(sym) | TokenType::ProperName(sym) | TokenType::Adjective(sym) => {
6137 self.advance();
6138 Ok(*sym)
6139 }
6140 TokenType::Verb { .. } => {
6143 let sym = token.lexeme;
6144 self.advance();
6145 Ok(sym)
6146 }
6147 TokenType::Article(_) => {
6149 let sym = token.lexeme;
6150 self.advance();
6151 Ok(sym)
6152 }
6153 TokenType::Pronoun { .. } | TokenType::Items | TokenType::Values | TokenType::Item | TokenType::Nothing | TokenType::TemporalAdverb(_) |
6161 TokenType::ScopalAdverb(_) |
6162 TokenType::Adverb(_) |
6163 TokenType::Read |
6165 TokenType::Write |
6166 TokenType::File |
6167 TokenType::Console |
6168 TokenType::Merge |
6170 TokenType::Increase |
6171 TokenType::Decrease |
6172 TokenType::Tally |
6174 TokenType::SharedSet |
6175 TokenType::SharedSequence |
6176 TokenType::CollaborativeSequence |
6177 TokenType::Add |
6180 TokenType::Remove |
6181 TokenType::First |
6182 TokenType::Both | TokenType::Either | TokenType::Combined | TokenType::Shared | TokenType::CalendarUnit(_) |
6189 TokenType::Focus(_) |
6191 TokenType::Escape => {
6193 let sym = token.lexeme;
6195 self.advance();
6196 Ok(sym)
6197 }
6198 TokenType::Ambiguous { .. } => {
6199 let sym = token.lexeme;
6202 self.advance();
6203 Ok(sym)
6204 }
6205 _ => Err(ParseError {
6206 kind: ParseErrorKind::ExpectedIdentifier,
6207 span: self.current_span(),
6208 }),
6209 }
6210 }
6211
6212 fn consume_content_word_for_relative(&mut self) -> ParseResult<Symbol> {
6213 let t = self.advance().clone();
6214 match t.kind {
6215 TokenType::Noun(s) | TokenType::Adjective(s) => Ok(s),
6216 TokenType::ProperName(s) => Ok(s),
6217 TokenType::Verb { lemma, .. } => Ok(lemma),
6218 other => Err(ParseError {
6219 kind: ParseErrorKind::ExpectedContentWord { found: other },
6220 span: self.current_span(),
6221 }),
6222 }
6223 }
6224
6225 fn check_modal(&self) -> bool {
6226 matches!(
6227 self.peek().kind,
6228 TokenType::Must
6229 | TokenType::Shall
6230 | TokenType::Should
6231 | TokenType::Can
6232 | TokenType::May
6233 | TokenType::Cannot
6234 | TokenType::Could
6235 | TokenType::Would
6236 | TokenType::Might
6237 )
6238 }
6239
6240 fn check_pronoun(&self) -> bool {
6241 match &self.peek().kind {
6242 TokenType::Pronoun { case, .. } => {
6243 if self.noun_priority_mode && matches!(case, Case::Possessive) {
6245 return false;
6246 }
6247 true
6248 }
6249 TokenType::Ambiguous { primary, alternatives } => {
6250 if self.noun_priority_mode {
6252 let has_possessive = matches!(**primary, TokenType::Pronoun { case: Case::Possessive, .. })
6253 || alternatives.iter().any(|t| matches!(t, TokenType::Pronoun { case: Case::Possessive, .. }));
6254 if has_possessive {
6255 return false;
6256 }
6257 }
6258 matches!(**primary, TokenType::Pronoun { .. })
6259 || alternatives.iter().any(|t| matches!(t, TokenType::Pronoun { .. }))
6260 }
6261 _ => false,
6262 }
6263 }
6264
6265 fn parse_atom(&mut self) -> ParseResult<&'a LogicExpr<'a>> {
6266 if self.check_focus() {
6268 return self.parse_focus();
6269 }
6270
6271 if self.check_measure() {
6273 return self.parse_measure();
6274 }
6275
6276 if self.check_quantifier() {
6277 self.advance();
6278 return self.parse_quantified();
6279 }
6280
6281 if self.check_npi_quantifier() {
6282 return self.parse_npi_quantified();
6283 }
6284
6285 if self.check_temporal_npi() {
6286 return self.parse_temporal_npi();
6287 }
6288
6289 if self.match_token(&[TokenType::LParen]) {
6290 let expr = self.parse_sentence()?;
6291 self.consume(TokenType::RParen)?;
6292 return Ok(expr);
6293 }
6294
6295 if self.check_pronoun() {
6297 let token = self.advance().clone();
6298 let (gender, number) = match &token.kind {
6299 TokenType::Pronoun { gender, number, .. } => (*gender, *number),
6300 TokenType::Ambiguous { primary, alternatives } => {
6301 if let TokenType::Pronoun { gender, number, .. } = **primary {
6302 (gender, number)
6303 } else {
6304 alternatives.iter().find_map(|t| {
6305 if let TokenType::Pronoun { gender, number, .. } = t {
6306 Some((*gender, *number))
6307 } else {
6308 None
6309 }
6310 }).unwrap_or((Gender::Unknown, Number::Singular))
6311 }
6312 }
6313 _ => (Gender::Unknown, Number::Singular),
6314 };
6315
6316 let token_text = self.interner.resolve(token.lexeme);
6317
6318 if token_text.eq_ignore_ascii_case("it") && self.check_verb() {
6321 if let TokenType::Verb { lemma, time, .. } = &self.peek().kind {
6322 let lemma_str = self.interner.resolve(*lemma);
6323 if Lexer::is_weather_verb(lemma_str) {
6324 let verb = *lemma;
6325 let verb_time = *time;
6326 self.advance(); let event_var = self.get_event_var();
6329 let suppress_existential = self.drs.in_conditional_antecedent();
6330 if suppress_existential {
6331 let event_class = self.interner.intern("Event");
6332 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
6333 }
6334 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
6335 event_var,
6336 verb,
6337 roles: self.ctx.roles.alloc_slice(vec![]), modifiers: self.ctx.syms.alloc_slice(vec![]),
6339 suppress_existential,
6340 world: None,
6341 })));
6342
6343 return Ok(match verb_time {
6344 Time::Past => self.ctx.exprs.alloc(LogicExpr::Temporal {
6345 operator: TemporalOperator::Past,
6346 body: neo_event,
6347 }),
6348 Time::Future => self.ctx.exprs.alloc(LogicExpr::Temporal {
6349 operator: TemporalOperator::Future,
6350 body: neo_event,
6351 }),
6352 _ => neo_event,
6353 });
6354 }
6355 }
6356 }
6357
6358 let resolved = if token_text.eq_ignore_ascii_case("i") {
6360 ResolvedPronoun::Constant(self.interner.intern("Speaker"))
6361 } else if token_text.eq_ignore_ascii_case("you") {
6362 ResolvedPronoun::Constant(self.interner.intern("Addressee"))
6363 } else {
6364 self.resolve_pronoun(gender, number)?
6366 };
6367
6368 if self.check_performative() {
6370 if let TokenType::Performative(act) = self.advance().kind.clone() {
6371 let sym = match resolved {
6372 ResolvedPronoun::Variable(s) | ResolvedPronoun::Constant(s) => s,
6373 };
6374 if self.check(&TokenType::To) {
6376 self.advance(); if self.check_verb() {
6379 let infinitive_verb = self.consume_verb();
6380
6381 let content = self.ctx.exprs.alloc(LogicExpr::Predicate {
6382 name: infinitive_verb,
6383 args: self.ctx.terms.alloc_slice([Term::Constant(sym)]),
6384 world: None,
6385 });
6386
6387 return Ok(self.ctx.exprs.alloc(LogicExpr::SpeechAct {
6388 performer: sym,
6389 act_type: act,
6390 content,
6391 }));
6392 }
6393 }
6394
6395 if self.check(&TokenType::That) {
6397 self.advance();
6398 }
6399 let content = self.parse_sentence()?;
6400 return Ok(self.ctx.exprs.alloc(LogicExpr::SpeechAct {
6401 performer: sym,
6402 act_type: act,
6403 content,
6404 }));
6405 }
6406 }
6407
6408 return match resolved {
6411 ResolvedPronoun::Variable(sym) => self.parse_predicate_with_subject_as_var(sym),
6412 ResolvedPronoun::Constant(sym) => self.parse_predicate_with_subject(sym),
6413 };
6414 }
6415
6416 let _had_both = self.match_token(&[TokenType::Both]);
6419
6420 let subject = self.parse_noun_phrase(true)?;
6421
6422 if subject.definiteness == Some(Definiteness::Indefinite)
6428 || subject.definiteness == Some(Definiteness::Distal) {
6429 let gender = Self::infer_noun_gender(self.interner.resolve(subject.noun));
6430 let number = if Self::is_plural_noun(self.interner.resolve(subject.noun)) {
6431 Number::Plural
6432 } else {
6433 Number::Singular
6434 };
6435 self.drs.introduce_referent(subject.noun, subject.noun, gender, number);
6437 }
6438
6439 if self.check(&TokenType::And) {
6441 match self.try_parse_plural_subject(&subject) {
6442 Ok(Some(result)) => return Ok(result),
6443 Ok(None) => {} Err(e) => return Err(e), }
6446 }
6447
6448 if self.check_scopal_adverb() {
6450 return self.parse_scopal_adverb(&subject);
6451 }
6452
6453 if self.check(&TokenType::Comma) {
6455 let saved_pos = self.current;
6456 self.advance(); if self.check_pronoun() {
6460 let topic_attempt = self.try_parse(|p| {
6461 let token = p.peek().clone();
6462 let pronoun_features = match &token.kind {
6463 TokenType::Pronoun { gender, number, .. } => Some((*gender, *number)),
6464 TokenType::Ambiguous { primary, alternatives } => {
6465 if let TokenType::Pronoun { gender, number, .. } = **primary {
6466 Some((gender, number))
6467 } else {
6468 alternatives.iter().find_map(|t| {
6469 if let TokenType::Pronoun { gender, number, .. } = t {
6470 Some((*gender, *number))
6471 } else {
6472 None
6473 }
6474 })
6475 }
6476 }
6477 _ => None,
6478 };
6479
6480 if let Some((gender, number)) = pronoun_features {
6481 p.advance(); let resolved = p.resolve_pronoun(gender, number)?;
6483 let resolved_term = match resolved {
6484 ResolvedPronoun::Variable(s) => Term::Variable(s),
6485 ResolvedPronoun::Constant(s) => Term::Constant(s),
6486 };
6487
6488 if p.check_verb() {
6489 let verb = p.consume_verb();
6490 let predicate = p.ctx.exprs.alloc(LogicExpr::Predicate {
6491 name: verb,
6492 args: p.ctx.terms.alloc_slice([
6493 resolved_term,
6494 Term::Constant(subject.noun),
6495 ]),
6496 world: None,
6497 });
6498 p.wrap_with_definiteness_full(&subject, predicate)
6499 } else {
6500 Err(ParseError {
6501 kind: ParseErrorKind::ExpectedVerb { found: p.peek().kind.clone() },
6502 span: p.current_span(),
6503 })
6504 }
6505 } else {
6506 Err(ParseError {
6507 kind: ParseErrorKind::ExpectedContentWord { found: token.kind },
6508 span: p.current_span(),
6509 })
6510 }
6511 });
6512
6513 if let Some(result) = topic_attempt {
6514 return Ok(result);
6515 }
6516 }
6517
6518 if self.check_content_word() {
6520 let topic_attempt = self.try_parse(|p| {
6521 let real_subject = p.parse_noun_phrase(true)?;
6522 if p.check_verb() {
6523 let verb = p.consume_verb();
6524 let predicate = p.ctx.exprs.alloc(LogicExpr::Predicate {
6525 name: verb,
6526 args: p.ctx.terms.alloc_slice([
6527 Term::Constant(real_subject.noun),
6528 Term::Constant(subject.noun),
6529 ]),
6530 world: None,
6531 });
6532 p.wrap_with_definiteness_full(&subject, predicate)
6533 } else {
6534 Err(ParseError {
6535 kind: ParseErrorKind::ExpectedVerb { found: p.peek().kind.clone() },
6536 span: p.current_span(),
6537 })
6538 }
6539 });
6540
6541 if let Some(result) = topic_attempt {
6542 return Ok(result);
6543 }
6544 }
6545
6546 self.current = saved_pos;
6548 }
6549
6550 let mut relative_clause: Option<(Symbol, &'a LogicExpr<'a>)> = None;
6552 if self.check(&TokenType::That) || self.check(&TokenType::Who) {
6553 self.advance();
6554 let var_name = self.next_var_name();
6555 let rel_pred = self.parse_relative_clause(var_name)?;
6556 relative_clause = Some((var_name, rel_pred));
6557 } else if matches!(self.peek().kind, TokenType::Article(_)) && self.is_contact_clause_pattern() {
6558 let var_name = self.next_var_name();
6561 let rel_pred = self.parse_relative_clause(var_name)?;
6562 relative_clause = Some((var_name, rel_pred));
6563 }
6564
6565 if let Some((var_name, rel_clause)) = relative_clause {
6567 if self.check_verb() {
6568 let (verb, verb_time, _, _) = self.consume_verb_with_metadata();
6569 let var_term = Term::Variable(var_name);
6570
6571 let event_var = self.get_event_var();
6572 let suppress_existential = self.drs.in_conditional_antecedent();
6573 let mut modifiers = vec![];
6574 if verb_time == Time::Past {
6575 modifiers.push(self.interner.intern("Past"));
6576 }
6577 let main_pred = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
6578 event_var,
6579 verb,
6580 roles: self.ctx.roles.alloc_slice(vec![
6581 (ThematicRole::Agent, var_term),
6582 ]),
6583 modifiers: self.ctx.syms.alloc_slice(modifiers),
6584 suppress_existential,
6585 world: None,
6586 })));
6587
6588 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
6589 name: subject.noun,
6590 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
6591 world: None,
6592 });
6593
6594 let inner = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6595 left: type_pred,
6596 op: TokenType::And,
6597 right: rel_clause,
6598 });
6599
6600 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6601 left: inner,
6602 op: TokenType::And,
6603 right: main_pred,
6604 });
6605
6606 return Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
6607 kind: QuantifierKind::Existential,
6608 variable: var_name,
6609 body,
6610 island_id: self.current_island,
6611 }));
6612 }
6613
6614 if self.is_at_end() || self.check(&TokenType::Period) || self.check(&TokenType::Comma) {
6617 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
6618 name: subject.noun,
6619 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
6620 world: None,
6621 });
6622
6623 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6624 left: type_pred,
6625 op: TokenType::And,
6626 right: rel_clause,
6627 });
6628
6629 let uniqueness_body = if subject.definiteness == Some(Definiteness::Definite) {
6631 let y_var = self.next_var_name();
6632 let type_pred_y = self.ctx.exprs.alloc(LogicExpr::Predicate {
6633 name: subject.noun,
6634 args: self.ctx.terms.alloc_slice([Term::Variable(y_var)]),
6635 world: None,
6636 });
6637 let identity = self.ctx.exprs.alloc(LogicExpr::Identity {
6638 left: self.ctx.terms.alloc(Term::Variable(y_var)),
6639 right: self.ctx.terms.alloc(Term::Variable(var_name)),
6640 });
6641 let uniqueness_cond = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6642 left: type_pred_y,
6643 op: TokenType::If,
6644 right: identity,
6645 });
6646 let uniqueness = self.ctx.exprs.alloc(LogicExpr::Quantifier {
6647 kind: QuantifierKind::Universal,
6648 variable: y_var,
6649 body: uniqueness_cond,
6650 island_id: self.current_island,
6651 });
6652 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6653 left: body,
6654 op: TokenType::And,
6655 right: uniqueness,
6656 })
6657 } else {
6658 body
6659 };
6660
6661 return Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
6662 kind: QuantifierKind::Existential,
6663 variable: var_name,
6664 body: uniqueness_body,
6665 island_id: self.current_island,
6666 }));
6667 }
6668
6669 relative_clause = Some((var_name, rel_clause));
6671 }
6672
6673 if self.check(&TokenType::Identity) {
6675 self.advance();
6676 let right = self.consume_content_word()?;
6677 return Ok(self.ctx.exprs.alloc(LogicExpr::Identity {
6678 left: self.ctx.terms.alloc(Term::Constant(subject.noun)),
6679 right: self.ctx.terms.alloc(Term::Constant(right)),
6680 }));
6681 }
6682
6683 if self.check_modal() {
6684 if let Some((var_name, rel_clause)) = relative_clause {
6685 let modal_pred = self.parse_aspect_chain_with_term(Term::Variable(var_name))?;
6686
6687 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
6688 name: subject.noun,
6689 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
6690 world: None,
6691 });
6692
6693 let inner = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6694 left: type_pred,
6695 op: TokenType::And,
6696 right: rel_clause,
6697 });
6698
6699 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6700 left: inner,
6701 op: TokenType::And,
6702 right: modal_pred,
6703 });
6704
6705 return Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
6706 kind: QuantifierKind::Existential,
6707 variable: var_name,
6708 body,
6709 island_id: self.current_island,
6710 }));
6711 }
6712
6713 let modal_pred = self.parse_aspect_chain(subject.noun)?;
6714 return self.wrap_with_definiteness_full(&subject, modal_pred);
6715 }
6716
6717 if self.check(&TokenType::Is) || self.check(&TokenType::Are)
6718 || self.check(&TokenType::Was) || self.check(&TokenType::Were)
6719 {
6720 let copula_time = if self.check(&TokenType::Was) || self.check(&TokenType::Were) {
6721 Time::Past
6722 } else {
6723 Time::Present
6724 };
6725 self.advance();
6726
6727 let is_negated = self.check(&TokenType::Not);
6729 if is_negated {
6730 self.advance(); }
6732
6733 if self.check_number() {
6736 let measure = self.parse_measure_phrase()?;
6737
6738 if self.check_comparative() {
6740 return self.parse_comparative(&subject, copula_time, Some(measure));
6741 }
6742
6743 if self.check_content_word() {
6745 let adj = self.consume_content_word()?;
6746 let result = self.ctx.exprs.alloc(LogicExpr::Predicate {
6747 name: adj,
6748 args: self.ctx.terms.alloc_slice([
6749 Term::Constant(subject.noun),
6750 *measure,
6751 ]),
6752 world: None,
6753 });
6754 return self.wrap_with_definiteness_full(&subject, result);
6755 }
6756
6757 if self.check(&TokenType::Period) || self.is_at_end() {
6760 if self.mode == ParserMode::Imperative {
6762 let variable = self.interner.resolve(subject.noun).to_string();
6763 let value = if let Term::Value { kind, .. } = measure {
6764 format!("{:?}", kind)
6765 } else {
6766 "value".to_string()
6767 };
6768 return Err(ParseError {
6769 kind: ParseErrorKind::IsValueEquality { variable, value },
6770 span: self.current_span(),
6771 });
6772 }
6773 let result = self.ctx.exprs.alloc(LogicExpr::Identity {
6774 left: self.ctx.terms.alloc(Term::Constant(subject.noun)),
6775 right: measure,
6776 });
6777 return self.wrap_with_definiteness_full(&subject, result);
6778 }
6779 }
6780
6781 if self.check_comparative() {
6783 return self.parse_comparative(&subject, copula_time, None);
6784 }
6785
6786 if self.check(&TokenType::Period) || self.is_at_end() {
6788 let var = self.next_var_name();
6789 let body = self.ctx.exprs.alloc(LogicExpr::Identity {
6790 left: self.ctx.terms.alloc(Term::Variable(var)),
6791 right: self.ctx.terms.alloc(Term::Constant(subject.noun)),
6792 });
6793 return Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
6794 kind: QuantifierKind::Existential,
6795 variable: var,
6796 body,
6797 island_id: self.current_island,
6798 }));
6799 }
6800
6801 if self.check(&TokenType::Article(Definiteness::Definite)) {
6803 let saved_pos = self.current;
6804 self.advance();
6805 if self.check_superlative() {
6806 return self.parse_superlative(&subject);
6807 }
6808 self.current = saved_pos;
6809 }
6810
6811 if self.check_article() {
6813 let predicate_np = self.parse_noun_phrase(true)?;
6814 let predicate_noun = predicate_np.noun;
6815
6816 if self.event_reading_mode {
6819 let noun_str = self.interner.resolve(predicate_noun);
6820 if let Some(base_verb) = lexicon::lookup_agentive_noun(noun_str) {
6821 let event_adj = predicate_np.adjectives.iter().find(|adj| {
6823 lexicon::is_event_modifier_adjective(self.interner.resolve(**adj))
6824 });
6825
6826 if let Some(&adj_sym) = event_adj {
6827 let verb_sym = self.interner.intern(base_verb);
6829 let event_var = self.get_event_var();
6830
6831 let verb_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
6832 name: verb_sym,
6833 args: self.ctx.terms.alloc_slice([Term::Variable(event_var)]),
6834 world: None,
6835 });
6836
6837 let agent_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
6838 name: self.interner.intern("Agent"),
6839 args: self.ctx.terms.alloc_slice([
6840 Term::Variable(event_var),
6841 Term::Constant(subject.noun),
6842 ]),
6843 world: None,
6844 });
6845
6846 let adj_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
6847 name: adj_sym,
6848 args: self.ctx.terms.alloc_slice([Term::Variable(event_var)]),
6849 world: None,
6850 });
6851
6852 let verb_agent = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6854 left: verb_pred,
6855 op: TokenType::And,
6856 right: agent_pred,
6857 });
6858
6859 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6861 left: verb_agent,
6862 op: TokenType::And,
6863 right: adj_pred,
6864 });
6865
6866 let event_reading = self.ctx.exprs.alloc(LogicExpr::Quantifier {
6868 kind: QuantifierKind::Existential,
6869 variable: event_var,
6870 body,
6871 island_id: self.current_island,
6872 });
6873
6874 return self.wrap_with_definiteness(subject.definiteness, subject.noun, event_reading);
6875 }
6876 }
6877 }
6878
6879 let subject_sort = lexicon::lookup_sort(self.interner.resolve(subject.noun));
6880 let predicate_sort = lexicon::lookup_sort(self.interner.resolve(predicate_noun));
6881
6882 if let (Some(s_sort), Some(p_sort)) = (subject_sort, predicate_sort) {
6883 if !s_sort.is_compatible_with(p_sort) && !p_sort.is_compatible_with(s_sort) {
6884 let metaphor = self.ctx.exprs.alloc(LogicExpr::Metaphor {
6885 tenor: self.ctx.terms.alloc(Term::Constant(subject.noun)),
6886 vehicle: self.ctx.terms.alloc(Term::Constant(predicate_noun)),
6887 });
6888 return self.wrap_with_definiteness(subject.definiteness, subject.noun, metaphor);
6889 }
6890 }
6891
6892 let mut predicates: Vec<&'a LogicExpr<'a>> = Vec::new();
6895
6896 for &adj_sym in predicate_np.adjectives {
6898 let adj_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
6899 name: adj_sym,
6900 args: self.ctx.terms.alloc_slice([Term::Constant(subject.noun)]),
6901 world: None,
6902 });
6903 predicates.push(adj_pred);
6904 }
6905
6906 let noun_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
6908 name: predicate_noun,
6909 args: self.ctx.terms.alloc_slice([Term::Constant(subject.noun)]),
6910 world: None,
6911 });
6912 predicates.push(noun_pred);
6913
6914 let result = if predicates.len() == 1 {
6916 predicates[0]
6917 } else {
6918 let mut combined = predicates[0];
6919 for pred in &predicates[1..] {
6920 combined = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
6921 left: combined,
6922 op: TokenType::And,
6923 right: *pred,
6924 });
6925 }
6926 combined
6927 };
6928
6929 return self.wrap_with_definiteness(subject.definiteness, subject.noun, result);
6930 }
6931
6932 let prefer_adjective = if let TokenType::Ambiguous { primary, alternatives } = &self.peek().kind {
6935 let is_simple_verb = if let TokenType::Verb { aspect, .. } = **primary {
6936 aspect == Aspect::Simple
6937 } else {
6938 false
6939 };
6940 let has_adj_alt = alternatives.iter().any(|t| matches!(t, TokenType::Adjective(_)));
6941 is_simple_verb && has_adj_alt
6942 } else {
6943 false
6944 };
6945
6946 if !prefer_adjective && self.check_verb() {
6947 let (verb, _verb_time, verb_aspect, verb_class) = self.consume_verb_with_metadata();
6948
6949 if verb_class.is_stative() && verb_aspect == Aspect::Progressive {
6951 return Err(ParseError {
6952 kind: ParseErrorKind::StativeProgressiveConflict,
6953 span: self.current_span(),
6954 });
6955 }
6956
6957 let mut goal_args: Vec<Term<'a>> = Vec::new();
6960 while self.check_to_preposition() {
6961 self.advance(); let goal = self.parse_noun_phrase(true)?;
6963 goal_args.push(self.noun_phrase_to_term(&goal));
6964 }
6965
6966 if self.check_by_preposition() {
6968 self.advance(); let agent = self.parse_noun_phrase(true)?;
6970
6971 let mut args = vec![
6973 self.noun_phrase_to_term(&agent),
6974 self.noun_phrase_to_term(&subject),
6975 ];
6976 args.extend(goal_args);
6977
6978 let predicate = self.ctx.exprs.alloc(LogicExpr::Predicate {
6979 name: verb,
6980 args: self.ctx.terms.alloc_slice(args),
6981 world: None,
6982 });
6983
6984 let with_time = if copula_time == Time::Past {
6985 self.ctx.exprs.alloc(LogicExpr::Temporal {
6986 operator: TemporalOperator::Past,
6987 body: predicate,
6988 })
6989 } else {
6990 predicate
6991 };
6992
6993 return self.wrap_with_definiteness(subject.definiteness, subject.noun, with_time);
6994 }
6995
6996 if copula_time == Time::Past && verb_aspect == Aspect::Simple
7001 && subject.definiteness != Some(Definiteness::Definite) {
7002 let var_name = self.next_var_name();
7004 let predicate = self.ctx.exprs.alloc(LogicExpr::Predicate {
7005 name: verb,
7006 args: self.ctx.terms.alloc_slice([
7007 Term::Variable(var_name),
7008 Term::Constant(subject.noun),
7009 ]),
7010 world: None,
7011 });
7012
7013 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7014 name: subject.noun,
7015 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
7016 world: None,
7017 });
7018
7019 let temporal = self.ctx.exprs.alloc(LogicExpr::Temporal {
7020 operator: TemporalOperator::Past,
7021 body: predicate,
7022 });
7023
7024 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7025 left: type_pred,
7026 op: TokenType::And,
7027 right: temporal,
7028 });
7029
7030 let result = self.ctx.exprs.alloc(LogicExpr::Quantifier {
7031 kind: QuantifierKind::Existential,
7032 variable: var_name,
7033 body,
7034 island_id: self.current_island,
7035 });
7036
7037 if is_negated {
7039 return Ok(self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7040 op: TokenType::Not,
7041 operand: result,
7042 }));
7043 }
7044 return Ok(result);
7045 }
7046
7047 let verb_str = self.interner.resolve(verb).to_lowercase();
7050 let subject_term = if lexicon::is_intensional_predicate(&verb_str) {
7051 Term::Intension(subject.noun)
7052 } else {
7053 Term::Constant(subject.noun)
7054 };
7055
7056 let predicate = self.ctx.exprs.alloc(LogicExpr::Predicate {
7057 name: verb,
7058 args: self.ctx.terms.alloc_slice([subject_term]),
7059 world: None,
7060 });
7061
7062 let with_aspect = if verb_aspect == Aspect::Progressive {
7063 let operator = if verb_class == VerbClass::Semelfactive {
7065 AspectOperator::Iterative
7066 } else {
7067 AspectOperator::Progressive
7068 };
7069 self.ctx.exprs.alloc(LogicExpr::Aspectual {
7070 operator,
7071 body: predicate,
7072 })
7073 } else {
7074 predicate
7075 };
7076
7077 let with_time = if copula_time == Time::Past {
7078 self.ctx.exprs.alloc(LogicExpr::Temporal {
7079 operator: TemporalOperator::Past,
7080 body: with_aspect,
7081 })
7082 } else {
7083 with_aspect
7084 };
7085
7086 let final_expr = if is_negated {
7087 self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7088 op: TokenType::Not,
7089 operand: with_time,
7090 })
7091 } else {
7092 with_time
7093 };
7094
7095 if subject.definiteness == Some(Definiteness::Definite) {
7099 return Ok(final_expr);
7100 }
7101
7102 return self.wrap_with_definiteness(subject.definiteness, subject.noun, final_expr);
7103 }
7104
7105 if let Some((var_name, rel_clause)) = relative_clause {
7107 let var_term = Term::Variable(var_name);
7108 let pred_word = self.consume_content_word()?;
7109
7110 let main_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7111 name: pred_word,
7112 args: self.ctx.terms.alloc_slice([var_term]),
7113 world: None,
7114 });
7115
7116 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7117 name: subject.noun,
7118 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
7119 world: None,
7120 });
7121
7122 let inner = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7123 left: type_pred,
7124 op: TokenType::And,
7125 right: rel_clause,
7126 });
7127
7128 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7129 left: inner,
7130 op: TokenType::And,
7131 right: main_pred,
7132 });
7133
7134 return Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
7135 kind: QuantifierKind::Existential,
7136 variable: var_name,
7137 body,
7138 island_id: self.current_island,
7139 }));
7140 }
7141
7142 if let TokenType::ProperName(predicate_name) = self.peek().kind {
7147 self.advance(); let identity = self.ctx.exprs.alloc(LogicExpr::Identity {
7149 left: self.ctx.terms.alloc(Term::Constant(subject.noun)),
7150 right: self.ctx.terms.alloc(Term::Constant(predicate_name)),
7151 });
7152 let result = if is_negated {
7153 self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7154 op: TokenType::Not,
7155 operand: identity,
7156 })
7157 } else {
7158 identity
7159 };
7160 return self.wrap_with_definiteness(subject.definiteness, subject.noun, result);
7161 }
7162
7163 let predicate_name = self.consume_content_word()?;
7166
7167 let subject_sort = lexicon::lookup_sort(self.interner.resolve(subject.noun));
7169 let predicate_str = self.interner.resolve(predicate_name);
7170
7171 if let Some(s_sort) = subject_sort {
7173 if !crate::ontology::check_sort_compatibility(predicate_str, s_sort) {
7174 let metaphor = self.ctx.exprs.alloc(LogicExpr::Metaphor {
7175 tenor: self.ctx.terms.alloc(Term::Constant(subject.noun)),
7176 vehicle: self.ctx.terms.alloc(Term::Constant(predicate_name)),
7177 });
7178 return self.wrap_with_definiteness(subject.definiteness, subject.noun, metaphor);
7179 }
7180 }
7181
7182 let predicate_sort = lexicon::lookup_sort(predicate_str);
7184 if let (Some(s_sort), Some(p_sort)) = (subject_sort, predicate_sort) {
7185 if s_sort != p_sort && !s_sort.is_compatible_with(p_sort) && !p_sort.is_compatible_with(s_sort) {
7186 let metaphor = self.ctx.exprs.alloc(LogicExpr::Metaphor {
7187 tenor: self.ctx.terms.alloc(Term::Constant(subject.noun)),
7188 vehicle: self.ctx.terms.alloc(Term::Constant(predicate_name)),
7189 });
7190 return self.wrap_with_definiteness(subject.definiteness, subject.noun, metaphor);
7191 }
7192 }
7193
7194 let predicate = self.ctx.exprs.alloc(LogicExpr::Predicate {
7195 name: predicate_name,
7196 args: self.ctx.terms.alloc_slice([Term::Constant(subject.noun)]),
7197 world: None,
7198 });
7199
7200 let result = if is_negated {
7202 self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7203 op: TokenType::Not,
7204 operand: predicate,
7205 })
7206 } else {
7207 predicate
7208 };
7209 return self.wrap_with_definiteness(subject.definiteness, subject.noun, result);
7210 }
7211
7212 if self.check_auxiliary() && self.is_true_auxiliary_usage() {
7216 let aux_time = if let TokenType::Auxiliary(time) = self.advance().kind {
7217 time
7218 } else {
7219 Time::None
7220 };
7221 self.pending_time = Some(aux_time);
7222
7223 if self.match_token(&[TokenType::Not]) {
7225 self.negative_depth += 1;
7226
7227 if self.check(&TokenType::Ever) {
7229 self.advance();
7230 }
7231
7232 if self.check_verb() || self.check(&TokenType::Do) {
7234 let verb = if self.check(&TokenType::Do) {
7235 self.advance(); self.interner.intern("Do")
7237 } else {
7238 self.consume_verb()
7239 };
7240 let subject_term = self.noun_phrase_to_term(&subject);
7241
7242 if self.check_npi_object() {
7244 let npi_token = self.advance().kind.clone();
7245 let obj_var = self.next_var_name();
7246
7247 let restriction_name = match npi_token {
7248 TokenType::Anything => "Thing",
7249 TokenType::Anyone => "Person",
7250 _ => "Thing",
7251 };
7252
7253 let restriction_sym = self.interner.intern(restriction_name);
7254 let obj_restriction = self.ctx.exprs.alloc(LogicExpr::Predicate {
7255 name: restriction_sym,
7256 args: self.ctx.terms.alloc_slice([Term::Variable(obj_var)]),
7257 world: None,
7258 });
7259
7260 let verb_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7261 name: verb,
7262 args: self.ctx.terms.alloc_slice([subject_term.clone(), Term::Variable(obj_var)]),
7263 world: None,
7264 });
7265
7266 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7267 left: obj_restriction,
7268 op: TokenType::And,
7269 right: verb_pred,
7270 });
7271
7272 let quantified = self.ctx.exprs.alloc(LogicExpr::Quantifier {
7273 kind: QuantifierKind::Existential,
7274 variable: obj_var,
7275 body,
7276 island_id: self.current_island,
7277 });
7278
7279 let effective_time = self.pending_time.take().unwrap_or(Time::None);
7280 let with_time = match effective_time {
7281 Time::Past => self.ctx.exprs.alloc(LogicExpr::Temporal {
7282 operator: TemporalOperator::Past,
7283 body: quantified,
7284 }),
7285 Time::Future => self.ctx.exprs.alloc(LogicExpr::Temporal {
7286 operator: TemporalOperator::Future,
7287 body: quantified,
7288 }),
7289 _ => quantified,
7290 };
7291
7292 self.negative_depth -= 1;
7293 return Ok(self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7294 op: TokenType::Not,
7295 operand: with_time,
7296 }));
7297 }
7298
7299 if self.check_quantifier() {
7301 let quantifier_token = self.advance().kind.clone();
7302 let object_np = self.parse_noun_phrase(false)?;
7303 let obj_var = self.next_var_name();
7304
7305 let obj_restriction = self.ctx.exprs.alloc(LogicExpr::Predicate {
7306 name: object_np.noun,
7307 args: self.ctx.terms.alloc_slice([Term::Variable(obj_var)]),
7308 world: None,
7309 });
7310
7311 let verb_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7312 name: verb,
7313 args: self.ctx.terms.alloc_slice([subject_term.clone(), Term::Variable(obj_var)]),
7314 world: None,
7315 });
7316
7317 let (kind, body) = match quantifier_token {
7318 TokenType::Any => {
7319 if self.is_negative_context() {
7320 (
7321 QuantifierKind::Existential,
7322 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7323 left: obj_restriction,
7324 op: TokenType::And,
7325 right: verb_pred,
7326 }),
7327 )
7328 } else {
7329 (
7330 QuantifierKind::Universal,
7331 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7332 left: obj_restriction,
7333 op: TokenType::If,
7334 right: verb_pred,
7335 }),
7336 )
7337 }
7338 }
7339 TokenType::Some => (
7340 QuantifierKind::Existential,
7341 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7342 left: obj_restriction,
7343 op: TokenType::And,
7344 right: verb_pred,
7345 }),
7346 ),
7347 TokenType::All => (
7348 QuantifierKind::Universal,
7349 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7350 left: obj_restriction,
7351 op: TokenType::If,
7352 right: verb_pred,
7353 }),
7354 ),
7355 _ => (
7356 QuantifierKind::Existential,
7357 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7358 left: obj_restriction,
7359 op: TokenType::And,
7360 right: verb_pred,
7361 }),
7362 ),
7363 };
7364
7365 let quantified = self.ctx.exprs.alloc(LogicExpr::Quantifier {
7366 kind,
7367 variable: obj_var,
7368 body,
7369 island_id: self.current_island,
7370 });
7371
7372 let effective_time = self.pending_time.take().unwrap_or(Time::None);
7373 let with_time = match effective_time {
7374 Time::Past => self.ctx.exprs.alloc(LogicExpr::Temporal {
7375 operator: TemporalOperator::Past,
7376 body: quantified,
7377 }),
7378 Time::Future => self.ctx.exprs.alloc(LogicExpr::Temporal {
7379 operator: TemporalOperator::Future,
7380 body: quantified,
7381 }),
7382 _ => quantified,
7383 };
7384
7385 self.negative_depth -= 1;
7386 return Ok(self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7387 op: TokenType::Not,
7388 operand: with_time,
7389 }));
7390 }
7391
7392 let mut roles: Vec<(ThematicRole, Term<'a>)> = vec![(ThematicRole::Agent, subject_term)];
7393
7394 let effective_time = self.pending_time.take().unwrap_or(Time::None);
7396 let mut modifiers: Vec<Symbol> = vec![];
7397 match effective_time {
7398 Time::Past => modifiers.push(self.interner.intern("Past")),
7399 Time::Future => modifiers.push(self.interner.intern("Future")),
7400 _ => {}
7401 }
7402
7403 if self.check_content_word() || self.check_article() || self.check_pronoun() {
7405 if self.check_pronoun() {
7406 let pronoun_token = self.advance();
7408 let pronoun_sym = pronoun_token.lexeme;
7409 roles.push((ThematicRole::Theme, Term::Constant(pronoun_sym)));
7410 } else {
7411 let object = self.parse_noun_phrase(false)?;
7412 let object_term = self.noun_phrase_to_term(&object);
7413 roles.push((ThematicRole::Theme, object_term));
7414 }
7415 }
7416
7417 let event_var = self.get_event_var();
7418 let suppress_existential = self.drs.in_conditional_antecedent();
7419 if suppress_existential {
7420 let event_class = self.interner.intern("Event");
7421 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
7422 }
7423 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
7424 event_var,
7425 verb,
7426 roles: self.ctx.roles.alloc_slice(roles),
7427 modifiers: self.ctx.syms.alloc_slice(modifiers),
7428 suppress_existential,
7429 world: None,
7430 })));
7431
7432 self.negative_depth -= 1;
7433 return Ok(self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7434 op: TokenType::Not,
7435 operand: neo_event,
7436 }));
7437 }
7438
7439 self.negative_depth -= 1;
7440 }
7441 }
7443
7444 if self.check_presup_trigger() && !self.is_followed_by_np_object() && self.is_followed_by_gerund() {
7450 let presup_kind = match self.advance().kind {
7451 TokenType::PresupTrigger(kind) => kind,
7452 TokenType::Verb { lemma, .. } => {
7453 let s = self.interner.resolve(lemma).to_lowercase();
7454 crate::lexicon::lookup_presup_trigger(&s)
7455 .expect("Lexicon mismatch: Verb flagged as trigger but lookup failed")
7456 }
7457 _ => panic!("Expected presupposition trigger"),
7458 };
7459 return self.parse_presupposition(&subject, presup_kind);
7460 }
7461
7462 let noun_str = self.interner.resolve(subject.noun);
7464 let is_bare_plural = subject.definiteness.is_none()
7465 && subject.possessor.is_none()
7466 && Self::is_plural_noun(noun_str)
7467 && self.check_verb();
7468
7469 if is_bare_plural {
7470 let var_name = self.next_var_name();
7471 let (verb, verb_time, verb_aspect, _) = self.consume_verb_with_metadata();
7472
7473 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7474 name: subject.noun,
7475 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
7476 world: None,
7477 });
7478
7479 let mut args = vec![Term::Variable(var_name)];
7480 if self.check_content_word() {
7481 let object = self.parse_noun_phrase(false)?;
7482 args.push(self.noun_phrase_to_term(&object));
7483 }
7484
7485 let verb_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7486 name: verb,
7487 args: self.ctx.terms.alloc_slice(args),
7488 world: None,
7489 });
7490
7491 let effective_time = self.pending_time.take().unwrap_or(verb_time);
7492 let with_time = match effective_time {
7493 Time::Past => self.ctx.exprs.alloc(LogicExpr::Temporal {
7494 operator: TemporalOperator::Past,
7495 body: verb_pred,
7496 }),
7497 Time::Future => self.ctx.exprs.alloc(LogicExpr::Temporal {
7498 operator: TemporalOperator::Future,
7499 body: verb_pred,
7500 }),
7501 _ => verb_pred,
7502 };
7503
7504 let with_aspect = if verb_aspect == Aspect::Progressive {
7505 self.ctx.exprs.alloc(LogicExpr::Aspectual {
7506 operator: AspectOperator::Progressive,
7507 body: with_time,
7508 })
7509 } else {
7510 with_time
7511 };
7512
7513 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7514 left: type_pred,
7515 op: TokenType::If,
7516 right: with_aspect,
7517 });
7518
7519 return Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
7520 kind: QuantifierKind::Generic,
7521 variable: var_name,
7522 body,
7523 island_id: self.current_island,
7524 }));
7525 }
7526
7527 if self.check(&TokenType::Does) || self.check(&TokenType::Do) {
7529 self.advance(); let is_negated = self.match_token(&[TokenType::Not]);
7531
7532 if self.check_verb() {
7533 let verb = self.consume_verb();
7534 let verb_lemma = self.interner.resolve(verb).to_lowercase();
7535
7536 if self.check_wh_word() {
7538 let wh_token = self.advance().kind.clone();
7539 let is_who = matches!(wh_token, TokenType::Who);
7540 let is_what = matches!(wh_token, TokenType::What);
7541
7542 let is_sluicing = self.is_at_end() ||
7543 self.check(&TokenType::Period) ||
7544 self.check(&TokenType::Comma);
7545
7546 if is_sluicing {
7547 if let Some(template) = self.last_event_template.clone() {
7548 let wh_var = self.next_var_name();
7549 let subject_term = self.noun_phrase_to_term(&subject);
7550
7551 let roles: Vec<_> = if is_who {
7552 std::iter::once((ThematicRole::Agent, Term::Variable(wh_var)))
7553 .chain(template.non_agent_roles.iter().cloned())
7554 .collect()
7555 } else if is_what {
7556 vec![
7557 (ThematicRole::Agent, subject_term.clone()),
7558 (ThematicRole::Theme, Term::Variable(wh_var)),
7559 ]
7560 } else {
7561 std::iter::once((ThematicRole::Agent, Term::Variable(wh_var)))
7562 .chain(template.non_agent_roles.iter().cloned())
7563 .collect()
7564 };
7565
7566 let event_var = self.get_event_var();
7567 let suppress_existential = self.drs.in_conditional_antecedent();
7568 if suppress_existential {
7569 let event_class = self.interner.intern("Event");
7570 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
7571 }
7572 let reconstructed = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
7573 event_var,
7574 verb: template.verb,
7575 roles: self.ctx.roles.alloc_slice(roles),
7576 modifiers: self.ctx.syms.alloc_slice(template.modifiers.clone()),
7577 suppress_existential,
7578 world: None,
7579 })));
7580
7581 let question = self.ctx.exprs.alloc(LogicExpr::Question {
7582 wh_variable: wh_var,
7583 body: reconstructed,
7584 });
7585
7586 let know_event_var = self.get_event_var();
7587 let suppress_existential2 = self.drs.in_conditional_antecedent();
7588 if suppress_existential2 {
7589 let event_class = self.interner.intern("Event");
7590 self.drs.introduce_referent(know_event_var, event_class, Gender::Neuter, Number::Singular);
7591 }
7592 let know_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
7593 event_var: know_event_var,
7594 verb,
7595 roles: self.ctx.roles.alloc_slice(vec![
7596 (ThematicRole::Agent, subject_term),
7597 (ThematicRole::Theme, Term::Proposition(question)),
7598 ]),
7599 modifiers: self.ctx.syms.alloc_slice(vec![]),
7600 suppress_existential: suppress_existential2,
7601 world: None,
7602 })));
7603
7604 let result = if is_negated {
7605 self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7606 op: TokenType::Not,
7607 operand: know_event,
7608 })
7609 } else {
7610 know_event
7611 };
7612
7613 return self.wrap_with_definiteness_full(&subject, result);
7614 }
7615 }
7616 }
7617
7618 if verb_lemma == "exist" && is_negated {
7620 let var_name = self.next_var_name();
7622 let restriction = self.ctx.exprs.alloc(LogicExpr::Predicate {
7623 name: subject.noun,
7624 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
7625 world: None,
7626 });
7627 let exists = self.ctx.exprs.alloc(LogicExpr::Quantifier {
7628 kind: QuantifierKind::Existential,
7629 variable: var_name,
7630 body: restriction,
7631 island_id: self.current_island,
7632 });
7633 return Ok(self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7634 op: TokenType::Not,
7635 operand: exists,
7636 }));
7637 }
7638
7639 let subject_term = self.noun_phrase_to_term(&subject);
7642 let modifiers: Vec<Symbol> = vec![];
7643
7644 if self.check(&TokenType::Reflexive) {
7646 self.advance();
7647 let roles = vec![
7648 (ThematicRole::Agent, subject_term.clone()),
7649 (ThematicRole::Theme, subject_term),
7650 ];
7651 let event_var = self.get_event_var();
7652 let suppress_existential = self.drs.in_conditional_antecedent();
7653 if suppress_existential {
7654 let event_class = self.interner.intern("Event");
7655 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
7656 }
7657 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
7658 event_var,
7659 verb,
7660 roles: self.ctx.roles.alloc_slice(roles),
7661 modifiers: self.ctx.syms.alloc_slice(modifiers),
7662 suppress_existential,
7663 world: None,
7664 })));
7665
7666 let result = if is_negated {
7667 self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7668 op: TokenType::Not,
7669 operand: neo_event,
7670 })
7671 } else {
7672 neo_event
7673 };
7674 return self.wrap_with_definiteness_full(&subject, result);
7675 }
7676
7677 if self.check_npi_quantifier() || self.check_quantifier() || self.check_article() {
7679 let (obj_quantifier, was_definite_article) = if self.check_npi_quantifier() {
7680 let tok = self.advance().kind.clone();
7682 (Some(tok), false)
7683 } else if self.check_quantifier() {
7684 (Some(self.advance().kind.clone()), false)
7685 } else {
7686 let art = self.advance().kind.clone();
7687 if let TokenType::Article(def) = art {
7688 if def == Definiteness::Indefinite {
7689 (Some(TokenType::Some), false)
7690 } else {
7691 (None, true)
7692 }
7693 } else {
7694 (None, false)
7695 }
7696 };
7697
7698 let object_np = self.parse_noun_phrase(false)?;
7699 let obj_var = self.next_var_name();
7700
7701 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7702 name: object_np.noun,
7703 args: self.ctx.terms.alloc_slice([Term::Variable(obj_var)]),
7704 world: None,
7705 });
7706
7707 let obj_restriction = if self.check(&TokenType::That) || self.check(&TokenType::Who) {
7709 self.advance();
7710 let rel_clause = self.parse_relative_clause(obj_var)?;
7711 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7712 left: type_pred,
7713 op: TokenType::And,
7714 right: rel_clause,
7715 })
7716 } else {
7717 type_pred
7718 };
7719
7720 let event_var = self.get_event_var();
7721 let suppress_existential = self.drs.in_conditional_antecedent();
7722 if suppress_existential {
7723 let event_class = self.interner.intern("Event");
7724 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
7725 }
7726
7727 let roles = vec![
7728 (ThematicRole::Agent, subject_term),
7729 (ThematicRole::Theme, Term::Variable(obj_var)),
7730 ];
7731
7732 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
7733 event_var,
7734 verb,
7735 roles: self.ctx.roles.alloc_slice(roles),
7736 modifiers: self.ctx.syms.alloc_slice(modifiers),
7737 suppress_existential,
7738 world: None,
7739 })));
7740
7741 let quantifier_kind = match &obj_quantifier {
7745 Some(TokenType::Any) if is_negated => QuantifierKind::Existential,
7746 Some(TokenType::All) => QuantifierKind::Universal,
7747 Some(TokenType::No) => QuantifierKind::Universal,
7748 _ => QuantifierKind::Existential,
7749 };
7750
7751 let obj_body = match &obj_quantifier {
7752 Some(TokenType::All) => self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7753 left: obj_restriction,
7754 op: TokenType::If,
7755 right: neo_event,
7756 }),
7757 Some(TokenType::No) => {
7758 let neg = self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7759 op: TokenType::Not,
7760 operand: neo_event,
7761 });
7762 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7763 left: obj_restriction,
7764 op: TokenType::If,
7765 right: neg,
7766 })
7767 }
7768 _ => self.ctx.exprs.alloc(LogicExpr::BinaryOp {
7769 left: obj_restriction,
7770 op: TokenType::And,
7771 right: neo_event,
7772 }),
7773 };
7774
7775 let obj_quantified = self.ctx.exprs.alloc(LogicExpr::Quantifier {
7776 kind: quantifier_kind,
7777 variable: obj_var,
7778 body: obj_body,
7779 island_id: self.current_island,
7780 });
7781
7782 let result = if is_negated && matches!(obj_quantifier, Some(TokenType::Any)) {
7784 self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7785 op: TokenType::Not,
7786 operand: obj_quantified,
7787 })
7788 } else if is_negated {
7789 self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7791 op: TokenType::Not,
7792 operand: obj_quantified,
7793 })
7794 } else {
7795 obj_quantified
7796 };
7797
7798 return self.wrap_with_definiteness_full(&subject, result);
7799 }
7800
7801 let roles: Vec<(ThematicRole, Term<'a>)> = vec![(ThematicRole::Agent, subject_term)];
7803 let event_var = self.get_event_var();
7804 let suppress_existential = self.drs.in_conditional_antecedent();
7805 if suppress_existential {
7806 let event_class = self.interner.intern("Event");
7807 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
7808 }
7809
7810 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
7811 event_var,
7812 verb,
7813 roles: self.ctx.roles.alloc_slice(roles),
7814 modifiers: self.ctx.syms.alloc_slice(modifiers),
7815 suppress_existential,
7816 world: None,
7817 })));
7818
7819 if is_negated {
7820 return Ok(self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7821 op: TokenType::Not,
7822 operand: neo_event,
7823 }));
7824 }
7825 return Ok(neo_event);
7826 }
7827 }
7828
7829 let is_perfect_aux = if self.check_verb() {
7835 let word = self.interner.resolve(self.peek().lexeme).to_lowercase();
7836 word == "has" || word == "have" || word == "had"
7837 } else {
7838 false
7839 };
7840 if subject.definiteness == Some(Definiteness::Definite) && self.check_verb() && self.pending_time.is_none() && !is_perfect_aux {
7841 let saved_pos = self.current;
7842
7843 if let Some(garden_path_result) = self.try_parse(|p| {
7845 let (modifier_verb, _modifier_time, _, _) = p.consume_verb_with_metadata();
7846
7847 let mut pp_mods: Vec<&'a LogicExpr<'a>> = Vec::new();
7849 while p.check_preposition() {
7850 let prep = if let TokenType::Preposition(prep) = p.advance().kind {
7851 prep
7852 } else {
7853 break;
7854 };
7855 if p.check_article() || p.check_content_word() {
7856 let pp_obj = p.parse_noun_phrase(false)?;
7857 let pp_pred = p.ctx.exprs.alloc(LogicExpr::Predicate {
7858 name: prep,
7859 args: p.ctx.terms.alloc_slice([Term::Variable(p.interner.intern("x")), Term::Constant(pp_obj.noun)]),
7860 world: None,
7861 });
7862 pp_mods.push(pp_pred);
7863 }
7864 }
7865
7866 if !p.check_verb() {
7868 return Err(ParseError {
7869 kind: ParseErrorKind::ExpectedVerb { found: p.peek().kind.clone() },
7870 span: p.current_span(),
7871 });
7872 }
7873
7874 let (main_verb, main_time, _, _) = p.consume_verb_with_metadata();
7875
7876 let var = p.interner.intern("x");
7878
7879 let type_pred = p.ctx.exprs.alloc(LogicExpr::Predicate {
7881 name: subject.noun,
7882 args: p.ctx.terms.alloc_slice([Term::Variable(var)]),
7883 world: None,
7884 });
7885
7886 let mod_pred = p.ctx.exprs.alloc(LogicExpr::Predicate {
7888 name: modifier_verb,
7889 args: p.ctx.terms.alloc_slice([Term::Variable(var)]),
7890 world: None,
7891 });
7892
7893 let main_pred = p.ctx.exprs.alloc(LogicExpr::Predicate {
7895 name: main_verb,
7896 args: p.ctx.terms.alloc_slice([Term::Variable(var)]),
7897 world: None,
7898 });
7899
7900 let mut body = p.ctx.exprs.alloc(LogicExpr::BinaryOp {
7902 left: type_pred,
7903 op: TokenType::And,
7904 right: mod_pred,
7905 });
7906
7907 for pp in pp_mods {
7909 body = p.ctx.exprs.alloc(LogicExpr::BinaryOp {
7910 left: body,
7911 op: TokenType::And,
7912 right: pp,
7913 });
7914 }
7915
7916 body = p.ctx.exprs.alloc(LogicExpr::BinaryOp {
7918 left: body,
7919 op: TokenType::And,
7920 right: main_pred,
7921 });
7922
7923 let with_time = match main_time {
7925 Time::Past => p.ctx.exprs.alloc(LogicExpr::Temporal {
7926 operator: TemporalOperator::Past,
7927 body,
7928 }),
7929 Time::Future => p.ctx.exprs.alloc(LogicExpr::Temporal {
7930 operator: TemporalOperator::Future,
7931 body,
7932 }),
7933 _ => body,
7934 };
7935
7936 Ok(p.ctx.exprs.alloc(LogicExpr::Quantifier {
7938 kind: QuantifierKind::Existential,
7939 variable: var,
7940 body: with_time,
7941 island_id: p.current_island,
7942 }))
7943 }) {
7944 return Ok(garden_path_result);
7945 }
7946
7947 self.current = saved_pos;
7949 }
7950
7951 if self.check_modal() {
7952 return self.parse_aspect_chain(subject.noun);
7953 }
7954
7955 if self.check_content_word() {
7957 let word = self.interner.resolve(self.peek().lexeme).to_lowercase();
7958 if word == "has" || word == "have" || word == "had" {
7959 let is_perfect_aspect = if self.current + 1 < self.tokens.len() {
7961 let next_token = &self.tokens[self.current + 1].kind;
7962 matches!(
7963 next_token,
7964 TokenType::Verb { .. } | TokenType::Not
7965 ) && !matches!(next_token, TokenType::Number(_))
7966 } else {
7967 false
7968 };
7969 if is_perfect_aspect {
7970 return self.parse_aspect_chain(subject.noun);
7971 }
7972 }
7974 }
7975
7976 if self.check(&TokenType::Had) {
7978 return self.parse_aspect_chain(subject.noun);
7979 }
7980
7981 if self.check(&TokenType::Never) {
7983 self.advance();
7984 let verb = self.consume_verb();
7985 let subject_term = self.noun_phrase_to_term(&subject);
7986 let verb_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
7987 name: verb,
7988 args: self.ctx.terms.alloc_slice([subject_term]),
7989 world: None,
7990 });
7991 let result = self.ctx.exprs.alloc(LogicExpr::UnaryOp {
7992 op: TokenType::Not,
7993 operand: verb_pred,
7994 });
7995 return self.wrap_with_definiteness_full(&subject, result);
7996 }
7997
7998 if self.check_verb() {
7999 let (mut verb, verb_time, verb_aspect, verb_class) = self.consume_verb_with_metadata();
8000
8001 let subject_sort = lexicon::lookup_sort(self.interner.resolve(subject.noun));
8003 let verb_str = self.interner.resolve(verb);
8004 if let Some(s_sort) = subject_sort {
8005 if !crate::ontology::check_sort_compatibility(verb_str, s_sort) {
8006 let metaphor = self.ctx.exprs.alloc(LogicExpr::Metaphor {
8007 tenor: self.ctx.terms.alloc(Term::Constant(subject.noun)),
8008 vehicle: self.ctx.terms.alloc(Term::Constant(verb)),
8009 });
8010 return self.wrap_with_definiteness(subject.definiteness, subject.noun, metaphor);
8011 }
8012 }
8013
8014 if self.is_control_verb(verb) {
8016 return self.parse_control_structure(&subject, verb, verb_time);
8017 }
8018
8019 if let Some((var_name, rel_clause)) = relative_clause {
8021 let main_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
8022 name: verb,
8023 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
8024 world: None,
8025 });
8026
8027 let effective_time = self.pending_time.take().unwrap_or(verb_time);
8028 let with_time = match effective_time {
8029 Time::Past => self.ctx.exprs.alloc(LogicExpr::Temporal {
8030 operator: TemporalOperator::Past,
8031 body: main_pred,
8032 }),
8033 Time::Future => self.ctx.exprs.alloc(LogicExpr::Temporal {
8034 operator: TemporalOperator::Future,
8035 body: main_pred,
8036 }),
8037 _ => main_pred,
8038 };
8039
8040 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
8042 name: subject.noun,
8043 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
8044 world: None,
8045 });
8046
8047 let inner = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8048 left: type_pred,
8049 op: TokenType::And,
8050 right: rel_clause,
8051 });
8052
8053 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8054 left: inner,
8055 op: TokenType::And,
8056 right: with_time,
8057 });
8058
8059 return Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
8060 kind: QuantifierKind::Existential,
8061 variable: var_name,
8062 body,
8063 island_id: self.current_island,
8064 }));
8065 }
8066
8067 let subject_term = self.noun_phrase_to_term(&subject);
8068 let mut args = vec![subject_term.clone()];
8069
8070 let unknown = self.interner.intern("?");
8071
8072 if self.check_wh_word() {
8074 let wh_token = self.advance().kind.clone();
8075
8076 let is_who = matches!(wh_token, TokenType::Who);
8078 let is_what = matches!(wh_token, TokenType::What);
8079
8080 let is_sluicing = self.is_at_end() ||
8082 self.check(&TokenType::Period) ||
8083 self.check(&TokenType::Comma);
8084
8085 if is_sluicing {
8086 if let Some(template) = self.last_event_template.clone() {
8088 let wh_var = self.next_var_name();
8089
8090 let roles: Vec<_> = if is_who {
8092 std::iter::once((ThematicRole::Agent, Term::Variable(wh_var)))
8094 .chain(template.non_agent_roles.iter().cloned())
8095 .collect()
8096 } else if is_what {
8097 vec![
8099 (ThematicRole::Agent, subject_term.clone()),
8100 (ThematicRole::Theme, Term::Variable(wh_var)),
8101 ]
8102 } else {
8103 std::iter::once((ThematicRole::Agent, Term::Variable(wh_var)))
8105 .chain(template.non_agent_roles.iter().cloned())
8106 .collect()
8107 };
8108
8109 let event_var = self.get_event_var();
8110 let suppress_existential = self.drs.in_conditional_antecedent();
8111 if suppress_existential {
8112 let event_class = self.interner.intern("Event");
8113 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
8114 }
8115 let reconstructed = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
8116 event_var,
8117 verb: template.verb,
8118 roles: self.ctx.roles.alloc_slice(roles),
8119 modifiers: self.ctx.syms.alloc_slice(template.modifiers.clone()),
8120 suppress_existential,
8121 world: None,
8122 })));
8123
8124 let question = self.ctx.exprs.alloc(LogicExpr::Question {
8125 wh_variable: wh_var,
8126 body: reconstructed,
8127 });
8128
8129 let know_event_var = self.get_event_var();
8131 let suppress_existential2 = self.drs.in_conditional_antecedent();
8132 if suppress_existential2 {
8133 let event_class = self.interner.intern("Event");
8134 self.drs.introduce_referent(know_event_var, event_class, Gender::Neuter, Number::Singular);
8135 }
8136 let know_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
8137 event_var: know_event_var,
8138 verb,
8139 roles: self.ctx.roles.alloc_slice(vec![
8140 (ThematicRole::Agent, subject_term),
8141 (ThematicRole::Theme, Term::Proposition(question)),
8142 ]),
8143 modifiers: self.ctx.syms.alloc_slice(vec![]),
8144 suppress_existential: suppress_existential2,
8145 world: None,
8146 })));
8147
8148 return self.wrap_with_definiteness_full(&subject, know_event);
8149 }
8150 }
8151
8152 let embedded = self.parse_embedded_wh_clause()?;
8154 let question = self.ctx.exprs.alloc(LogicExpr::Question {
8155 wh_variable: self.interner.intern("x"),
8156 body: embedded,
8157 });
8158
8159 let know_event_var = self.get_event_var();
8161 let suppress_existential = self.drs.in_conditional_antecedent();
8162 if suppress_existential {
8163 let event_class = self.interner.intern("Event");
8164 self.drs.introduce_referent(know_event_var, event_class, Gender::Neuter, Number::Singular);
8165 }
8166 let know_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
8167 event_var: know_event_var,
8168 verb,
8169 roles: self.ctx.roles.alloc_slice(vec![
8170 (ThematicRole::Agent, subject_term),
8171 (ThematicRole::Theme, Term::Proposition(question)),
8172 ]),
8173 modifiers: self.ctx.syms.alloc_slice(vec![]),
8174 suppress_existential,
8175 world: None,
8176 })));
8177
8178 return self.wrap_with_definiteness_full(&subject, know_event);
8179 }
8180
8181 let mut object_term: Option<Term<'a>> = None;
8182 let mut second_object_term: Option<Term<'a>> = None;
8183 let mut object_superlative: Option<(Symbol, Symbol)> = None; if self.check(&TokenType::Reflexive) {
8185 self.advance();
8186 let term = self.noun_phrase_to_term(&subject);
8187 object_term = Some(term.clone());
8188 args.push(term);
8189
8190 if let TokenType::Particle(particle_sym) = self.peek().kind {
8192 let verb_str = self.interner.resolve(verb).to_lowercase();
8193 let particle_str = self.interner.resolve(particle_sym).to_lowercase();
8194 if let Some((phrasal_lemma, _class)) = crate::lexicon::lookup_phrasal_verb(&verb_str, &particle_str) {
8195 self.advance();
8196 verb = self.interner.intern(phrasal_lemma);
8197 }
8198 }
8199 } else if self.check_pronoun() {
8200 let token = self.advance().clone();
8201 if let TokenType::Pronoun { gender, number, .. } = token.kind {
8202 let resolved = self.resolve_pronoun(gender, number)?;
8203 let term = match resolved {
8204 ResolvedPronoun::Variable(s) => Term::Variable(s),
8205 ResolvedPronoun::Constant(s) => Term::Constant(s),
8206 };
8207 object_term = Some(term.clone());
8208 args.push(term);
8209
8210 if let TokenType::Particle(particle_sym) = self.peek().kind {
8212 let verb_str = self.interner.resolve(verb).to_lowercase();
8213 let particle_str = self.interner.resolve(particle_sym).to_lowercase();
8214 if let Some((phrasal_lemma, _class)) = crate::lexicon::lookup_phrasal_verb(&verb_str, &particle_str) {
8215 self.advance();
8216 verb = self.interner.intern(phrasal_lemma);
8217 }
8218 }
8219 }
8220 } else if self.check_quantifier() || self.check_article() {
8221 let (obj_quantifier, was_definite_article) = if self.check_quantifier() {
8223 (Some(self.advance().kind.clone()), false)
8224 } else {
8225 let art = self.advance().kind.clone();
8226 if let TokenType::Article(def) = art {
8227 if def == Definiteness::Indefinite {
8228 (Some(TokenType::Some), false)
8229 } else {
8230 (None, true) }
8232 } else {
8233 (None, false)
8234 }
8235 };
8236
8237 let object_np = self.parse_noun_phrase(false)?;
8238
8239 if let Some(adj) = object_np.superlative {
8241 object_superlative = Some((adj, object_np.noun));
8242 }
8243
8244 if let TokenType::Particle(particle_sym) = self.peek().kind {
8246 let verb_str = self.interner.resolve(verb).to_lowercase();
8247 let particle_str = self.interner.resolve(particle_sym).to_lowercase();
8248 if let Some((phrasal_lemma, _class)) = crate::lexicon::lookup_phrasal_verb(&verb_str, &particle_str) {
8249 self.advance(); verb = self.interner.intern(phrasal_lemma);
8251 }
8252 }
8253
8254 if let Some(obj_q) = obj_quantifier {
8255 let verb_str = self.interner.resolve(verb).to_lowercase();
8259 let is_opaque = lexicon::lookup_verb_db(&verb_str)
8260 .map(|meta| meta.features.contains(&lexicon::Feature::Opaque))
8261 .unwrap_or(false);
8262
8263 if is_opaque && matches!(obj_q, TokenType::Some) {
8264 let intension_term = Term::Intension(object_np.noun);
8266
8267 let event_var = self.get_event_var();
8269 let mut modifiers = self.collect_adverbs();
8270 let effective_time = self.pending_time.take().unwrap_or(verb_time);
8271 match effective_time {
8272 Time::Past => modifiers.push(self.interner.intern("Past")),
8273 Time::Future => modifiers.push(self.interner.intern("Future")),
8274 _ => {}
8275 }
8276
8277 let subject_term_for_event = self.noun_phrase_to_term(&subject);
8278 let roles = vec![
8279 (ThematicRole::Agent, subject_term_for_event),
8280 (ThematicRole::Theme, intension_term),
8281 ];
8282
8283 let suppress_existential = self.drs.in_conditional_antecedent();
8284 if suppress_existential {
8285 let event_class = self.interner.intern("Event");
8286 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
8287 }
8288 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
8289 event_var,
8290 verb,
8291 roles: self.ctx.roles.alloc_slice(roles),
8292 modifiers: self.ctx.syms.alloc_slice(modifiers),
8293 suppress_existential,
8294 world: None,
8295 })));
8296
8297 return self.wrap_with_definiteness_full(&subject, neo_event);
8298 }
8299
8300 let obj_var = self.next_var_name();
8301
8302 let obj_gender = Self::infer_noun_gender(self.interner.resolve(object_np.noun));
8304 let obj_number = if Self::is_plural_noun(self.interner.resolve(object_np.noun)) {
8305 Number::Plural
8306 } else {
8307 Number::Singular
8308 };
8309 if object_np.definiteness == Some(Definiteness::Definite) {
8311 self.drs.introduce_referent_with_source(obj_var, object_np.noun, obj_gender, obj_number, ReferentSource::MainClause);
8312 } else {
8313 self.drs.introduce_referent(obj_var, object_np.noun, obj_gender, obj_number);
8314 }
8315
8316 let type_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
8317 name: object_np.noun,
8318 args: self.ctx.terms.alloc_slice([Term::Variable(obj_var)]),
8319 world: None,
8320 });
8321
8322 let obj_restriction = if self.check(&TokenType::That) || self.check(&TokenType::Who) {
8323 self.advance();
8324 let rel_clause = self.parse_relative_clause(obj_var)?;
8325 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8326 left: type_pred,
8327 op: TokenType::And,
8328 right: rel_clause,
8329 })
8330 } else {
8331 type_pred
8332 };
8333
8334 let event_var = self.get_event_var();
8335 let mut modifiers = self.collect_adverbs();
8336 let effective_time = self.pending_time.take().unwrap_or(verb_time);
8337 match effective_time {
8338 Time::Past => modifiers.push(self.interner.intern("Past")),
8339 Time::Future => modifiers.push(self.interner.intern("Future")),
8340 _ => {}
8341 }
8342
8343 let subject_term_for_event = self.noun_phrase_to_term(&subject);
8344 let roles = vec![
8345 (ThematicRole::Agent, subject_term_for_event),
8346 (ThematicRole::Theme, Term::Variable(obj_var)),
8347 ];
8348
8349 let template_roles = vec![
8352 (ThematicRole::Agent, subject_term_for_event),
8353 (ThematicRole::Theme, Term::Constant(object_np.noun)),
8354 ];
8355 self.capture_event_template(verb, &template_roles, &modifiers);
8356
8357 let suppress_existential = self.drs.in_conditional_antecedent();
8358 if suppress_existential {
8359 let event_class = self.interner.intern("Event");
8360 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
8361 }
8362 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
8363 event_var,
8364 verb,
8365 roles: self.ctx.roles.alloc_slice(roles),
8366 modifiers: self.ctx.syms.alloc_slice(modifiers),
8367 suppress_existential,
8368 world: None,
8369 })));
8370
8371 let obj_kind = match obj_q {
8372 TokenType::All => QuantifierKind::Universal,
8373 TokenType::Some => QuantifierKind::Existential,
8374 TokenType::No => QuantifierKind::Universal,
8375 TokenType::Most => QuantifierKind::Most,
8376 TokenType::Few => QuantifierKind::Few,
8377 TokenType::Many => QuantifierKind::Many,
8378 TokenType::Cardinal(n) => QuantifierKind::Cardinal(n),
8379 TokenType::AtLeast(n) => QuantifierKind::AtLeast(n),
8380 TokenType::AtMost(n) => QuantifierKind::AtMost(n),
8381 _ => QuantifierKind::Existential,
8382 };
8383
8384 let obj_body = match obj_q {
8385 TokenType::All => self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8386 left: obj_restriction,
8387 op: TokenType::If,
8388 right: neo_event,
8389 }),
8390 TokenType::No => {
8391 let neg = self.ctx.exprs.alloc(LogicExpr::UnaryOp {
8392 op: TokenType::Not,
8393 operand: neo_event,
8394 });
8395 self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8396 left: obj_restriction,
8397 op: TokenType::If,
8398 right: neg,
8399 })
8400 }
8401 _ => self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8402 left: obj_restriction,
8403 op: TokenType::And,
8404 right: neo_event,
8405 }),
8406 };
8407
8408 let obj_quantified = self.ctx.exprs.alloc(LogicExpr::Quantifier {
8410 kind: obj_kind,
8411 variable: obj_var,
8412 body: obj_body,
8413 island_id: self.current_island,
8414 });
8415
8416 return self.wrap_with_definiteness_full(&subject, obj_quantified);
8418 } else {
8419 if was_definite_article {
8424 let obj_gender = Self::infer_noun_gender(self.interner.resolve(object_np.noun));
8425 let obj_number = if Self::is_plural_noun(self.interner.resolve(object_np.noun)) {
8426 Number::Plural
8427 } else {
8428 Number::Singular
8429 };
8430 self.drs.introduce_referent_with_source(object_np.noun, object_np.noun, obj_gender, obj_number, ReferentSource::MainClause);
8432 }
8433
8434 let term = self.noun_phrase_to_term(&object_np);
8435 object_term = Some(term.clone());
8436 args.push(term);
8437 }
8438 } else if self.check_focus() {
8439 let focus_kind = if let TokenType::Focus(k) = self.advance().kind {
8440 k
8441 } else {
8442 FocusKind::Only
8443 };
8444
8445 let event_var = self.get_event_var();
8446 let mut modifiers = self.collect_adverbs();
8447 let effective_time = self.pending_time.take().unwrap_or(verb_time);
8448 match effective_time {
8449 Time::Past => modifiers.push(self.interner.intern("Past")),
8450 Time::Future => modifiers.push(self.interner.intern("Future")),
8451 _ => {}
8452 }
8453
8454 let subject_term_for_event = self.noun_phrase_to_term(&subject);
8455
8456 if self.check_preposition() {
8457 let prep_token = self.advance().clone();
8458 let prep_name = if let TokenType::Preposition(sym) = prep_token.kind {
8459 sym
8460 } else {
8461 self.interner.intern("to")
8462 };
8463 let pp_obj = self.parse_noun_phrase(false)?;
8464 let pp_obj_term = Term::Constant(pp_obj.noun);
8465
8466 let roles = vec![(ThematicRole::Agent, subject_term_for_event)];
8467 let suppress_existential = self.drs.in_conditional_antecedent();
8468 if suppress_existential {
8469 let event_class = self.interner.intern("Event");
8470 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
8471 }
8472 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
8473 event_var,
8474 verb,
8475 roles: self.ctx.roles.alloc_slice(roles),
8476 modifiers: self.ctx.syms.alloc_slice(modifiers),
8477 suppress_existential,
8478 world: None,
8479 })));
8480
8481 let pp_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
8482 name: prep_name,
8483 args: self.ctx.terms.alloc_slice([Term::Variable(event_var), pp_obj_term]),
8484 world: None,
8485 });
8486
8487 let with_pp = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8488 left: neo_event,
8489 op: TokenType::And,
8490 right: pp_pred,
8491 });
8492
8493 let focused_ref = self.ctx.terms.alloc(pp_obj_term);
8494 return Ok(self.ctx.exprs.alloc(LogicExpr::Focus {
8495 kind: focus_kind,
8496 focused: focused_ref,
8497 scope: with_pp,
8498 }));
8499 }
8500
8501 let focused_np = self.parse_noun_phrase(false)?;
8502 let focused_term = self.noun_phrase_to_term(&focused_np);
8503 args.push(focused_term.clone());
8504
8505 let roles = vec![
8506 (ThematicRole::Agent, subject_term_for_event),
8507 (ThematicRole::Theme, focused_term.clone()),
8508 ];
8509
8510 let suppress_existential = self.drs.in_conditional_antecedent();
8511 if suppress_existential {
8512 let event_class = self.interner.intern("Event");
8513 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
8514 }
8515 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
8516 event_var,
8517 verb,
8518 roles: self.ctx.roles.alloc_slice(roles),
8519 modifiers: self.ctx.syms.alloc_slice(modifiers),
8520 suppress_existential,
8521 world: None,
8522 })));
8523
8524 let focused_ref = self.ctx.terms.alloc(focused_term);
8525 return Ok(self.ctx.exprs.alloc(LogicExpr::Focus {
8526 kind: focus_kind,
8527 focused: focused_ref,
8528 scope: neo_event,
8529 }));
8530 } else if self.check_number() {
8531 let measure = self.parse_measure_phrase()?;
8533
8534 if self.check_content_word() {
8536 let noun_sym = self.consume_content_word()?;
8537 let count_term = *measure;
8539 object_term = Some(count_term.clone());
8540 args.push(count_term);
8541 second_object_term = Some(Term::Constant(noun_sym));
8542 args.push(Term::Constant(noun_sym));
8543 } else {
8544 object_term = Some(*measure);
8546 args.push(*measure);
8547 }
8548 } else if self.check_content_word() || self.check_article() {
8549 let object = self.parse_noun_phrase(false)?;
8550 if let Some(adj) = object.superlative {
8551 object_superlative = Some((adj, object.noun));
8552 }
8553
8554 let mut all_objects: Vec<Symbol> = vec![object.noun];
8556
8557 while self.check(&TokenType::And) {
8559 let saved = self.current;
8560 self.advance(); if self.check_content_word() || self.check_article() {
8562 let next_obj = match self.parse_noun_phrase(false) {
8563 Ok(np) => np,
8564 Err(_) => {
8565 self.current = saved;
8566 break;
8567 }
8568 };
8569 all_objects.push(next_obj.noun);
8570 } else {
8571 self.current = saved;
8572 break;
8573 }
8574 }
8575
8576 if self.check(&TokenType::Respectively) {
8578 let respectively_span = self.peek().span;
8579 if all_objects.len() > 1 {
8581 return Err(ParseError {
8582 kind: ParseErrorKind::RespectivelyLengthMismatch {
8583 subject_count: 1,
8584 object_count: all_objects.len(),
8585 },
8586 span: respectively_span,
8587 });
8588 }
8589 self.advance(); }
8592
8593 let term = self.noun_phrase_to_term(&object);
8595 object_term = Some(term.clone());
8596 args.push(term.clone());
8597
8598 if all_objects.len() > 1 {
8600 let obj_members: Vec<Term<'a>> = all_objects.iter()
8601 .map(|o| Term::Constant(*o))
8602 .collect();
8603 let obj_group = Term::Group(self.ctx.terms.alloc_slice(obj_members));
8604 args.pop();
8606 args.push(obj_group);
8607 }
8608
8609 if let TokenType::Particle(particle_sym) = self.peek().kind {
8611 let verb_str = self.interner.resolve(verb).to_lowercase();
8612 let particle_str = self.interner.resolve(particle_sym).to_lowercase();
8613 if let Some((phrasal_lemma, _class)) = crate::lexicon::lookup_phrasal_verb(&verb_str, &particle_str) {
8614 self.advance(); verb = self.interner.intern(phrasal_lemma);
8616 }
8617 }
8618
8619 if self.check_number() {
8621 let measure = self.parse_measure_phrase()?;
8622 second_object_term = Some(*measure);
8623 args.push(*measure);
8624 }
8625 else {
8627 let verb_str = self.interner.resolve(verb);
8628 if Lexer::is_ditransitive_verb(verb_str) && (self.check_content_word() || self.check_article()) {
8629 let second_np = self.parse_noun_phrase(false)?;
8630 let second_term = self.noun_phrase_to_term(&second_np);
8631 second_object_term = Some(second_term.clone());
8632 args.push(second_term);
8633 }
8634 }
8635 }
8636
8637 let mut pp_predicates: Vec<&'a LogicExpr<'a>> = Vec::new();
8638 while self.check_preposition() || self.check_to() {
8639 let prep_token = self.advance().clone();
8640 let prep_name = if let TokenType::Preposition(sym) = prep_token.kind {
8641 sym
8642 } else if matches!(prep_token.kind, TokenType::To) {
8643 self.interner.intern("To")
8644 } else {
8645 continue;
8646 };
8647
8648 let pp_obj_term = if self.check(&TokenType::Reflexive) {
8649 self.advance();
8650 self.noun_phrase_to_term(&subject)
8651 } else if self.check_pronoun() {
8652 let token = self.advance().clone();
8653 if let TokenType::Pronoun { gender, number, .. } = token.kind {
8654 let resolved = self.resolve_pronoun(gender, number)?;
8655 match resolved {
8656 ResolvedPronoun::Variable(s) => Term::Variable(s),
8657 ResolvedPronoun::Constant(s) => Term::Constant(s),
8658 }
8659 } else {
8660 continue;
8661 }
8662 } else if self.check_content_word() || self.check_article() {
8663 let prep_obj = self.parse_noun_phrase(false)?;
8664 self.noun_phrase_to_term(&prep_obj)
8665 } else {
8666 continue;
8667 };
8668
8669 if self.pp_attach_to_noun {
8670 if let Some(ref obj) = object_term {
8671 let pp_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
8673 name: prep_name,
8674 args: self.ctx.terms.alloc_slice([obj.clone(), pp_obj_term]),
8675 world: None,
8676 });
8677 pp_predicates.push(pp_pred);
8678 } else {
8679 args.push(pp_obj_term);
8680 }
8681 } else {
8682 let event_sym = self.get_event_var();
8684 let pp_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
8685 name: prep_name,
8686 args: self.ctx.terms.alloc_slice([Term::Variable(event_sym), pp_obj_term]),
8687 world: None,
8688 });
8689 pp_predicates.push(pp_pred);
8690 }
8691 }
8692
8693 if self.check(&TokenType::That) || self.check(&TokenType::Who) {
8695 self.advance();
8696 let rel_var = self.next_var_name();
8697 let rel_pred = self.parse_relative_clause(rel_var)?;
8698 pp_predicates.push(rel_pred);
8699 }
8700
8701 let mut modifiers = self.collect_adverbs();
8703
8704 let effective_time = self.pending_time.take().unwrap_or(verb_time);
8706 match effective_time {
8707 Time::Past => modifiers.push(self.interner.intern("Past")),
8708 Time::Future => modifiers.push(self.interner.intern("Future")),
8709 _ => {}
8710 }
8711
8712 if verb_aspect == Aspect::Progressive {
8714 modifiers.push(self.interner.intern("Progressive"));
8715 } else if verb_aspect == Aspect::Perfect {
8716 modifiers.push(self.interner.intern("Perfect"));
8717 }
8718
8719 let mut roles: Vec<(ThematicRole, Term<'a>)> = Vec::new();
8721
8722 let verb_str_for_check = self.interner.resolve(verb).to_lowercase();
8724 let is_unaccusative = crate::lexicon::lookup_verb_db(&verb_str_for_check)
8725 .map(|meta| meta.features.contains(&crate::lexicon::Feature::Unaccusative))
8726 .unwrap_or(false);
8727
8728 let has_object = object_term.is_some() || second_object_term.is_some();
8730 let subject_role = if is_unaccusative && !has_object {
8731 ThematicRole::Theme
8732 } else {
8733 ThematicRole::Agent
8734 };
8735
8736 roles.push((subject_role, subject_term));
8737 if let Some(second_obj) = second_object_term {
8738 if let Some(first_obj) = object_term {
8740 roles.push((ThematicRole::Recipient, first_obj));
8741 }
8742 roles.push((ThematicRole::Theme, second_obj));
8743 } else if let Some(obj) = object_term {
8744 roles.push((ThematicRole::Theme, obj));
8746 }
8747
8748 let event_var = self.get_event_var();
8750
8751 self.capture_event_template(verb, &roles, &modifiers);
8753
8754 let suppress_existential = self.drs.in_conditional_antecedent();
8756 if suppress_existential {
8757 let event_class = self.interner.intern("Event");
8758 self.drs.introduce_referent(event_var, event_class, Gender::Neuter, Number::Singular);
8759 }
8760 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
8761 event_var,
8762 verb,
8763 roles: self.ctx.roles.alloc_slice(roles),
8764 modifiers: self.ctx.syms.alloc_slice(modifiers),
8765 suppress_existential,
8766 world: None,
8767 })));
8768
8769 let with_pps = if pp_predicates.is_empty() {
8771 neo_event
8772 } else {
8773 let mut combined = neo_event;
8774 for pp in pp_predicates {
8775 combined = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8776 left: combined,
8777 op: TokenType::And,
8778 right: pp,
8779 });
8780 }
8781 combined
8782 };
8783
8784 let with_aspect = if verb_aspect == Aspect::Progressive {
8786 if verb_class == crate::lexicon::VerbClass::Semelfactive {
8788 self.ctx.exprs.alloc(LogicExpr::Aspectual {
8789 operator: AspectOperator::Iterative,
8790 body: with_pps,
8791 })
8792 } else {
8793 self.ctx.exprs.alloc(LogicExpr::Aspectual {
8795 operator: AspectOperator::Progressive,
8796 body: with_pps,
8797 })
8798 }
8799 } else if verb_aspect == Aspect::Perfect {
8800 self.ctx.exprs.alloc(LogicExpr::Aspectual {
8801 operator: AspectOperator::Perfect,
8802 body: with_pps,
8803 })
8804 } else if effective_time == Time::Present && verb_aspect == Aspect::Simple {
8805 if !verb_class.is_stative() {
8807 self.ctx.exprs.alloc(LogicExpr::Aspectual {
8808 operator: AspectOperator::Habitual,
8809 body: with_pps,
8810 })
8811 } else {
8812 with_pps
8814 }
8815 } else {
8816 with_pps
8817 };
8818
8819 let with_adverbs = with_aspect;
8820
8821 let with_temporal = if self.check_temporal_adverb() {
8823 let anchor = if let TokenType::TemporalAdverb(adv) = self.advance().kind.clone() {
8824 adv
8825 } else {
8826 panic!("Expected temporal adverb");
8827 };
8828 self.ctx.exprs.alloc(LogicExpr::TemporalAnchor {
8829 anchor,
8830 body: with_adverbs,
8831 })
8832 } else {
8833 with_adverbs
8834 };
8835
8836 let wrapped = self.wrap_with_definiteness_full(&subject, with_temporal)?;
8837
8838 if let Some((adj, noun)) = object_superlative {
8840 let superlative_expr = self.ctx.exprs.alloc(LogicExpr::Superlative {
8841 adjective: adj,
8842 subject: self.ctx.terms.alloc(Term::Constant(noun)),
8843 domain: noun,
8844 });
8845 return Ok(self.ctx.exprs.alloc(LogicExpr::BinaryOp {
8846 left: wrapped,
8847 op: TokenType::And,
8848 right: superlative_expr,
8849 }));
8850 }
8851
8852 return Ok(wrapped);
8853 }
8854
8855 Ok(self.ctx.exprs.alloc(LogicExpr::Atom(subject.noun)))
8856 }
8857
8858 fn check_preposition(&self) -> bool {
8859 matches!(self.peek().kind, TokenType::Preposition(_))
8860 }
8861
8862 fn check_by_preposition(&self) -> bool {
8863 if let TokenType::Preposition(p) = self.peek().kind {
8864 p.is(self.interner, "by")
8865 } else {
8866 false
8867 }
8868 }
8869
8870 fn check_preposition_is(&self, word: &str) -> bool {
8871 if let TokenType::Preposition(p) = self.peek().kind {
8872 p.is(self.interner, word)
8873 } else {
8874 false
8875 }
8876 }
8877
8878 fn check_word(&self, word: &str) -> bool {
8880 let token = self.peek();
8881 let lexeme = self.interner.resolve(token.lexeme);
8882 lexeme.eq_ignore_ascii_case(word)
8883 }
8884
8885 fn peek_word_at(&self, offset: usize, word: &str) -> bool {
8886 if self.current + offset >= self.tokens.len() {
8887 return false;
8888 }
8889 let token = &self.tokens[self.current + offset];
8890 let lexeme = self.interner.resolve(token.lexeme);
8891 lexeme.eq_ignore_ascii_case(word)
8892 }
8893
8894 fn check_to_preposition(&self) -> bool {
8895 match self.peek().kind {
8896 TokenType::To => true,
8897 TokenType::Preposition(p) => p.is(self.interner, "to"),
8898 _ => false,
8899 }
8900 }
8901
8902 fn check_content_word(&self) -> bool {
8903 match &self.peek().kind {
8904 TokenType::Noun(_)
8905 | TokenType::Adjective(_)
8906 | TokenType::NonIntersectiveAdjective(_)
8907 | TokenType::Verb { .. }
8908 | TokenType::ProperName(_)
8909 | TokenType::Article(_) => true,
8910 TokenType::Ambiguous { primary, alternatives } => {
8911 Self::is_content_word_type(primary)
8912 || alternatives.iter().any(Self::is_content_word_type)
8913 }
8914 _ => false,
8915 }
8916 }
8917
8918 fn is_content_word_type(t: &TokenType) -> bool {
8919 matches!(
8920 t,
8921 TokenType::Noun(_)
8922 | TokenType::Adjective(_)
8923 | TokenType::NonIntersectiveAdjective(_)
8924 | TokenType::Verb { .. }
8925 | TokenType::ProperName(_)
8926 | TokenType::Article(_)
8927 )
8928 }
8929
8930 fn check_verb(&self) -> bool {
8931 match &self.peek().kind {
8932 TokenType::Verb { .. } => true,
8933 TokenType::Ambiguous { primary, alternatives } => {
8934 if self.noun_priority_mode {
8935 return false;
8936 }
8937 matches!(**primary, TokenType::Verb { .. })
8938 || alternatives.iter().any(|t| matches!(t, TokenType::Verb { .. }))
8939 }
8940 _ => false,
8941 }
8942 }
8943
8944 fn check_adverb(&self) -> bool {
8945 matches!(self.peek().kind, TokenType::Adverb(_))
8946 }
8947
8948 fn check_performative(&self) -> bool {
8949 matches!(self.peek().kind, TokenType::Performative(_))
8950 }
8951
8952 fn collect_adverbs(&mut self) -> Vec<Symbol> {
8953 let mut adverbs = Vec::new();
8954 while self.check_adverb() {
8955 if let TokenType::Adverb(adv) = self.advance().kind.clone() {
8956 adverbs.push(adv);
8957 }
8958 if self.check(&TokenType::And) {
8960 self.advance();
8961 }
8962 }
8963 adverbs
8964 }
8965
8966 fn check_auxiliary(&self) -> bool {
8967 matches!(self.peek().kind, TokenType::Auxiliary(_))
8968 }
8969
8970 fn is_true_auxiliary_usage(&self) -> bool {
8977 if self.current + 1 >= self.tokens.len() {
8978 return false;
8979 }
8980
8981 let next_token = &self.tokens[self.current + 1].kind;
8982
8983 if matches!(next_token, TokenType::Not) {
8985 return true;
8986 }
8987
8988 if matches!(next_token, TokenType::Verb { .. }) {
8990 return true;
8991 }
8992
8993 if matches!(
8995 next_token,
8996 TokenType::Pronoun { .. }
8997 | TokenType::Article(_)
8998 | TokenType::Noun(_)
8999 | TokenType::ProperName(_)
9000 ) {
9001 return false;
9002 }
9003
9004 true
9006 }
9007
9008 fn check_auxiliary_as_main_verb(&self) -> bool {
9011 if let TokenType::Auxiliary(Time::Past) = self.peek().kind {
9012 if self.current + 1 < self.tokens.len() {
9014 let next = &self.tokens[self.current + 1].kind;
9015 matches!(
9016 next,
9017 TokenType::Pronoun { .. }
9018 | TokenType::Article(_)
9019 | TokenType::Noun(_)
9020 | TokenType::ProperName(_)
9021 )
9022 } else {
9023 false
9024 }
9025 } else {
9026 false
9027 }
9028 }
9029
9030 fn parse_do_as_main_verb(&mut self, subject_term: Term<'a>) -> ParseResult<&'a LogicExpr<'a>> {
9033 let aux_token = self.advance();
9035 let verb_time = if let TokenType::Auxiliary(time) = aux_token.kind {
9036 time
9037 } else {
9038 Time::Past
9039 };
9040
9041 let verb = self.interner.intern("Do");
9043
9044 let object_term = if let TokenType::Pronoun { .. } = self.peek().kind {
9046 self.advance();
9048 let it_sym = self.interner.intern("it");
9051 Term::Constant(it_sym)
9052 } else {
9053 let object = self.parse_noun_phrase(false)?;
9054 self.noun_phrase_to_term(&object)
9055 };
9056
9057 let event_var = self.get_event_var();
9059 let suppress_existential = self.drs.in_conditional_antecedent();
9060
9061 let mut modifiers = Vec::new();
9062 if verb_time == Time::Past {
9063 modifiers.push(self.interner.intern("Past"));
9064 } else if verb_time == Time::Future {
9065 modifiers.push(self.interner.intern("Future"));
9066 }
9067
9068 let neo_event = self.ctx.exprs.alloc(LogicExpr::NeoEvent(Box::new(NeoEventData {
9069 event_var,
9070 verb,
9071 roles: self.ctx.roles.alloc_slice(vec![
9072 (ThematicRole::Agent, subject_term),
9073 (ThematicRole::Theme, object_term),
9074 ]),
9075 modifiers: self.ctx.syms.alloc_slice(modifiers),
9076 suppress_existential,
9077 world: None,
9078 })));
9079
9080 Ok(neo_event)
9081 }
9082
9083 fn check_to(&self) -> bool {
9084 matches!(self.peek().kind, TokenType::To)
9085 }
9086
9087 fn has_modal_subordination_ahead(&self) -> bool {
9091 for i in self.current..self.tokens.len() {
9094 match &self.tokens[i].kind {
9095 TokenType::Would | TokenType::Could | TokenType::Should | TokenType::Might => {
9096 return true;
9097 }
9098 TokenType::Period | TokenType::EOF => break,
9100 _ => {}
9101 }
9102 }
9103 false
9104 }
9105
9106 fn consume_verb(&mut self) -> Symbol {
9107 let t = self.advance().clone();
9108 match t.kind {
9109 TokenType::Verb { lemma, .. } => lemma,
9110 TokenType::Ambiguous { primary, .. } => match *primary {
9111 TokenType::Verb { lemma, .. } => lemma,
9112 _ => panic!("Expected verb in Ambiguous primary, got {:?}", primary),
9113 },
9114 _ => panic!("Expected verb, got {:?}", t.kind),
9115 }
9116 }
9117
9118 fn consume_verb_with_metadata(&mut self) -> (Symbol, Time, Aspect, VerbClass) {
9119 let t = self.advance().clone();
9120 match t.kind {
9121 TokenType::Verb { lemma, time, aspect, class } => (lemma, time, aspect, class),
9122 TokenType::Ambiguous { primary, .. } => match *primary {
9123 TokenType::Verb { lemma, time, aspect, class } => (lemma, time, aspect, class),
9124 _ => panic!("Expected verb in Ambiguous primary, got {:?}", primary),
9125 },
9126 _ => panic!("Expected verb, got {:?}", t.kind),
9127 }
9128 }
9129
9130 fn match_token(&mut self, types: &[TokenType]) -> bool {
9131 for t in types {
9132 if self.check(t) {
9133 self.advance();
9134 return true;
9135 }
9136 }
9137 false
9138 }
9139
9140 fn check_quantifier(&self) -> bool {
9141 matches!(
9142 self.peek().kind,
9143 TokenType::All
9144 | TokenType::No
9145 | TokenType::Some
9146 | TokenType::Any
9147 | TokenType::Most
9148 | TokenType::Few
9149 | TokenType::Many
9150 | TokenType::Cardinal(_)
9151 | TokenType::AtLeast(_)
9152 | TokenType::AtMost(_)
9153 )
9154 }
9155
9156 fn check_npi_quantifier(&self) -> bool {
9157 matches!(
9158 self.peek().kind,
9159 TokenType::Nobody | TokenType::Nothing | TokenType::NoOne
9160 )
9161 }
9162
9163 fn check_npi_object(&self) -> bool {
9164 matches!(
9165 self.peek().kind,
9166 TokenType::Anything | TokenType::Anyone
9167 )
9168 }
9169
9170 fn check_temporal_npi(&self) -> bool {
9171 matches!(
9172 self.peek().kind,
9173 TokenType::Ever | TokenType::Never
9174 )
9175 }
9176
9177 fn parse_npi_quantified(&mut self) -> ParseResult<&'a LogicExpr<'a>> {
9178 let npi_token = self.advance().kind.clone();
9179 let var_name = self.next_var_name();
9180
9181 let (restriction_name, is_person) = match npi_token {
9182 TokenType::Nobody | TokenType::NoOne => ("Person", true),
9183 TokenType::Nothing => ("Thing", false),
9184 _ => ("Thing", false),
9185 };
9186
9187 let restriction_sym = self.interner.intern(restriction_name);
9188 let subject_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
9189 name: restriction_sym,
9190 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
9191 world: None,
9192 });
9193
9194 self.negative_depth += 1;
9195
9196 let verb = self.consume_verb();
9197
9198 if self.check_npi_object() {
9199 let obj_npi_token = self.advance().kind.clone();
9200 let obj_var = self.next_var_name();
9201
9202 let obj_restriction_name = match obj_npi_token {
9203 TokenType::Anything => "Thing",
9204 TokenType::Anyone => "Person",
9205 _ => "Thing",
9206 };
9207
9208 let obj_restriction_sym = self.interner.intern(obj_restriction_name);
9209 let obj_restriction = self.ctx.exprs.alloc(LogicExpr::Predicate {
9210 name: obj_restriction_sym,
9211 args: self.ctx.terms.alloc_slice([Term::Variable(obj_var)]),
9212 world: None,
9213 });
9214
9215 let verb_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
9216 name: verb,
9217 args: self.ctx.terms.alloc_slice([Term::Variable(var_name), Term::Variable(obj_var)]),
9218 world: None,
9219 });
9220
9221 let verb_and_obj = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
9222 left: obj_restriction,
9223 op: TokenType::And,
9224 right: verb_pred,
9225 });
9226
9227 let inner_existential = self.ctx.exprs.alloc(LogicExpr::Quantifier {
9228 kind: crate::ast::QuantifierKind::Existential,
9229 variable: obj_var,
9230 body: verb_and_obj,
9231 island_id: self.current_island,
9232 });
9233
9234 self.negative_depth -= 1;
9235
9236 let negated = self.ctx.exprs.alloc(LogicExpr::UnaryOp {
9237 op: TokenType::Not,
9238 operand: inner_existential,
9239 });
9240
9241 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
9242 left: subject_pred,
9243 op: TokenType::If,
9244 right: negated,
9245 });
9246
9247 return Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
9248 kind: crate::ast::QuantifierKind::Universal,
9249 variable: var_name,
9250 body,
9251 island_id: self.current_island,
9252 }));
9253 }
9254
9255 let verb_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
9256 name: verb,
9257 args: self.ctx.terms.alloc_slice([Term::Variable(var_name)]),
9258 world: None,
9259 });
9260
9261 self.negative_depth -= 1;
9262
9263 let negated_verb = self.ctx.exprs.alloc(LogicExpr::UnaryOp {
9264 op: TokenType::Not,
9265 operand: verb_pred,
9266 });
9267
9268 let body = self.ctx.exprs.alloc(LogicExpr::BinaryOp {
9269 left: subject_pred,
9270 op: TokenType::If,
9271 right: negated_verb,
9272 });
9273
9274 Ok(self.ctx.exprs.alloc(LogicExpr::Quantifier {
9275 kind: crate::ast::QuantifierKind::Universal,
9276 variable: var_name,
9277 body,
9278 island_id: self.current_island,
9279 }))
9280 }
9281
9282 fn parse_temporal_npi(&mut self) -> ParseResult<&'a LogicExpr<'a>> {
9283 let npi_token = self.advance().kind.clone();
9284 let is_never = matches!(npi_token, TokenType::Never);
9285
9286 let subject = self.parse_noun_phrase(true)?;
9287
9288 if is_never {
9289 self.negative_depth += 1;
9290 }
9291
9292 let verb = self.consume_verb();
9293 let verb_pred = self.ctx.exprs.alloc(LogicExpr::Predicate {
9294 name: verb,
9295 args: self.ctx.terms.alloc_slice([Term::Constant(subject.noun)]),
9296 world: None,
9297 });
9298
9299 if is_never {
9300 self.negative_depth -= 1;
9301 Ok(self.ctx.exprs.alloc(LogicExpr::UnaryOp {
9302 op: TokenType::Not,
9303 operand: verb_pred,
9304 }))
9305 } else {
9306 Ok(verb_pred)
9307 }
9308 }
9309
9310 fn check(&self, kind: &TokenType) -> bool {
9311 if self.is_at_end() {
9312 return false;
9313 }
9314 std::mem::discriminant(&self.peek().kind) == std::mem::discriminant(kind)
9315 }
9316
9317 fn check_any(&self, kinds: &[TokenType]) -> bool {
9318 if self.is_at_end() {
9319 return false;
9320 }
9321 let current = std::mem::discriminant(&self.peek().kind);
9322 kinds.iter().any(|k| std::mem::discriminant(k) == current)
9323 }
9324
9325 fn check_article(&self) -> bool {
9326 matches!(self.peek().kind, TokenType::Article(_))
9327 }
9328
9329 fn advance(&mut self) -> &Token {
9330 if !self.is_at_end() {
9331 self.current += 1;
9332 }
9333 self.previous()
9334 }
9335
9336 fn is_at_end(&self) -> bool {
9337 self.peek().kind == TokenType::EOF
9338 }
9339
9340 fn peek(&self) -> &Token {
9341 &self.tokens[self.current]
9342 }
9343
9344 fn peek_next_is_string_literal(&self) -> bool {
9347 self.tokens.get(self.current + 1)
9348 .map(|t| matches!(t.kind, TokenType::StringLiteral(_)))
9349 .unwrap_or(false)
9350 }
9351
9352 fn previous(&self) -> &Token {
9353 &self.tokens[self.current - 1]
9354 }
9355
9356 fn current_span(&self) -> crate::token::Span {
9357 self.peek().span
9358 }
9359
9360 fn consume(&mut self, kind: TokenType) -> ParseResult<&Token> {
9361 if self.check(&kind) {
9362 Ok(self.advance())
9363 } else {
9364 Err(ParseError {
9365 kind: ParseErrorKind::UnexpectedToken {
9366 expected: kind,
9367 found: self.peek().kind.clone(),
9368 },
9369 span: self.current_span(),
9370 })
9371 }
9372 }
9373
9374 fn consume_content_word(&mut self) -> ParseResult<Symbol> {
9375 let t = self.advance().clone();
9376 match t.kind {
9377 TokenType::Noun(s) | TokenType::Adjective(s) | TokenType::NonIntersectiveAdjective(s) => Ok(s),
9378 TokenType::Article(_) => Ok(t.lexeme),
9380 TokenType::Number(s) => Ok(s),
9382 TokenType::ProperName(s) => {
9383 if self.mode == ParserMode::Imperative {
9385 if !self.drs.has_referent_by_variable(s) {
9386 return Err(ParseError {
9387 kind: ParseErrorKind::UndefinedVariable {
9388 name: self.interner.resolve(s).to_string()
9389 },
9390 span: t.span,
9391 });
9392 }
9393 return Ok(s);
9394 }
9395
9396 let s_str = self.interner.resolve(s);
9398 let gender = Self::infer_gender(s_str);
9399
9400 self.drs.introduce_proper_name(s, s, gender);
9402
9403 Ok(s)
9404 }
9405 TokenType::Verb { lemma, .. } => Ok(lemma),
9406 TokenType::Ambiguous { primary, .. } => {
9407 match *primary {
9408 TokenType::Noun(s) | TokenType::Adjective(s) | TokenType::NonIntersectiveAdjective(s) => Ok(s),
9409 TokenType::Verb { lemma, .. } => Ok(lemma),
9410 TokenType::ProperName(s) => {
9411 if self.mode == ParserMode::Imperative {
9413 if !self.drs.has_referent_by_variable(s) {
9414 return Err(ParseError {
9415 kind: ParseErrorKind::UndefinedVariable {
9416 name: self.interner.resolve(s).to_string()
9417 },
9418 span: t.span,
9419 });
9420 }
9421 return Ok(s);
9422 }
9423 let s_str = self.interner.resolve(s);
9425 let gender = Self::infer_gender(s_str);
9426 self.drs.introduce_proper_name(s, s, gender);
9427 Ok(s)
9428 }
9429 _ => Err(ParseError {
9430 kind: ParseErrorKind::ExpectedContentWord { found: *primary },
9431 span: self.current_span(),
9432 }),
9433 }
9434 }
9435 other => Err(ParseError {
9436 kind: ParseErrorKind::ExpectedContentWord { found: other },
9437 span: self.current_span(),
9438 }),
9439 }
9440 }
9441
9442 fn consume_copula(&mut self) -> ParseResult<()> {
9443 if self.match_token(&[TokenType::Is, TokenType::Are, TokenType::Was, TokenType::Were]) {
9444 Ok(())
9445 } else {
9446 Err(ParseError {
9447 kind: ParseErrorKind::ExpectedCopula,
9448 span: self.current_span(),
9449 })
9450 }
9451 }
9452
9453 fn check_comparative(&self) -> bool {
9454 matches!(self.peek().kind, TokenType::Comparative(_))
9455 }
9456
9457 fn is_contact_clause_pattern(&self) -> bool {
9458 let mut pos = self.current;
9461
9462 if pos < self.tokens.len() && matches!(self.tokens[pos].kind, TokenType::Article(_)) {
9464 pos += 1;
9465 } else {
9466 return false;
9467 }
9468
9469 while pos < self.tokens.len() && matches!(self.tokens[pos].kind, TokenType::Adjective(_)) {
9471 pos += 1;
9472 }
9473
9474 if pos < self.tokens.len() && matches!(self.tokens[pos].kind, TokenType::Noun(_) | TokenType::ProperName(_) | TokenType::Adjective(_)) {
9476 pos += 1;
9477 } else {
9478 return false;
9479 }
9480
9481 pos < self.tokens.len() && matches!(self.tokens[pos].kind, TokenType::Verb { .. } | TokenType::Article(_))
9483 }
9484
9485 fn check_superlative(&self) -> bool {
9486 matches!(self.peek().kind, TokenType::Superlative(_))
9487 }
9488
9489 fn check_scopal_adverb(&self) -> bool {
9490 matches!(self.peek().kind, TokenType::ScopalAdverb(_))
9491 }
9492
9493 fn check_temporal_adverb(&self) -> bool {
9494 matches!(self.peek().kind, TokenType::TemporalAdverb(_))
9495 }
9496
9497 fn check_non_intersective_adjective(&self) -> bool {
9498 matches!(self.peek().kind, TokenType::NonIntersectiveAdjective(_))
9499 }
9500
9501 fn check_focus(&self) -> bool {
9502 matches!(self.peek().kind, TokenType::Focus(_))
9503 }
9504
9505 fn check_measure(&self) -> bool {
9506 matches!(self.peek().kind, TokenType::Measure(_))
9507 }
9508
9509 fn check_presup_trigger(&self) -> bool {
9510 match &self.peek().kind {
9511 TokenType::PresupTrigger(_) => true,
9512 TokenType::Verb { lemma, .. } => {
9513 let s = self.interner.resolve(*lemma).to_lowercase();
9514 crate::lexicon::lookup_presup_trigger(&s).is_some()
9515 }
9516 _ => false,
9517 }
9518 }
9519
9520 fn is_followed_by_np_object(&self) -> bool {
9521 if self.current + 1 >= self.tokens.len() {
9522 return false;
9523 }
9524 let next = &self.tokens[self.current + 1].kind;
9525 matches!(next,
9526 TokenType::ProperName(_) |
9527 TokenType::Article(_) |
9528 TokenType::Noun(_) |
9529 TokenType::Pronoun { .. } |
9530 TokenType::Reflexive |
9531 TokenType::Who |
9532 TokenType::What |
9533 TokenType::Where |
9534 TokenType::When |
9535 TokenType::Why
9536 )
9537 }
9538
9539 fn is_followed_by_gerund(&self) -> bool {
9540 if self.current + 1 >= self.tokens.len() {
9541 return false;
9542 }
9543 matches!(self.tokens[self.current + 1].kind, TokenType::Verb { .. })
9544 }
9545
9546 fn parse_spawn_statement(&mut self) -> ParseResult<Stmt<'a>> {
9552 self.advance(); if !self.check_article() {
9556 return Err(ParseError {
9557 kind: ParseErrorKind::ExpectedKeyword { keyword: "a/an".to_string() },
9558 span: self.current_span(),
9559 });
9560 }
9561 self.advance(); let agent_type = match &self.tokens[self.current].kind {
9565 TokenType::Noun(sym) | TokenType::ProperName(sym) => {
9566 let s = *sym;
9567 self.advance();
9568 s
9569 }
9570 _ => {
9571 return Err(ParseError {
9572 kind: ParseErrorKind::ExpectedKeyword { keyword: "agent type".to_string() },
9573 span: self.current_span(),
9574 });
9575 }
9576 };
9577
9578 if !self.check(&TokenType::Called) {
9580 return Err(ParseError {
9581 kind: ParseErrorKind::ExpectedKeyword { keyword: "called".to_string() },
9582 span: self.current_span(),
9583 });
9584 }
9585 self.advance(); let name = if let TokenType::StringLiteral(sym) = &self.tokens[self.current].kind {
9589 let s = *sym;
9590 self.advance();
9591 s
9592 } else {
9593 return Err(ParseError {
9594 kind: ParseErrorKind::ExpectedKeyword { keyword: "agent name".to_string() },
9595 span: self.current_span(),
9596 });
9597 };
9598
9599 Ok(Stmt::Spawn { agent_type, name })
9600 }
9601
9602 fn parse_send_statement(&mut self) -> ParseResult<Stmt<'a>> {
9604 self.advance(); let message = self.parse_imperative_expr()?;
9608
9609 if !self.check_preposition_is("to") {
9611 return Err(ParseError {
9612 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
9613 span: self.current_span(),
9614 });
9615 }
9616 self.advance(); let destination = self.parse_imperative_expr()?;
9620
9621 Ok(Stmt::SendMessage { message, destination })
9622 }
9623
9624 fn parse_await_statement(&mut self) -> ParseResult<Stmt<'a>> {
9626 self.advance(); if self.check_word("response") {
9630 self.advance();
9631 }
9632
9633 if !self.check(&TokenType::From) && !self.check_preposition_is("from") {
9635 return Err(ParseError {
9636 kind: ParseErrorKind::ExpectedKeyword { keyword: "from".to_string() },
9637 span: self.current_span(),
9638 });
9639 }
9640 self.advance(); let source = self.parse_imperative_expr()?;
9644
9645 if !self.check_word("into") {
9647 return Err(ParseError {
9648 kind: ParseErrorKind::ExpectedKeyword { keyword: "into".to_string() },
9649 span: self.current_span(),
9650 });
9651 }
9652 self.advance(); let into = match &self.tokens[self.current].kind {
9656 TokenType::Noun(sym) | TokenType::ProperName(sym) | TokenType::Adjective(sym) => {
9657 let s = *sym;
9658 self.advance();
9659 s
9660 }
9661 _ if self.check_content_word() => {
9663 let sym = self.tokens[self.current].lexeme;
9664 self.advance();
9665 sym
9666 }
9667 _ => {
9668 return Err(ParseError {
9669 kind: ParseErrorKind::ExpectedKeyword { keyword: "variable name".to_string() },
9670 span: self.current_span(),
9671 });
9672 }
9673 };
9674
9675 Ok(Stmt::AwaitMessage { source, into })
9676 }
9677
9678 fn parse_merge_statement(&mut self) -> ParseResult<Stmt<'a>> {
9684 self.advance(); let source = self.parse_imperative_expr()?;
9688
9689 if !self.check_word("into") {
9691 return Err(ParseError {
9692 kind: ParseErrorKind::ExpectedKeyword { keyword: "into".to_string() },
9693 span: self.current_span(),
9694 });
9695 }
9696 self.advance(); let target = self.parse_imperative_expr()?;
9700
9701 Ok(Stmt::MergeCrdt { source, target })
9702 }
9703
9704 fn parse_increase_statement(&mut self) -> ParseResult<Stmt<'a>> {
9706 self.advance(); let expr = self.parse_imperative_expr()?;
9710
9711 let (object, field) = if let Expr::FieldAccess { object, field } = expr {
9713 (object, field)
9714 } else {
9715 return Err(ParseError {
9716 kind: ParseErrorKind::ExpectedKeyword { keyword: "field access (e.g., 'x's count')".to_string() },
9717 span: self.current_span(),
9718 });
9719 };
9720
9721 if !self.check_preposition_is("by") {
9723 return Err(ParseError {
9724 kind: ParseErrorKind::ExpectedKeyword { keyword: "by".to_string() },
9725 span: self.current_span(),
9726 });
9727 }
9728 self.advance(); let amount = self.parse_imperative_expr()?;
9732
9733 Ok(Stmt::IncreaseCrdt { object, field: *field, amount })
9734 }
9735
9736 fn parse_decrease_statement(&mut self) -> ParseResult<Stmt<'a>> {
9738 self.advance(); let expr = self.parse_imperative_expr()?;
9742
9743 let (object, field) = if let Expr::FieldAccess { object, field } = expr {
9745 (object, field)
9746 } else {
9747 return Err(ParseError {
9748 kind: ParseErrorKind::ExpectedKeyword { keyword: "field access (e.g., 'x's count')".to_string() },
9749 span: self.current_span(),
9750 });
9751 };
9752
9753 if !self.check_preposition_is("by") {
9755 return Err(ParseError {
9756 kind: ParseErrorKind::ExpectedKeyword { keyword: "by".to_string() },
9757 span: self.current_span(),
9758 });
9759 }
9760 self.advance(); let amount = self.parse_imperative_expr()?;
9764
9765 Ok(Stmt::DecreaseCrdt { object, field: *field, amount })
9766 }
9767
9768 fn parse_append_statement(&mut self) -> ParseResult<Stmt<'a>> {
9770 self.advance(); let value = self.parse_imperative_expr()?;
9774
9775 if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
9777 return Err(ParseError {
9778 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
9779 span: self.current_span(),
9780 });
9781 }
9782 self.advance(); let sequence = self.parse_imperative_expr()?;
9786
9787 Ok(Stmt::AppendToSequence { sequence, value })
9788 }
9789
9790 fn parse_resolve_statement(&mut self) -> ParseResult<Stmt<'a>> {
9792 self.advance(); let expr = self.parse_imperative_expr()?;
9796
9797 let (object, field) = if let Expr::FieldAccess { object, field } = expr {
9799 (object, field)
9800 } else {
9801 return Err(ParseError {
9802 kind: ParseErrorKind::ExpectedKeyword { keyword: "field access (e.g., 'x's title')".to_string() },
9803 span: self.current_span(),
9804 });
9805 };
9806
9807 if !self.check(&TokenType::To) && !self.check_preposition_is("to") {
9809 return Err(ParseError {
9810 kind: ParseErrorKind::ExpectedKeyword { keyword: "to".to_string() },
9811 span: self.current_span(),
9812 });
9813 }
9814 self.advance(); let value = self.parse_imperative_expr()?;
9818
9819 Ok(Stmt::ResolveConflict { object, field: *field, value })
9820 }
9821
9822}
9823