diff options
author | Sergey Bugaev <bugaevc@serenityos.org> | 2020-05-28 21:12:13 +0300 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2020-05-29 07:53:30 +0200 |
commit | 3847d007271a58b33658f400d092e72e7e087db6 (patch) | |
tree | e75b5c94ba39f25a6e188f2652d5287efa947abc /Kernel | |
parent | d395b93b150ab1819f4480d966169e6ef12b636b (diff) | |
download | serenity-3847d007271a58b33658f400d092e72e7e087db6.zip |
Kernel+Userland: Support remounting filesystems :^)
This makes it possible to change flags of a mount after the fact, with the
caveats outlined in the man page.
Diffstat (limited to 'Kernel')
-rw-r--r-- | Kernel/FileSystem/VirtualFileSystem.cpp | 14 | ||||
-rw-r--r-- | Kernel/FileSystem/VirtualFileSystem.h | 2 | ||||
-rw-r--r-- | Kernel/Process.cpp | 5 | ||||
-rw-r--r-- | Kernel/UnixTypes.h | 1 |
4 files changed, 22 insertions, 0 deletions
diff --git a/Kernel/FileSystem/VirtualFileSystem.cpp b/Kernel/FileSystem/VirtualFileSystem.cpp index df3000e38e..29766e3557 100644 --- a/Kernel/FileSystem/VirtualFileSystem.cpp +++ b/Kernel/FileSystem/VirtualFileSystem.cpp @@ -91,6 +91,20 @@ KResult VFS::bind_mount(Custody& source, Custody& mount_point, int flags) return KSuccess; } +KResult VFS::remount(Custody& mount_point, int new_flags) +{ + LOCKER(m_lock); + + dbg() << "VFS: Remounting " << mount_point.absolute_path(); + + Mount* mount = find_mount_for_guest(mount_point.inode().identifier()); + if (!mount) + return KResult(-ENODEV); + + mount->set_flags(new_flags); + return KSuccess; +} + KResult VFS::unmount(InodeIdentifier guest_inode_id) { LOCKER(m_lock); diff --git a/Kernel/FileSystem/VirtualFileSystem.h b/Kernel/FileSystem/VirtualFileSystem.h index 4ea33b3d58..ad7cfa5d85 100644 --- a/Kernel/FileSystem/VirtualFileSystem.h +++ b/Kernel/FileSystem/VirtualFileSystem.h @@ -66,6 +66,7 @@ public: String absolute_path() const; int flags() const { return m_flags; } + void set_flags(int flags) { m_flags = flags; } private: InodeIdentifier m_host; @@ -83,6 +84,7 @@ public: bool mount_root(FS&); KResult mount(FS&, Custody& mount_point, int flags); KResult bind_mount(Custody& source, Custody& mount_point, int flags); + KResult remount(Custody& mount_point, int new_flags); KResult unmount(InodeIdentifier guest_inode_id); KResultOr<NonnullRefPtr<FileDescription>> open(StringView path, int options, mode_t mode, Custody& base, Optional<UidAndGid> = {}); diff --git a/Kernel/Process.cpp b/Kernel/Process.cpp index cd11dd1767..bb9404df05 100644 --- a/Kernel/Process.cpp +++ b/Kernel/Process.cpp @@ -4103,6 +4103,11 @@ int Process::sys$mount(const Syscall::SC_mount_params* user_params) auto& target_custody = custody_or_error.value(); + if (params.flags & MS_REMOUNT) { + // We're not creating a new mount, we're updating an existing one! + return VFS::the().remount(target_custody, params.flags & ~MS_REMOUNT); + } + if (params.flags & MS_BIND) { // We're doing a bind mount. if (description.is_null()) diff --git a/Kernel/UnixTypes.h b/Kernel/UnixTypes.h index 6f57ec83b8..f74c28e402 100644 --- a/Kernel/UnixTypes.h +++ b/Kernel/UnixTypes.h @@ -53,6 +53,7 @@ #define MS_NOSUID (1 << 2) #define MS_BIND (1 << 3) #define MS_RDONLY (1 << 4) +#define MS_REMOUNT (1 << 5) #define PERF_EVENT_MALLOC 1 #define PERF_EVENT_FREE 2 |