From 8058701f7e195636fd1759f10187fa431b7aa61c Mon Sep 17 00:00:00 2001 From: Alan Somers Date: Thu, 4 Jul 2019 13:02:02 -0600 Subject: [PATCH] Fix mocking methods with mutable arguments --- mockall_derive/src/automock.rs | 44 ++++++++++++++++++++++++++++++---- mockall_derive/src/mock.rs | 2 +- 2 files changed, 41 insertions(+), 5 deletions(-) diff --git a/mockall_derive/src/automock.rs b/mockall_derive/src/automock.rs index e2b5e965..1da0238b 100644 --- a/mockall_derive/src/automock.rs +++ b/mockall_derive/src/automock.rs @@ -345,7 +345,7 @@ fn mock_function(vis: &syn::Visibility, { let fn_token = &decl.fn_token; let generics = &decl.generics; - let inputs = &decl.inputs; + let inputs = demutify(&decl.inputs); let output = match &decl.output{ syn::ReturnType::Default => quote!(-> ()), _ => { @@ -361,7 +361,7 @@ fn mock_function(vis: &syn::Visibility, return TokenStream::new(); } - for p in decl.inputs.iter() { + for p in inputs.iter() { match p { syn::FnArg::Captured(arg) => { args.push(arg.pat.clone()); @@ -878,6 +878,42 @@ mod t { check(&attrs, &desired, &code); } + #[test] + fn foreign_mutable_arg() { + let attrs = "mod mock;"; + let desired = r#" + pub mod mock { + ::mockall::expectation!{ + pub(in super::super) fn __foo< >(x: u32) -> i64 { + let (p0: &u32) = (&x); + } + } + ::mockall::lazy_static!{ + static ref foo_expectation: + ::std::sync::Mutex< __foo::Expectations> + = ::std::sync::Mutex::new(__foo::Expectations:: < > ::new()); + } + pub(in super) unsafe fn foo(x: u32) -> i64 { + foo_expectation.lock().unwrap().call(x) + } + pub(in super) fn expect_foo< 'guard>() + -> __foo::ExpectationGuard< 'guard, > + { + __foo::ExpectationGuard:: < > ::new(foo_expectation.lock().unwrap()) + } + pub fn checkpoint() { + foo_expectation.lock().unwrap().checkpoint(); + } + } + "#; + let code = r#" + extern "Rust" { + fn foo(mut x: u32) -> i64; + } + "#; + check(&attrs, &desired, &code); + } + #[test] fn generic_method() { check("", @@ -1589,12 +1625,12 @@ mod t { pub mod __mock_Foo { use super:: * ; ::mockall::expectation!{ - pub fn foo< >(&self, mut x: u32) -> () { + pub fn foo< >(&self, x: u32) -> () { let (p1: &u32) = (&x); } } ::mockall::expectation!{ - pub fn bar< >(mut self) -> () { let () = (); } + pub fn bar< >(self) -> () { let () = (); } } } pub struct MockFoo { diff --git a/mockall_derive/src/mock.rs b/mockall_derive/src/mock.rs index ce537d2a..583df892 100644 --- a/mockall_derive/src/mock.rs +++ b/mockall_derive/src/mock.rs @@ -363,7 +363,7 @@ fn gen_struct(mock_ident: &syn::Ident, let attrs = format_attrs(&meth.borrow().attrs); let method_ident = &meth.borrow().sig.ident; let meth_types = method_types(&meth.borrow().sig, Some(generics)); - let args = &meth.borrow().sig.decl.inputs; + let args = demutify(&meth.borrow().sig.decl.inputs); let expect_obj = &meth_types.expect_obj; let expectations = &meth_types.expectations; let altargs = &meth_types.altargs;