use super::*; use std::cmp; use std::ptr; use std::ffi::c_void; /// Explicitly zero out a byte buffer. /// /// Essentially `explicit_bzero()`. #[inline(never)] pub fn explicit_clear(buffer : &mut[u8]) { unsafe { std::ptr::write_bytes(buffer.as_mut_ptr() as * mut c_void, 0, buffer.len()); if cfg!(target_arch = "x86_64") || cfg!(target_arch = "x86") { asm!("clflush [{}]", in(reg)buffer.as_mut_ptr()); } else { asm!("") } } } /// Set all bytes of this buffer to a single value. /// /// Essentially `memset()`. #[inline] pub fn set(buffer: &mut [u8], to: u8) { unsafe { std::ptr::write_bytes(buffer.as_mut_ptr() as *mut c_void, to, buffer.len()); } } /// Zero out this buffer /// /// Essentially `bzero()`. #[inline(always)] pub fn clear(buffer: &mut [u8]) { set(buffer, 0); } /// Copy bytes from one slice to another. /// /// # Notes /// The slices can overlap. #[inline] pub fn memmove(from: &[u8], to: &mut [u8]) -> usize { let len = cmp::min(from.len(), to.len()); unsafe { ptr::copy(from.as_ptr(), to.as_mut_ptr(), len); } len } /// Copy bytes from one slice to another. /// /// # Notes /// The slices must *not* overlap. #[inline] pub fn memcpy(from: &[u8], to: &mut [u8]) -> usize { let len = cmp::min(from.len(), to.len()); unsafe { ptr::copy_nonoverlapping(from.as_ptr(), to.as_mut_ptr(), len); } len }