use std::io::{
Result,
Seek,
SeekFrom,
Write,
};
use crate::WriteSeek;
pub trait WriteSeekExt: Write + Seek {
fn write_all_at_preserving_position(&mut self, offset: u64, buffer: &[u8]) -> Result<()>;
}
impl<T> WriteSeekExt for T
where
T: Write + Seek + ?Sized,
{
#[inline]
fn write_all_at_preserving_position(&mut self, offset: u64, buffer: &[u8]) -> Result<()> {
let mut writer = self;
write_all_at_preserving_position_impl(&mut writer, offset, buffer)
}
}
fn write_all_at_preserving_position_impl(
writer: &mut dyn WriteSeek,
offset: u64,
buffer: &[u8],
) -> Result<()> {
let position = writer.stream_position()?;
let write_result = match writer.seek(SeekFrom::Start(offset)) {
Ok(_) => writer.write_all(buffer),
Err(error) => Err(error),
};
let restore_result = writer.seek(SeekFrom::Start(position));
match (write_result, restore_result) {
(Ok(()), Ok(_)) => Ok(()),
(Err(error), Ok(_)) => Err(error),
(_, Err(error)) => Err(error),
}
}