Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 18 additions & 0 deletions tests/ui/fail/mod_annot.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
//@error-in-other-file: Unsat
//@compile-flags: -C debug-assertions=off

mod math {
#[thrust_macros::requires(true)]
#[thrust_macros::ensures(result >= a)]
pub fn max(a: i64, b: i64) -> i64 {
if a >= b {
a
} else {
b
}
}
}

fn main() {
assert!(math::max(1, 2) >= 2);
}
17 changes: 17 additions & 0 deletions tests/ui/fail/mod_invariant.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
//@error-in-other-file: Unsat
//@compile-flags: -C debug-assertions=off

mod counter {
pub fn count_to(n: i64) -> i64 {
let mut i = 0_i64;
while i < n {
thrust_macros::invariant!(|i: i64| i >= 1);
i += 1;
}
i
}
}

fn main() {
assert!(counter::count_to(3) >= 0);
}
18 changes: 18 additions & 0 deletions tests/ui/pass/mod_annot.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
//@check-pass
//@compile-flags: -C debug-assertions=off

mod math {
#[thrust_macros::requires(true)]
#[thrust_macros::ensures(result >= a && result >= b)]
Comment on lines +4 to +6
pub fn max(a: i64, b: i64) -> i64 {
if a >= b {
a
} else {
b
}
}
}

fn main() {
assert!(math::max(1, 2) >= 2);
}
17 changes: 17 additions & 0 deletions tests/ui/pass/mod_invariant.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
//@check-pass
//@compile-flags: -C debug-assertions=off

mod counter {
pub fn count_to(n: i64) -> i64 {
let mut i = 0_i64;
while i < n {
thrust_macros::invariant!(|i: i64| i >= 0);
i += 1;
}
i
}
}

fn main() {
assert!(counter::count_to(3) >= 0);
}
12 changes: 6 additions & 6 deletions thrust-macros/src/formula.rs
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ pub fn expand(input: TokenStream) -> TokenStream {
};

// Rewrites each assignment `lhs = rhs` (produced by [`desugar_arrows`] from
// `lhs ==> rhs`) into `thrust_models::implies(lhs, rhs)`. Visiting
// `lhs ==> rhs`) into `crate::thrust_models::implies(lhs, rhs)`. Visiting
// post-order means nested implications are rewritten innermost-first, so the
// right-associative chain `a ==> b ==> c` becomes `implies(a, implies(b, c))`.
struct ImplicationRewriter;
Expand All @@ -115,7 +115,7 @@ pub fn expand(input: TokenStream) -> TokenStream {
if let syn::Expr::Assign(assign) = expr {
let left = &assign.left;
let right = &assign.right;
*expr = syn::parse_quote!(thrust_models::implies((#left), (#right)));
*expr = syn::parse_quote!(crate::thrust_models::implies((#left), (#right)));
}
}
}
Expand Down Expand Up @@ -215,22 +215,22 @@ mod tests {
fn desugars_implication() {
assert_eq!(
expand_expr("a ==> b"),
expect("thrust_models::implies((a), (b))")
expect("crate::thrust_models::implies((a), (b))")
);
// right-associative
assert_eq!(
expand_expr("a ==> b ==> c"),
expect("thrust_models::implies((a), (thrust_models::implies((b), (c))))")
expect("crate::thrust_models::implies((a), (crate::thrust_models::implies((b), (c))))")
);
// lower precedence than `||` and `==`
assert_eq!(
expand_expr("a || b ==> c == d"),
expect("thrust_models::implies((a || b), (c == d))")
expect("crate::thrust_models::implies((a || b), (c == d))")
);
// nested inside a closure argument
assert_eq!(
expand_expr("exists(|x| a ==> b)"),
expect("exists(|x| thrust_models::implies((a), (b)))")
expect("exists(|x| crate::thrust_models::implies((a), (b)))")
);
}

Expand Down
26 changes: 14 additions & 12 deletions thrust-macros/src/formula_fn_type_lowering.rs
Original file line number Diff line number Diff line change
Expand Up @@ -35,12 +35,12 @@ impl<'a> FormulaFnTypeLowering<'a> {
}
}

/// Maps each function parameter `x: T` to `x: <T as thrust_models::Model>::Ty`.
/// Maps each function parameter `x: T` to `x: <T as crate::thrust_models::Model>::Ty`.
///
/// Closure/function type parameters are first rewritten to
/// `thrust_models::model::Closure<F>`, including when nested in references such as `&mut F`, so
/// specifications can refer to the modeled closure environment while marker functions can still
/// recover the instantiated closure definition from `F`.
/// `crate::thrust_models::model::Closure<F>`, including when nested in references such as
/// `&mut F`, so specifications can refer to the modeled closure environment while marker
/// functions can still recover the instantiated closure definition from `F`.
pub fn lower_params<'ast, I>(&self, args: I) -> TokenStream2
where
I: IntoIterator<Item = &'ast syn::FnArg>,
Expand All @@ -50,14 +50,16 @@ impl<'a> FormulaFnTypeLowering<'a> {
match arg {
syn::FnArg::Receiver(receiver) => {
let ty = crate::receiver_type(receiver);
model_inputs.push(syn::parse_quote!(self_: <#ty as thrust_models::Model>::Ty));
model_inputs
.push(syn::parse_quote!(self_: <#ty as crate::thrust_models::Model>::Ty));
}
syn::FnArg::Typed(pt) => {
let pat = &pt.pat;
let ty = &pt.ty;
let lowered_ty = self.lower_closure_type_params_in_ty(ty);
model_inputs
.push(syn::parse_quote!(#pat: <#lowered_ty as thrust_models::Model>::Ty));
model_inputs.push(
syn::parse_quote!(#pat: <#lowered_ty as crate::thrust_models::Model>::Ty),
);
}
}
}
Expand All @@ -66,10 +68,10 @@ impl<'a> FormulaFnTypeLowering<'a> {

pub fn lower_return_type(&self, ret: &syn::ReturnType) -> syn::Type {
match ret {
syn::ReturnType::Default => syn::parse_quote!(<() as thrust_models::Model>::Ty),
syn::ReturnType::Default => syn::parse_quote!(<() as crate::thrust_models::Model>::Ty),
syn::ReturnType::Type(_, ty) => {
let lowered_ty = self.lower_closure_type_params_in_ty(ty);
syn::parse_quote!(<#lowered_ty as thrust_models::Model>::Ty)
syn::parse_quote!(<#lowered_ty as crate::thrust_models::Model>::Ty)
}
}
}
Expand Down Expand Up @@ -176,7 +178,7 @@ impl<'a> FormulaFnTypeLowering<'a> {
.get_ident()
.is_some_and(|ident| self.closure_type_params.contains(ident)) =>
{
syn::parse_quote!(thrust_models::model::Closure<#ty>)
syn::parse_quote!(crate::thrust_models::model::Closure<#ty>)
}
syn::Type::Reference(tr) => {
let mut tr = tr.clone();
Expand Down Expand Up @@ -251,7 +253,7 @@ fn collect_closure_type_params(generics: &syn::Generics, result: &mut HashSet<sy

fn model_predicates(ty: &impl quote::ToTokens) -> [syn::WherePredicate; 2] {
[
syn::parse_quote!(#ty: thrust_models::Model),
syn::parse_quote!(<#ty as thrust_models::Model>::Ty: PartialEq),
syn::parse_quote!(#ty: crate::thrust_models::Model),
syn::parse_quote!(<#ty as crate::thrust_models::Model>::Ty: PartialEq),
]
}
2 changes: 1 addition & 1 deletion thrust-macros/src/ghost.rs
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,6 @@ fn expand_ghost(closure: &syn::ExprClosure) -> syn::Result<syn::Expr> {
#value == (#body)
}

thrust_models::__ghost_marker::<_, #value_ty>(#name)
crate::thrust_models::__ghost_marker::<_, #value_ty>(#name)
}))
}
2 changes: 1 addition & 1 deletion thrust-macros/src/invariant.rs
Original file line number Diff line number Diff line change
Expand Up @@ -280,7 +280,7 @@ fn expand_invariant(
#body
}

thrust_models::__invariant_marker(#name #turbofish)
crate::thrust_models::__invariant_marker(#name #turbofish)
}))
}

Expand Down
4 changes: 2 additions & 2 deletions thrust-macros/src/pre_post.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ pub fn expand_pre(input: TokenStream) -> TokenStream {
let call = syn::parse_macro_input!(input as syn::ExprCall);
let func = &*call.func;
let args = call_args_tuple(&call.args);
quote::quote!(thrust_models::model::closure_precondition(#func, #args)).into()
quote::quote!(crate::thrust_models::model::closure_precondition(#func, #args)).into()
}

pub fn expand_post(input: TokenStream) -> TokenStream {
Expand All @@ -43,5 +43,5 @@ pub fn expand_post(input: TokenStream) -> TokenStream {
};
let func = &*call.func;
let args = call_args_tuple(&call.args);
quote::quote!(thrust_models::model::closure_postcondition(#func, #args, #result)).into()
quote::quote!(crate::thrust_models::model::closure_postcondition(#func, #args, #result)).into()
}
2 changes: 1 addition & 1 deletion thrust-macros/src/rty.rs
Original file line number Diff line number Diff line change
Expand Up @@ -448,7 +448,7 @@ fn build_formula_fn(
#[allow(non_snake_case)]
#[thrust::formula_fn]
fn #name #def_generics(
#binder: <#binder_ty as thrust_models::Model>::Ty,
#binder: <#binder_ty as crate::thrust_models::Model>::Ty,
#model_params
) -> bool #extended_where {
#formula
Expand Down