@@ -196,6 +196,7 @@ enum FormulaOrTerm<T> {
196196 Term ( chc:: Term < T > , chc:: Sort ) ,
197197 BinOp ( chc:: Term < T > , AmbiguousBinOp , chc:: Term < T > ) ,
198198 Not ( Box < FormulaOrTerm < T > > ) ,
199+ Literal ( bool ) ,
199200}
200201
201202impl < T > FormulaOrTerm < T > {
@@ -215,6 +216,13 @@ impl<T> FormulaOrTerm<T> {
215216 chc:: Formula :: Atom ( chc:: Atom :: new ( pred. into ( ) , vec ! [ lhs, rhs] ) )
216217 }
217218 FormulaOrTerm :: Not ( formula_or_term) => formula_or_term. into_formula ( ) ?. not ( ) ,
219+ FormulaOrTerm :: Literal ( b) => {
220+ if b {
221+ chc:: Formula :: top ( )
222+ } else {
223+ chc:: Formula :: bottom ( )
224+ }
225+ }
218226 } ;
219227 Some ( fo)
220228 }
@@ -233,6 +241,7 @@ impl<T> FormulaOrTerm<T> {
233241 let ( t, _) = formula_or_term. into_term ( ) ?;
234242 ( t. not ( ) , chc:: Sort :: bool ( ) )
235243 }
244+ FormulaOrTerm :: Literal ( b) => ( chc:: Term :: bool ( b) , chc:: Sort :: bool ( ) ) ,
236245 } ;
237246 Some ( ( t, s) )
238247 }
@@ -461,8 +470,8 @@ where
461470 ident. as_str ( ) ,
462471 self . formula_existentials . get ( ident. name . as_str ( ) ) ,
463472 ) {
464- ( "true" , _) => FormulaOrTerm :: Formula ( chc :: Formula :: top ( ) ) ,
465- ( "false" , _) => FormulaOrTerm :: Formula ( chc :: Formula :: bottom ( ) ) ,
473+ ( "true" , _) => FormulaOrTerm :: Literal ( true ) ,
474+ ( "false" , _) => FormulaOrTerm :: Literal ( false ) ,
466475 ( _, Some ( sort) ) => {
467476 let var =
468477 chc:: Term :: FormulaExistentialVar ( sort. clone ( ) , ident. name . to_string ( ) ) ;
@@ -502,6 +511,31 @@ where
502511 ) ,
503512 _ => unimplemented ! ( ) ,
504513 } ,
514+ TokenKind :: Lt => {
515+ let ( t1, s1) = self
516+ . parse_binop_2 ( ) ?
517+ . into_term ( )
518+ . ok_or_else ( || ParseAttrError :: unexpected_formula ( "in box/mut term" ) ) ?;
519+
520+ match self . next_token ( "> or ," ) ? {
521+ Token {
522+ kind : TokenKind :: Gt ,
523+ ..
524+ } => FormulaOrTerm :: Term ( chc:: Term :: box_ ( t1) , chc:: Sort :: box_ ( s1) ) ,
525+ Token {
526+ kind : TokenKind :: Comma ,
527+ ..
528+ } => {
529+ let ( t2, _s2) = self
530+ . parse_binop_2 ( ) ?
531+ . into_term ( )
532+ . ok_or_else ( || ParseAttrError :: unexpected_formula ( "in mut term" ) ) ?;
533+ self . expect_next_token ( TokenKind :: Gt , ">" ) ?;
534+ FormulaOrTerm :: Term ( chc:: Term :: mut_ ( t1, t2) , chc:: Sort :: mut_ ( s1) )
535+ }
536+ t => return Err ( ParseAttrError :: unexpected_token ( "> or ," , t. clone ( ) ) ) ,
537+ }
538+ }
505539 _ => {
506540 return Err ( ParseAttrError :: unexpected_token (
507541 "identifier, or literal" ,
@@ -801,6 +835,26 @@ where
801835 fn parse_sort ( & mut self ) -> Result < chc:: Sort > {
802836 let tt = self . next_token_tree ( "sort" ) ?. clone ( ) ;
803837 match tt {
838+ TokenTree :: Token (
839+ Token {
840+ kind : TokenKind :: BinOp ( BinOpToken :: And ) ,
841+ ..
842+ } ,
843+ _,
844+ ) => match self . look_ahead_token ( 0 ) {
845+ Some ( Token {
846+ kind : TokenKind :: Ident ( sym, _) ,
847+ ..
848+ } ) if sym. as_str ( ) == "mut" => {
849+ self . consume ( ) ;
850+ let inner_sort = self . parse_sort ( ) ?;
851+ Ok ( chc:: Sort :: mut_ ( inner_sort) )
852+ }
853+ _ => {
854+ let inner_sort = self . parse_sort ( ) ?;
855+ Ok ( chc:: Sort :: box_ ( inner_sort) )
856+ }
857+ } ,
804858 TokenTree :: Token (
805859 Token {
806860 kind : TokenKind :: Ident ( sym, _) ,
@@ -814,7 +868,16 @@ where
814868 "string" => unimplemented ! ( ) ,
815869 "null" => chc:: Sort :: null ( ) ,
816870 "fn" => unimplemented ! ( ) ,
817- _ => unimplemented ! ( ) ,
871+ name => {
872+ // TODO: ad-hoc
873+ if let Some ( i) =
874+ name. strip_prefix ( 'T' ) . and_then ( |s| s. parse :: < usize > ( ) . ok ( ) )
875+ {
876+ chc:: Sort :: param ( i)
877+ } else {
878+ unimplemented ! ( ) ;
879+ }
880+ }
818881 } ;
819882 Ok ( sort)
820883 }
0 commit comments