1 // SPDX-License-Identifier: Apache-2.0 OR MIT 2 3 #![allow(clippy::disallowed_names)] 4 5 use pin_init::*; 6 7 #[pin_data] 8 struct SelfRef { 9 #[uses('_: invariant)] 10 not_cov: Box<dyn Fn(&'str str) -> bool + 'str>, 11 12 part: &'str str, 13 str: String, 14 15 mut_part: &'mut_str mut str, 16 #[borrowed(mut)] 17 mut_str: String, 18 } 19 20 fn use_self_ref() { 21 stack_pin_init!(let foo = pin_init!(SelfRef { 22 str: "hello world".to_owned(), 23 part: &str[..5], 24 mut_str: "hello world".to_owned(), 25 mut_part: &mut mut_str[..5], 26 not_cov: Box::new(move |s| s == str), 27 })); 28 29 // Access via projection. 30 println!("{}", foo.as_mut().project().part); 31 32 // Access via accessor. 33 println!("{}", foo.part()); 34 35 // Access via `with_project`, gives mutable reference. 36 foo.as_mut().with_project(|proj| { 37 *proj.part = &proj.str[5..]; 38 }); 39 40 println!("{}", foo.part()); 41 42 // Access fields that mutable borrow others are similar to those of shared borrow. 43 println!("{}", foo.as_mut().project().mut_part); 44 println!("{}", foo.mut_part()); 45 foo.as_mut().with_project(|proj| { 46 proj.mut_part.make_ascii_uppercase(); 47 }); 48 49 // Access non-covariant type using `with_` accessor. 50 foo.with_not_cov(|not_cov| { 51 not_cov(""); 52 }); 53 54 // Access non-covariant type using `with_project`. 55 foo.as_mut().with_project(|proj| (proj.not_cov)(proj.str)); 56 } 57 58 fn main() { 59 use_self_ref(); 60 } 61