1b8a62b91Sopenharmony_ci#[test] 2b8a62b91Sopenharmony_cifn test_sockopts() { 3b8a62b91Sopenharmony_ci use rustix::net::{AddressFamily, Protocol, SocketType}; 4b8a62b91Sopenharmony_ci use std::time::Duration; 5b8a62b91Sopenharmony_ci 6b8a62b91Sopenharmony_ci let s = 7b8a62b91Sopenharmony_ci rustix::net::socket(AddressFamily::INET, SocketType::STREAM, Protocol::default()).unwrap(); 8b8a62b91Sopenharmony_ci 9b8a62b91Sopenharmony_ci // On a new socket we shouldn't have a timeout yet. 10b8a62b91Sopenharmony_ci assert!( 11b8a62b91Sopenharmony_ci rustix::net::sockopt::get_socket_timeout(&s, rustix::net::sockopt::Timeout::Recv) 12b8a62b91Sopenharmony_ci .unwrap() 13b8a62b91Sopenharmony_ci .is_none() 14b8a62b91Sopenharmony_ci ); 15b8a62b91Sopenharmony_ci assert_eq!( 16b8a62b91Sopenharmony_ci rustix::net::sockopt::get_socket_type(&s).unwrap(), 17b8a62b91Sopenharmony_ci SocketType::STREAM 18b8a62b91Sopenharmony_ci ); 19b8a62b91Sopenharmony_ci #[cfg(not(windows))] 20b8a62b91Sopenharmony_ci assert!(!rustix::net::sockopt::get_socket_broadcast(&s).unwrap()); 21b8a62b91Sopenharmony_ci // On a new socket we shouldn't have a linger yet. 22b8a62b91Sopenharmony_ci assert!(rustix::net::sockopt::get_socket_linger(&s) 23b8a62b91Sopenharmony_ci .unwrap() 24b8a62b91Sopenharmony_ci .is_none()); 25b8a62b91Sopenharmony_ci #[cfg(any(target_os = "android", target_os = "linux"))] 26b8a62b91Sopenharmony_ci assert!(!rustix::net::sockopt::get_socket_passcred(&s).unwrap()); 27b8a62b91Sopenharmony_ci assert_ne!(rustix::net::sockopt::get_ip_ttl(&s).unwrap(), 0); 28b8a62b91Sopenharmony_ci assert_ne!(rustix::net::sockopt::get_ip_ttl(&s).unwrap(), 77); 29b8a62b91Sopenharmony_ci #[cfg(not(any( 30b8a62b91Sopenharmony_ci windows, 31b8a62b91Sopenharmony_ci target_os = "dragonfly", 32b8a62b91Sopenharmony_ci target_os = "freebsd", 33b8a62b91Sopenharmony_ci target_os = "ios", 34b8a62b91Sopenharmony_ci target_os = "macos", 35b8a62b91Sopenharmony_ci target_os = "netbsd", 36b8a62b91Sopenharmony_ci target_os = "openbsd", 37b8a62b91Sopenharmony_ci )))] 38b8a62b91Sopenharmony_ci assert!(rustix::net::sockopt::get_ip_multicast_loop(&s).unwrap()); 39b8a62b91Sopenharmony_ci #[cfg(not(any( 40b8a62b91Sopenharmony_ci windows, 41b8a62b91Sopenharmony_ci target_os = "dragonfly", 42b8a62b91Sopenharmony_ci target_os = "freebsd", 43b8a62b91Sopenharmony_ci target_os = "ios", 44b8a62b91Sopenharmony_ci target_os = "macos", 45b8a62b91Sopenharmony_ci target_os = "netbsd", 46b8a62b91Sopenharmony_ci target_os = "openbsd", 47b8a62b91Sopenharmony_ci )))] 48b8a62b91Sopenharmony_ci assert_eq!(rustix::net::sockopt::get_ip_multicast_ttl(&s).unwrap(), 1); 49b8a62b91Sopenharmony_ci assert!(!rustix::net::sockopt::get_tcp_nodelay(&s).unwrap()); 50b8a62b91Sopenharmony_ci 51b8a62b91Sopenharmony_ci // Set a timeout. 52b8a62b91Sopenharmony_ci rustix::net::sockopt::set_socket_timeout( 53b8a62b91Sopenharmony_ci &s, 54b8a62b91Sopenharmony_ci rustix::net::sockopt::Timeout::Recv, 55b8a62b91Sopenharmony_ci Some(Duration::new(1, 1)), 56b8a62b91Sopenharmony_ci ) 57b8a62b91Sopenharmony_ci .unwrap(); 58b8a62b91Sopenharmony_ci 59b8a62b91Sopenharmony_ci // Check that we have a timeout of at least the time we set. 60b8a62b91Sopenharmony_ci if cfg!(not(target_os = "freebsd")) { 61b8a62b91Sopenharmony_ci assert!( 62b8a62b91Sopenharmony_ci rustix::net::sockopt::get_socket_timeout(&s, rustix::net::sockopt::Timeout::Recv) 63b8a62b91Sopenharmony_ci .unwrap() 64b8a62b91Sopenharmony_ci .unwrap() 65b8a62b91Sopenharmony_ci >= Duration::new(1, 1) 66b8a62b91Sopenharmony_ci ); 67b8a62b91Sopenharmony_ci } else { 68b8a62b91Sopenharmony_ci // On FreeBSD <= 12, it appears the system rounds the timeout down. 69b8a62b91Sopenharmony_ci assert!( 70b8a62b91Sopenharmony_ci rustix::net::sockopt::get_socket_timeout(&s, rustix::net::sockopt::Timeout::Recv) 71b8a62b91Sopenharmony_ci .unwrap() 72b8a62b91Sopenharmony_ci .unwrap() 73b8a62b91Sopenharmony_ci >= Duration::new(1, 0) 74b8a62b91Sopenharmony_ci ); 75b8a62b91Sopenharmony_ci } 76b8a62b91Sopenharmony_ci 77b8a62b91Sopenharmony_ci #[cfg(not(windows))] 78b8a62b91Sopenharmony_ci { 79b8a62b91Sopenharmony_ci // Set the broadcast flag; 80b8a62b91Sopenharmony_ci rustix::net::sockopt::set_socket_broadcast(&s, true).unwrap(); 81b8a62b91Sopenharmony_ci 82b8a62b91Sopenharmony_ci // Check that the broadcast flag is set. This has no effect on stream 83b8a62b91Sopenharmony_ci // sockets, and not all platforms even remember the value. 84b8a62b91Sopenharmony_ci #[cfg(not(any( 85b8a62b91Sopenharmony_ci target_os = "dragonfly", 86b8a62b91Sopenharmony_ci target_os = "freebsd", 87b8a62b91Sopenharmony_ci target_os = "ios", 88b8a62b91Sopenharmony_ci target_os = "macos", 89b8a62b91Sopenharmony_ci target_os = "netbsd", 90b8a62b91Sopenharmony_ci target_os = "openbsd", 91b8a62b91Sopenharmony_ci )))] 92b8a62b91Sopenharmony_ci assert!(rustix::net::sockopt::get_socket_broadcast(&s).unwrap()); 93b8a62b91Sopenharmony_ci } 94b8a62b91Sopenharmony_ci 95b8a62b91Sopenharmony_ci // Set a linger. 96b8a62b91Sopenharmony_ci rustix::net::sockopt::set_socket_linger(&s, Some(Duration::new(1, 1))).unwrap(); 97b8a62b91Sopenharmony_ci 98b8a62b91Sopenharmony_ci // Check that we have a linger of at least the time we set. 99b8a62b91Sopenharmony_ci assert!( 100b8a62b91Sopenharmony_ci dbg!(rustix::net::sockopt::get_socket_linger(&s) 101b8a62b91Sopenharmony_ci .unwrap() 102b8a62b91Sopenharmony_ci .unwrap()) 103b8a62b91Sopenharmony_ci >= Duration::new(1, 1) 104b8a62b91Sopenharmony_ci ); 105b8a62b91Sopenharmony_ci 106b8a62b91Sopenharmony_ci #[cfg(any(target_os = "android", target_os = "linux"))] 107b8a62b91Sopenharmony_ci { 108b8a62b91Sopenharmony_ci // Set the passcred flag; 109b8a62b91Sopenharmony_ci rustix::net::sockopt::set_socket_passcred(&s, true).unwrap(); 110b8a62b91Sopenharmony_ci 111b8a62b91Sopenharmony_ci // Check that the passcred flag is set. 112b8a62b91Sopenharmony_ci assert!(rustix::net::sockopt::get_socket_passcred(&s).unwrap()); 113b8a62b91Sopenharmony_ci } 114b8a62b91Sopenharmony_ci 115b8a62b91Sopenharmony_ci // Set the ip ttl. 116b8a62b91Sopenharmony_ci rustix::net::sockopt::set_ip_ttl(&s, 77).unwrap(); 117b8a62b91Sopenharmony_ci 118b8a62b91Sopenharmony_ci // Check the ip ttl. 119b8a62b91Sopenharmony_ci assert_eq!(rustix::net::sockopt::get_ip_ttl(&s).unwrap(), 77); 120b8a62b91Sopenharmony_ci 121b8a62b91Sopenharmony_ci #[cfg(not(any( 122b8a62b91Sopenharmony_ci windows, 123b8a62b91Sopenharmony_ci target_os = "dragonfly", 124b8a62b91Sopenharmony_ci target_os = "freebsd", 125b8a62b91Sopenharmony_ci target_os = "ios", 126b8a62b91Sopenharmony_ci target_os = "macos", 127b8a62b91Sopenharmony_ci target_os = "netbsd", 128b8a62b91Sopenharmony_ci target_os = "openbsd", 129b8a62b91Sopenharmony_ci )))] 130b8a62b91Sopenharmony_ci { 131b8a62b91Sopenharmony_ci // Set the multicast loop flag; 132b8a62b91Sopenharmony_ci rustix::net::sockopt::set_ip_multicast_loop(&s, false).unwrap(); 133b8a62b91Sopenharmony_ci 134b8a62b91Sopenharmony_ci // Check that the multicast loop flag is set. 135b8a62b91Sopenharmony_ci assert!(!rustix::net::sockopt::get_ip_multicast_loop(&s).unwrap()); 136b8a62b91Sopenharmony_ci } 137b8a62b91Sopenharmony_ci 138b8a62b91Sopenharmony_ci // Set the nodelay flag; 139b8a62b91Sopenharmony_ci rustix::net::sockopt::set_tcp_nodelay(&s, true).unwrap(); 140b8a62b91Sopenharmony_ci 141b8a62b91Sopenharmony_ci // Check that the nodelay flag is set. 142b8a62b91Sopenharmony_ci assert!(rustix::net::sockopt::get_tcp_nodelay(&s).unwrap()); 143b8a62b91Sopenharmony_ci} 144