use crate::{
borrow_streamer::{BorrowStreamer, BorrowStreamerMut},
Advice, Metadata, ReadAt,
};
#[cfg(unix)]
use std::os::unix::fs::MetadataExt;
#[cfg(target_os = "wasi")]
use std::os::unix::fs::MetadataExt;
use std::{
fs,
io::{self, copy, IoSlice, IoSliceMut, Read},
};
use system_interface::fs::FileIoExt;
use unsafe_io::AsUnsafeFile;
#[cfg(feature = "io-streams")]
use {
crate::own_streamer::OwnStreamer,
cap_fs_ext::{OpenOptions, Reopen},
io_streams::StreamReader,
std::io::SeekFrom,
};
#[inline]
pub fn metadata<Filelike: AsUnsafeFile>(filelike: &Filelike) -> io::Result<Metadata> {
filelike.as_file_view().metadata().map(|meta| {
Metadata {
len: meta.len(),
#[cfg(not(windows))]
blksize: meta.blksize(),
#[cfg(windows)]
blksize: 0x1000,
}
})
}
#[inline]
pub fn advise<Filelike: AsUnsafeFile>(
filelike: &Filelike,
offset: u64,
len: u64,
advice: Advice,
) -> io::Result<()> {
<fs::File as FileIoExt>::advise(&filelike.as_file_view(), offset, len, advice)
}
#[inline]
pub fn read_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
buf: &mut [u8],
offset: u64,
) -> io::Result<usize> {
<fs::File as FileIoExt>::read_at(&filelike.as_file_view(), buf, offset)
}
#[inline]
pub fn read_exact_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
buf: &mut [u8],
offset: u64,
) -> io::Result<()> {
<fs::File as FileIoExt>::read_exact_at(&filelike.as_file_view(), buf, offset)
}
#[inline]
pub fn read_vectored_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
bufs: &mut [IoSliceMut],
offset: u64,
) -> io::Result<usize> {
<fs::File as FileIoExt>::read_vectored_at(&filelike.as_file_view(), bufs, offset)
}
#[inline]
pub fn read_exact_vectored_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
bufs: &mut [IoSliceMut],
offset: u64,
) -> io::Result<()> {
<fs::File as FileIoExt>::read_exact_vectored_at(&filelike.as_file_view(), bufs, offset)
}
#[inline]
pub fn is_read_vectored_at<Filelike: AsUnsafeFile>(filelike: &Filelike) -> bool {
<fs::File as FileIoExt>::is_read_vectored_at(&filelike.as_file_view())
}
#[cfg(feature = "io-streams")]
pub fn read_via_stream_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
offset: u64,
) -> io::Result<StreamReader> {
if let Ok(file) = filelike
.as_file_view()
.reopen(OpenOptions::new().read(true))
{
if offset != 0 {
file.seek(SeekFrom::Start(offset))?;
}
return Ok(StreamReader::file(file));
}
StreamReader::piped_thread(Box::new(OwnStreamer::new(
filelike.as_file_view().try_clone()?,
offset,
)))
}
#[inline]
pub fn write_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
buf: &[u8],
offset: u64,
) -> io::Result<usize> {
<fs::File as FileIoExt>::write_at(&filelike.as_file_view(), buf, offset)
}
#[inline]
pub fn write_all_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
buf: &[u8],
offset: u64,
) -> io::Result<()> {
<fs::File as FileIoExt>::write_all_at(&filelike.as_file_view(), buf, offset)
}
#[inline]
pub fn write_vectored_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
bufs: &[IoSlice],
offset: u64,
) -> io::Result<usize> {
<fs::File as FileIoExt>::write_vectored_at(&filelike.as_file_view(), bufs, offset)
}
#[inline]
pub fn write_all_vectored_at<Filelike: AsUnsafeFile>(
filelike: &Filelike,
bufs: &mut [IoSlice],
offset: u64,
) -> io::Result<()> {
<fs::File as FileIoExt>::write_all_vectored_at(&filelike.as_file_view(), bufs, offset)
}
#[inline]
pub fn is_write_vectored_at<Filelike: AsUnsafeFile>(filelike: &Filelike) -> bool {
<fs::File as FileIoExt>::is_write_vectored_at(&filelike.as_file_view())
}
#[inline]
pub fn copy_from<Filelike: AsUnsafeFile, R: ReadAt>(
filelike: &mut Filelike,
offset: u64,
input: &R,
input_offset: u64,
len: u64,
) -> io::Result<u64> {
let mut input_view = filelike.as_file_view();
let mut output_streamer = BorrowStreamerMut::new(&mut *input_view, offset);
let input_streamer = BorrowStreamer::new(input, input_offset);
copy(&mut input_streamer.take(len), &mut output_streamer)
}
#[inline]
pub fn set_len<Filelike: AsUnsafeFile>(filelike: &Filelike, size: u64) -> io::Result<()> {
filelike.as_file_view().set_len(size)
}