Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions project/libfuse-fs/examples/overlay.rs
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,17 @@ async fn main() -> Result<(), std::io::Error> {

set_log(&args);

let file = std::fs::OpenOptions::new()
.create(true)
.write(true)
.truncate(true)
.open("/tmp/overlayfs.log")?;
use std::os::unix::io::AsRawFd;
unsafe {
libc::dup2(file.as_raw_fd(), libc::STDOUT_FILENO);
libc::dup2(file.as_raw_fd(), libc::STDERR_FILENO);
}

let mut mount_handle = libfuse_fs::overlayfs::mount_fs(OverlayArgs {
name: Some(args.name),
mountpoint: args.mountpoint,
Expand Down
2 changes: 1 addition & 1 deletion project/libfuse-fs/examples/overlayfs_example.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ struct Args {
#[arg(long)]
lowerdir: Vec<String>,
/// Use privileged mount instead of unprivileged (default false)
#[arg(long, default_value_t = true)]
#[arg(long, default_value_t = false)]
privileged: bool,
/// Options, currently contains uid/gid mapping info
#[arg(long, short)]
Expand Down
11 changes: 9 additions & 2 deletions project/libfuse-fs/src/overlayfs/async_io.rs
Original file line number Diff line number Diff line change
Expand Up @@ -366,11 +366,18 @@ impl Filesystem for OverlayFs {

self.handles.lock().await.insert(hd, Arc::new(handle_data));

let mut opts = OpenOptions::empty();
match self.config.cache_policy {
CachePolicy::Never => opts |= OpenOptions::DIRECT_IO,
CachePolicy::Always => opts |= OpenOptions::KEEP_CACHE,
_ => {}
}

trace!("OPEN: returning handle: {hd}");

Ok(ReplyOpen {
fh: hd,
flags: flags as u32,
flags: opts.bits(),
})
}

Expand Down Expand Up @@ -837,8 +844,8 @@ impl Filesystem for OverlayFs {
let mut opts = OpenOptions::empty();
match self.config.cache_policy {
CachePolicy::Never => opts |= OpenOptions::DIRECT_IO,
CachePolicy::Auto => opts |= OpenOptions::DIRECT_IO,
CachePolicy::Always => opts |= OpenOptions::KEEP_CACHE,
_ => {}
}

Ok(ReplyCreated {
Expand Down
39 changes: 31 additions & 8 deletions project/libfuse-fs/src/passthrough/async_io.rs
Original file line number Diff line number Diff line change
Expand Up @@ -491,6 +491,7 @@ impl<S: BitmapSlice + Send + Sync> PassthroughFs<S> {
uid.unwrap_or(self.cfg.mapping.get_uid(req.uid)),
gid.unwrap_or(self.cfg.mapping.get_gid(req.gid)),
)?;
// Maybe buggy because `open_file` may call `open_by_handle_at`, which requires CAP_DAC_READ_SEARCH.
data.open_file(final_flags, &self.proc_self_fd)?
}
}
Expand Down Expand Up @@ -560,14 +561,14 @@ impl<S: BitmapSlice + Send + Sync> PassthroughFs<S> {
self.validate_path_component(name)?;

let data = self.inode_map.get(parent).await?;
let file = data.get_file()?;

let res = {
let _guard = set_creds(
uid.unwrap_or(self.cfg.mapping.get_uid(req.uid)),
gid.unwrap_or(self.cfg.mapping.get_gid(req.gid)),
)?;

let file = data.get_file()?;
// Safe because this doesn't modify any memory and we check the return value.
unsafe { libc::mkdirat(file.as_raw_fd(), name.as_ptr(), mode & !umask) }
};
Expand Down Expand Up @@ -617,14 +618,14 @@ impl<S: BitmapSlice + Send + Sync> PassthroughFs<S> {
self.validate_path_component(name)?;

let data = self.inode_map.get(parent).await?;
let file = data.get_file()?;

let res = {
let _guard = set_creds(
uid.unwrap_or(self.cfg.mapping.get_uid(req.uid)),
gid.unwrap_or(self.cfg.mapping.get_gid(req.gid)),
)?;

let file = data.get_file()?;
// Safe because this doesn't modify any memory and we check the return value.
unsafe { libc::symlinkat(link.as_ptr(), file.as_raw_fd(), name.as_ptr()) }
};
Expand Down Expand Up @@ -1097,8 +1098,14 @@ impl Filesystem for PassthroughFs {
buf.truncate(bytes_read); // Adjust the buffer size
}
} else {
error!("read error: {ret}");
return Err(Errno::from(ret as i32));
let e = io::Error::last_os_error();
// if e.raw_os_error() == Some(libc::EINVAL) {
// // Handle EINVAL for sparse files by returning zeroed data
// buf.clear();
// } else {
error!("read error: {e:?}");
return Err(Errno::from(e.raw_os_error().unwrap_or(-1)));
// }
}
}
}
Expand Down Expand Up @@ -1145,6 +1152,17 @@ impl Filesystem for PassthroughFs {
let size = data.len();

self.check_fd_flags(&handle_data, raw_fd, flags).await?;
// // Debug for O_DIRECT alignment issues
// if (flags & libc::O_DIRECT as u32) != 0 {
// let block_size = 512;
// debug!(
// "Alignment check (block_size={}): offset_ok={}, len_ok={}, addr_ok={}",
// block_size,
// offset % block_size as u64 == 0,
// size % block_size == 0,
// (data.as_ptr() as usize) % block_size == 0
// );
// }
let ret = unsafe {
libc::pwrite(
raw_fd as c_int,
Expand All @@ -1156,8 +1174,9 @@ impl Filesystem for PassthroughFs {
if ret >= 0 {
ret
} else {
error!("write error: {ret}");
return Err(Errno::from(ret as i32));
let e = io::Error::last_os_error();
error!("write error: {e:?}");
return Err(Errno::from(e.raw_os_error().unwrap_or(-1)));
}
}
};
Expand Down Expand Up @@ -1313,7 +1332,9 @@ impl Filesystem for PassthroughFs {
)
};
if res < 0 {
return Err(io::Error::last_os_error().into());
let e = io::Error::last_os_error();
// error!("getxattr error: {e:?}");
return Err(e.into());
}

if size == 0 {
Expand Down Expand Up @@ -1351,7 +1372,9 @@ impl Filesystem for PassthroughFs {
)
};
if res < 0 {
return Err(io::Error::last_os_error().into());
let e = io::Error::last_os_error();
// error!("listxattr error: {e:?}");
return Err(e.into());
}

if size == 0 {
Expand Down
Loading