diff --git a/src/libos/src/fs/event_file.rs b/src/libos/src/fs/event_file.rs index 224e8a9c..8428be58 100644 --- a/src/libos/src/fs/event_file.rs +++ b/src/libos/src/fs/event_file.rs @@ -83,12 +83,7 @@ impl File for EventFile { } fn set_status_flags(&self, new_status_flags: StatusFlags) -> Result<()> { - let valid_flags_mask = StatusFlags::O_APPEND - | StatusFlags::O_ASYNC - | StatusFlags::O_DIRECT - | StatusFlags::O_NOATIME - | StatusFlags::O_NONBLOCK; - let raw_status_flags = (new_status_flags & valid_flags_mask).bits(); + let raw_status_flags = (new_status_flags & STATUS_FLAGS_MASK).bits(); try_libc!(libc::ocall::fcntl_arg1( self.host_fd(), libc::F_SETFL, diff --git a/src/libos/src/fs/file_ops/file_flags.rs b/src/libos/src/fs/file_ops/file_flags.rs index 0449cfa7..b06f1545 100644 --- a/src/libos/src/fs/file_ops/file_flags.rs +++ b/src/libos/src/fs/file_ops/file_flags.rs @@ -111,6 +111,15 @@ bitflags! { const O_PATH = 1 << 21; } } +// On Linux, F_SETFL can change only the O_APPEND, +// O_ASYNC, O_DIRECT, O_NOATIME, and O_NONBLOCK flags +pub const STATUS_FLAGS_MASK: StatusFlags = StatusFlags::from_bits_truncate( + StatusFlags::O_APPEND.bits() + | StatusFlags::O_ASYNC.bits() + | StatusFlags::O_DIRECT.bits() + | StatusFlags::O_NOATIME.bits() + | StatusFlags::O_NONBLOCK.bits(), +); impl StatusFlags { pub fn always_append(&self) -> bool { diff --git a/src/libos/src/fs/file_ops/mod.rs b/src/libos/src/fs/file_ops/mod.rs index e36596d1..e64d924b 100644 --- a/src/libos/src/fs/file_ops/mod.rs +++ b/src/libos/src/fs/file_ops/mod.rs @@ -8,7 +8,7 @@ pub use self::close::do_close; pub use self::dup::{do_dup, do_dup2, do_dup3}; pub use self::fallocate::{do_fallocate, FallocateFlags}; pub use self::fcntl::{do_fcntl, FcntlCmd}; -pub use self::file_flags::{AccessMode, CreationFlags, StatusFlags}; +pub use self::file_flags::{AccessMode, CreationFlags, StatusFlags, STATUS_FLAGS_MASK}; pub use self::flock::do_flock; pub use self::fspath::{get_abs_path_by_fd, FsPath, AT_FDCWD}; pub use self::fsync::{do_fdatasync, do_fsync}; diff --git a/src/libos/src/fs/inode_file.rs b/src/libos/src/fs/inode_file.rs index e5c7fd03..a5ca35b2 100644 --- a/src/libos/src/fs/inode_file.rs +++ b/src/libos/src/fs/inode_file.rs @@ -176,14 +176,8 @@ impl File for INodeFile { fn set_status_flags(&self, new_status_flags: StatusFlags) -> Result<()> { let mut status_flags = self.status_flags.write().unwrap(); - // Currently, F_SETFL can change only the O_APPEND, - // O_ASYNC, O_NOATIME, and O_NONBLOCK flags - let valid_flags_mask = StatusFlags::O_APPEND - | StatusFlags::O_ASYNC - | StatusFlags::O_NOATIME - | StatusFlags::O_NONBLOCK; - status_flags.remove(valid_flags_mask); - status_flags.insert(new_status_flags & valid_flags_mask); + status_flags.remove(STATUS_FLAGS_MASK); + status_flags.insert(new_status_flags & STATUS_FLAGS_MASK); Ok(()) } diff --git a/src/libos/src/fs/mod.rs b/src/libos/src/fs/mod.rs index 55ab8618..9af110b5 100644 --- a/src/libos/src/fs/mod.rs +++ b/src/libos/src/fs/mod.rs @@ -21,6 +21,7 @@ pub use self::file::{File, FileRef}; pub use self::file_ops::{ occlum_ocall_ioctl, utimbuf_t, AccessMode, BuiltinIoctlNum, CreationFlags, FallocateFlags, FileMode, IfConf, IoctlCmd, Stat, StatusFlags, StructuredIoctlArgType, StructuredIoctlNum, + STATUS_FLAGS_MASK, }; pub use self::file_table::{FileDesc, FileTable, FileTableEvent, FileTableNotifier}; pub use self::fs_ops::Statfs; diff --git a/src/libos/src/fs/stdio.rs b/src/libos/src/fs/stdio.rs index 2e35540a..66a26b8a 100644 --- a/src/libos/src/fs/stdio.rs +++ b/src/libos/src/fs/stdio.rs @@ -213,6 +213,24 @@ impl File for StdoutFile { Ok(ret) } + fn status_flags(&self) -> Result { + let ret = try_libc!(libc::ocall::fcntl_arg0( + self.host_fd() as i32, + libc::F_GETFL + )); + Ok(StatusFlags::from_bits_truncate(ret as u32)) + } + + fn set_status_flags(&self, new_status_flags: StatusFlags) -> Result<()> { + let raw_status_flags = (new_status_flags & STATUS_FLAGS_MASK).bits(); + try_libc!(libc::ocall::fcntl_arg1( + self.host_fd() as i32, + libc::F_SETFL, + raw_status_flags as c_int + )); + Ok(()) + } + fn as_any(&self) -> &dyn Any { self } @@ -375,6 +393,24 @@ impl File for StdinFile { Ok(ret) } + fn status_flags(&self) -> Result { + let ret = try_libc!(libc::ocall::fcntl_arg0( + self.host_fd() as i32, + libc::F_GETFL + )); + Ok(StatusFlags::from_bits_truncate(ret as u32)) + } + + fn set_status_flags(&self, new_status_flags: StatusFlags) -> Result<()> { + let raw_status_flags = (new_status_flags & STATUS_FLAGS_MASK).bits(); + try_libc!(libc::ocall::fcntl_arg1( + self.host_fd() as i32, + libc::F_SETFL, + raw_status_flags as c_int + )); + Ok(()) + } + fn as_any(&self) -> &dyn Any { self } diff --git a/src/libos/src/fs/timer_file.rs b/src/libos/src/fs/timer_file.rs index f04f1d13..638ced52 100644 --- a/src/libos/src/fs/timer_file.rs +++ b/src/libos/src/fs/timer_file.rs @@ -130,12 +130,7 @@ impl File for TimerFile { } fn set_status_flags(&self, new_status_flags: StatusFlags) -> Result<()> { - let valid_flags_mask = StatusFlags::O_APPEND - | StatusFlags::O_ASYNC - | StatusFlags::O_DIRECT - | StatusFlags::O_NOATIME - | StatusFlags::O_NONBLOCK; - let raw_status_flags = (new_status_flags & valid_flags_mask).bits(); + let raw_status_flags = (new_status_flags & STATUS_FLAGS_MASK).bits(); try_libc!(libc::ocall::fcntl_arg1( self.host_fd(), libc::F_SETFL, diff --git a/src/libos/src/net/socket/host/socket_file.rs b/src/libos/src/net/socket/host/socket_file.rs index c8a8172c..5bd8535a 100644 --- a/src/libos/src/net/socket/host/socket_file.rs +++ b/src/libos/src/net/socket/host/socket_file.rs @@ -6,7 +6,7 @@ use atomic::{Atomic, Ordering}; use super::*; use crate::fs::{ occlum_ocall_ioctl, AccessMode, AtomicIoEvents, CreationFlags, File, FileRef, HostFd, IoEvents, - IoctlCmd, StatusFlags, + IoctlCmd, StatusFlags, STATUS_FLAGS_MASK, }; //TODO: refactor write syscall to allow zero length with non-zero buffer @@ -63,12 +63,7 @@ impl File for HostSocket { } fn set_status_flags(&self, new_status_flags: StatusFlags) -> Result<()> { - let valid_flags_mask = StatusFlags::O_APPEND - | StatusFlags::O_ASYNC - | StatusFlags::O_DIRECT - | StatusFlags::O_NOATIME - | StatusFlags::O_NONBLOCK; - let raw_status_flags = (new_status_flags & valid_flags_mask).bits(); + let raw_status_flags = (new_status_flags & STATUS_FLAGS_MASK).bits(); try_libc!(libc::ocall::fcntl_arg1( self.raw_host_fd() as i32, libc::F_SETFL,