diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 629dce65..89ad88ea 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -63,3 +63,26 @@ jobs: - name: Run tests run: INTERACTIVE="" make ${{ matrix.test_group }} + + test-mac: + runs-on: macos-latest + steps: + - uses: actions/checkout@v4 + + - name: Install macfuse + run: brew install --cask macfuse + + - uses: actions-rust-lang/setup-rust-toolchain@v1 + + - name: Run mount test + run: ./osx_mount_tests.sh + env: + RUST_LOG: DEBUG + timeout-minutes: 5 + + - name: Run tests + run: cargo test --features=libfuse + env: + RUST_LOG: DEBUG + timeout-minutes: 5 + diff --git a/examples/simple.rs b/examples/simple.rs index 12469f38..762bbc64 100644 --- a/examples/simple.rs +++ b/examples/simple.rs @@ -1098,6 +1098,9 @@ impl Filesystem for SimpleFS { flags: u32, reply: ReplyEmpty, ) { + #[cfg(target_os = "macos")] + let _ = flags; + let mut inode_attrs = match self.lookup_name(parent, name) { Ok(attrs) => attrs, Err(error_code) => { @@ -1922,6 +1925,9 @@ fn as_file_kind(mut mode: u32) -> FileKind { } fn get_groups(pid: u32) -> Vec { + #[cfg(target_os = "macos")] + let _ = pid; + #[cfg(not(target_os = "macos"))] { let path = format!("/proc/{pid}/task/{pid}/status"); diff --git a/src/mnt/mod.rs b/src/mnt/mod.rs index 79d283cc..73c5d1c2 100644 --- a/src/mnt/mod.rs +++ b/src/mnt/mod.rs @@ -17,7 +17,7 @@ pub mod mount_options; #[cfg(any(feature = "libfuse", test))] use fuse2_sys::fuse_args; -#[cfg(any(test, not(feature = "libfuse")))] +#[cfg(any(all(test, not(target_os = "macos")), not(feature = "libfuse")))] use std::fs::File; #[cfg(any(test, not(feature = "libfuse"), not(feature = "libfuse3")))] use std::io; @@ -87,7 +87,7 @@ fn libc_umount(mnt: &CStr) -> io::Result<()> { /// Warning: This will return true if the filesystem has been detached (lazy unmounted), but not /// yet destroyed by the kernel. -#[cfg(any(test, not(feature = "libfuse")))] +#[cfg(any(all(test, not(target_os = "macos")), not(feature = "libfuse")))] fn is_mounted(fuse_device: &File) -> bool { use libc::{poll, pollfd}; use std::os::unix::prelude::AsRawFd; @@ -121,7 +121,7 @@ fn is_mounted(fuse_device: &File) -> bool { #[cfg(test)] mod test { use super::*; - use std::{ffi::CStr, mem::ManuallyDrop}; + use std::ffi::CStr; #[test] fn fuse_args() { @@ -142,6 +142,8 @@ mod test { }, ); } + + #[cfg(not(target_os = "macos"))] fn cmd_mount() -> String { std::str::from_utf8( std::process::Command::new("sh") @@ -156,8 +158,12 @@ mod test { .to_owned() } + // Mountpoint are not directly available on MacOS. + #[cfg(not(target_os = "macos"))] #[test] fn mount_unmount() { + use std::mem::ManuallyDrop; + // We use ManuallyDrop here to leak the directory on test failure. We don't // want to try and clean up the directory if it's a mountpoint otherwise we'll // deadlock. diff --git a/tests/integration_tests.rs b/tests/integration_tests.rs index 0ed8c804..1bbd1345 100644 --- a/tests/integration_tests.rs +++ b/tests/integration_tests.rs @@ -5,19 +5,25 @@ use std::time::Duration; use tempfile::TempDir; #[test] -#[cfg(target_os = "linux")] +#[cfg(any(target_os = "linux", target_os = "macos"))] fn unmount_no_send() { // Rc to make this !Send + env_logger::init(); struct NoSendFS(Rc<()>); impl Filesystem for NoSendFS {} let tmpdir: TempDir = tempfile::tempdir().unwrap(); let mut session = Session::new(NoSendFS(Rc::new(())), tmpdir.path(), &[]).unwrap(); + log::debug!("Session created"); let mut unmounter = session.unmount_callable(); thread::spawn(move || { thread::sleep(Duration::from_secs(1)); + log::debug!("unmounting"); unmounter.unmount().unwrap(); + log::debug!("unmounted"); }); + log::debug!("running session"); session.run().unwrap(); + log::debug!("session finished") }