//! These tests are not run automatically right now. Please run these tests manually by copying them //! to a separate project when modifying any related code. use super::alloc::*; use super::time::system_time_internal::{from_uefi, to_uefi}; use crate::io::{IoSlice, IoSliceMut}; use crate::time::Duration; const SECS_IN_MINUTE: u64 = 60; #[test] fn align() { // UEFI ABI specifies that allocation alignment minimum is always 8. So this can be // statically verified. assert_eq!(POOL_ALIGNMENT, 8); // Loop over allocation-request sizes from 0-256 and alignments from 1-128, and verify // that in case of overalignment there is at least space for one additional pointer to // store in the allocation. for i in 0..256 { for j in &[1, 2, 4, 8, 16, 32, 64, 128] { if *j <= 8 { assert_eq!(align_size(i, *j), i); } else { assert!(align_size(i, *j) > i + size_of::<*mut ()>()); } } } } #[test] fn systemtime_start() { let t = r_efi::efi::Time { year: 1900, month: 1, day: 1, hour: 0, minute: 0, second: 0, nanosecond: 0, timezone: -1440, daylight: 0, pad2: 0, }; assert_eq!(from_uefi(&t), Duration::new(0, 0)); assert_eq!(t, to_uefi(&from_uefi(&t), -1440, 0).unwrap()); assert!(to_uefi(&from_uefi(&t), 0, 0).is_none()); } #[test] fn systemtime_utc_start() { let t = r_efi::efi::Time { year: 1900, month: 1, day: 1, hour: 0, minute: 0, second: 0, pad1: 0, nanosecond: 0, timezone: 0, daylight: 0, pad2: 0, }; assert_eq!(from_uefi(&t), Duration::new(1440 * SECS_IN_MINUTE, 0)); assert_eq!(t, to_uefi(&from_uefi(&t), 0, 0).unwrap()); assert!(to_uefi(&from_uefi(&t), -1440, 0).is_some()); } #[test] fn systemtime_end() { let t = r_efi::efi::Time { year: 9999, month: 12, day: 31, hour: 23, minute: 59, second: 59, pad1: 0, nanosecond: 0, timezone: 1440, daylight: 0, pad2: 0, }; assert!(to_uefi(&from_uefi(&t), 1440, 0).is_some()); assert!(to_uefi(&from_uefi(&t), 1439, 0).is_none()); } // UEFI IoSlice and IoSliceMut Tests // // Strictly speaking, vectored read/write types for UDP4, UDP6, TCP4, TCP6 are defined // separately in the UEFI Spec. However, they have the same signature. These tests just ensure // that `IoSlice` and `IoSliceMut` are compatible with the vectored types for all the // networking protocols. unsafe fn to_slice(val: &T) -> &[u8] { let len = size_of_val(val); unsafe { crate::slice::from_raw_parts(crate::ptr::from_ref(val).cast(), len) } } #[test] fn io_slice_single() { let mut data = [0, 1, 2, 3, 4]; let tcp4_frag = r_efi::protocols::tcp4::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let tcp6_frag = r_efi::protocols::tcp6::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let udp4_frag = r_efi::protocols::udp4::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let udp6_frag = r_efi::protocols::udp6::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let io_slice = IoSlice::new(&data); unsafe { assert_eq!(to_slice(&io_slice), to_slice(&tcp4_frag)); assert_eq!(to_slice(&io_slice), to_slice(&tcp6_frag)); assert_eq!(to_slice(&io_slice), to_slice(&udp4_frag)); assert_eq!(to_slice(&io_slice), to_slice(&udp6_frag)); } } #[test] fn io_slice_mut_single() { let mut data = [0, 1, 2, 3, 4]; let tcp4_frag = r_efi::protocols::tcp4::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let tcp6_frag = r_efi::protocols::tcp6::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let udp4_frag = r_efi::protocols::udp4::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let udp6_frag = r_efi::protocols::udp6::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let io_slice_mut = IoSliceMut::new(&mut data); unsafe { assert_eq!(to_slice(&io_slice_mut), to_slice(&tcp4_frag)); assert_eq!(to_slice(&io_slice_mut), to_slice(&tcp6_frag)); assert_eq!(to_slice(&io_slice_mut), to_slice(&udp4_frag)); assert_eq!(to_slice(&io_slice_mut), to_slice(&udp6_frag)); } } #[test] fn io_slice_multi() { let mut data = [0, 1, 2, 3, 4]; let tcp4_frag = r_efi::protocols::tcp4::FragmentData { fragment_length: data.len().try_into().unwrap(), fragment_buffer: data.as_mut_ptr().cast(), }; let rhs = [tcp4_frag.clone(), tcp4_frag.clone(), tcp4_frag.clone(), tcp4_frag.clone(), tcp4_frag]; let lhs = [ IoSlice::new(&data), IoSlice::new(&data), IoSlice::new(&data), IoSlice::new(&data), IoSlice::new(&data), ]; unsafe { assert_eq!(to_slice(&lhs), to_slice(&rhs)); } } #[test] fn io_slice_basic() { let data = [0, 1, 2, 3, 4]; let mut io_slice = IoSlice::new(&data); assert_eq!(data, io_slice.as_slice()); io_slice.advance(2); assert_eq!(&data[2..], io_slice.as_slice()); } #[test] fn io_slice_mut_basic() { let data = [0, 1, 2, 3, 4]; let mut data_clone = [0, 1, 2, 3, 4]; let mut io_slice_mut = IoSliceMut::new(&mut data_clone); assert_eq!(data, io_slice_mut.as_slice()); assert_eq!(data, io_slice_mut.as_mut_slice()); io_slice_mut.advance(2); assert_eq!(&data[2..], io_slice_mut.into_slice()); }