use std::io;
use std::ops::Range;
pub(crate) trait Overlaps {
fn overlaps(&self, other: &Self) -> bool;
}
impl<I: Ord> Overlaps for Range<I> {
fn overlaps(&self, other: &Self) -> bool {
self.start < other.end && other.start < self.end
}
}
pub(crate) trait ErrorContext {
fn context<C: std::fmt::Display>(self, context: C) -> Self;
}
impl ErrorContext for io::Error {
fn context<C: std::fmt::Display>(self, context: C) -> Self {
io::Error::new(self.kind(), format!("{context}: {self}"))
}
}
pub(crate) trait ResultErrorContext {
fn err_context<C: std::fmt::Display, F: FnOnce() -> C>(self, context: F) -> Self;
}
impl<V, E: ErrorContext> ResultErrorContext for Result<V, E> {
fn err_context<C: std::fmt::Display, F: FnOnce() -> C>(self, context: F) -> Self {
self.map_err(|err| err.context(context()))
}
}
#[cfg(feature = "vm-memory")]
pub trait ImagoAsRef<'a, T: ?Sized> {
fn as_ref(&self) -> &'a T;
}
#[cfg(feature = "vm-memory")]
impl<'a, T: ?Sized, U: ImagoAsRef<'a, T>> ImagoAsRef<'a, T> for &'a U {
fn as_ref(&self) -> &'a T {
<U as ImagoAsRef<T>>::as_ref(self)
}
}
#[cfg(feature = "vm-memory")]
impl<'a, B: vm_memory::bitmap::BitmapSlice> ImagoAsRef<'a, vm_memory::VolatileSlice<'a, B>>
for &'a vm_memory::VolatileSlice<'a, B>
{
fn as_ref(&self) -> &'a vm_memory::VolatileSlice<'a, B> {
self
}
}
#[cfg(unix)]
pub(crate) fn while_eintr<R: From<i8> + PartialEq, F: FnMut() -> R>(
mut syscall: F,
) -> io::Result<R> {
loop {
let ret: R = syscall();
if ret == R::from(-1i8) {
let err = io::Error::last_os_error();
if err.raw_os_error() != Some(libc::EINTR) {
return Err(err);
}
} else {
return Ok(ret);
}
}
}
pub(crate) fn invalid_data<E: Into<Box<dyn std::error::Error + Send + Sync>>>(
error: E,
) -> io::Error {
io::Error::new(io::ErrorKind::InvalidData, error)
}