1 #[cfg(test)] 2 mod lifetime_test; 3 4 use std::fmt; 5 use std::time::Duration; 6 use stun::attributes::*; 7 use stun::checks::*; 8 use stun::message::*; 9 10 // DEFAULT_LIFETIME in RFC 5766 is 10 minutes. 11 // 12 // RFC 5766 Section 2.2 13 pub const DEFAULT_LIFETIME: Duration = Duration::from_secs(10 * 60); 14 15 // Lifetime represents LIFETIME attribute. 16 // 17 // The LIFETIME attribute represents the duration for which the server 18 // will maintain an allocation in the absence of a refresh. The value 19 // portion of this attribute is 4-bytes long and consists of a 32-bit 20 // unsigned integral value representing the number of seconds remaining 21 // until expiration. 22 // 23 // RFC 5766 Section 14.2 24 #[derive(Default, Debug, PartialEq, Eq)] 25 pub struct Lifetime(pub Duration); 26 27 impl fmt::Display for Lifetime { fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result28 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { 29 write!(f, "{}s", self.0.as_secs()) 30 } 31 } 32 33 // uint32 seconds 34 const LIFETIME_SIZE: usize = 4; // 4 bytes, 32 bits 35 36 impl Setter for Lifetime { 37 // AddTo adds LIFETIME to message. add_to(&self, m: &mut Message) -> Result<(), stun::Error>38 fn add_to(&self, m: &mut Message) -> Result<(), stun::Error> { 39 let mut v = vec![0; LIFETIME_SIZE]; 40 v.copy_from_slice(&(self.0.as_secs() as u32).to_be_bytes()); 41 m.add(ATTR_LIFETIME, &v); 42 Ok(()) 43 } 44 } 45 46 impl Getter for Lifetime { 47 // GetFrom decodes LIFETIME from message. get_from(&mut self, m: &Message) -> Result<(), stun::Error>48 fn get_from(&mut self, m: &Message) -> Result<(), stun::Error> { 49 let v = m.get(ATTR_LIFETIME)?; 50 51 check_size(ATTR_LIFETIME, v.len(), LIFETIME_SIZE)?; 52 53 let seconds = u32::from_be_bytes([v[0], v[1], v[2], v[3]]); 54 self.0 = Duration::from_secs(seconds as u64); 55 56 Ok(()) 57 } 58 } 59