Purpose: Break one mut short into two structures. If you use one structure with the host closure, then everything works well.
Lightweight code:
fn main() { let mut is_visible = true; let mut is_close = true; let mut function = |name:Option<&[u8]>, value:&[u8]| { if let Some(name) = name { match name { b"is_visible" => { is_visible = match value { b"ON" => true, b"OFF" => false, _=> false, }; }, _=>{}, } } }; Test::test_set_vars(&mut function); Test2::test_set_vars(&mut function); if is_visible { println!("VISIBLE OK"); } if is_close { println!("CLOSE OK"); } } pub struct Test { } impl Test { pub fn test_set_vars<F: FnMut(Option<&[u8]>, &[u8])>(mut function: F) { function(Some(b"is_close"), b"OFF"); function(Some(b"is_visible"), b"ON"); } } pub struct Test2 { } impl Test2 { pub fn test_set_vars<F: FnMut(Option<&[u8]>, &[u8])>(mut function: F) { function(Some(b"is_close"), b"ON"); function(Some(b"is_visible"), b"ON"); } } Running: https://play.rust-lang.org/?gist=f3d656088b19ee1b847db54036983584&version=stable
If you duplicate the closure, then everything goes well.
Code 2:
fn main() { let mut is_visible = true; let mut is_close = true; Test::test_set_vars(|name:Option<&[u8]>, value:&[u8]| { if let Some(name) = name { match name { b"is_visible" => { is_visible = match value { b"ON" => true, b"OFF" => false, _=> false, }; }, _=>{}, } } }); Test2::test_set_vars(|name:Option<&[u8]>, value:&[u8]| { if let Some(name) = name { match name { b"is_visible" => { is_visible = match value { b"ON" => true, b"OFF" => false, _=> false, }; }, _=>{}, } } }); if is_visible { println!("VISIBLE OK"); } if is_close { println!("CLOSE OK"); } } pub struct Test { } impl Test { pub fn test_set_vars<F: FnMut(Option<&[u8]>, &[u8])>(mut function: F) { function(Some(b"is_close"), b"OFF"); function(Some(b"is_visible"), b"ON"); } } pub struct Test2 { } impl Test2 { pub fn test_set_vars<F: FnMut(Option<&[u8]>, &[u8])>(mut function: F) { function(Some(b"is_close"), b"ON"); function(Some(b"is_visible"), b"ON"); } }