kernel+libc+apps: Add a source parameter to the mount() system call

This commit is contained in:
apio 2023-06-20 21:39:41 +02:00
parent 707f64acb5
commit a9460469d9
Signed by: apio
GPG Key ID: B8A7D06E42258954
10 changed files with 31 additions and 6 deletions

View File

@ -279,7 +279,7 @@ static void mount_devfs()
{ {
if (mkdir("/dev", 0755) < 0 && errno != EEXIST) exit(255); if (mkdir("/dev", 0755) < 0 && errno != EEXIST) exit(255);
if (mount("/dev", "devfs") < 0) exit(255); if (mount("/dev", "devfs", "devfs") < 0) exit(255);
} }
int main() int main()

View File

@ -6,15 +6,17 @@ Result<int> luna_main(int argc, char** argv)
{ {
StringView target; StringView target;
StringView fstype { "auto" }; StringView fstype { "auto" };
StringView source;
os::ArgumentParser parser; os::ArgumentParser parser;
parser.add_description("Mount a file system."); parser.add_description("Mount a file system.");
parser.add_system_program_info("mount"_sv); parser.add_system_program_info("mount"_sv);
parser.add_positional_argument(target, "mountpoint"_sv, true); parser.add_positional_argument(target, "mountpoint"_sv, true);
parser.add_positional_argument(source, "source"_sv, true);
parser.add_value_argument(fstype, 't', "type"_sv, "the file system type to use"); parser.add_value_argument(fstype, 't', "type"_sv, "the file system type to use");
parser.parse(argc, argv); parser.parse(argc, argv);
if (mount(target.chars(), fstype.chars()) < 0) if (mount(target.chars(), fstype.chars(), source.chars()) < 0)
{ {
perror("mount"); perror("mount");
return 1; return 1;

View File

@ -1,5 +1,5 @@
#!/bin/sh #!/bin/sh
mkdir -p /tmp mkdir -p /tmp
mount -t tmpfs /tmp mount -t tmpfs /tmp tmpfs
chmod 1777 /tmp chmod 1777 /tmp

View File

@ -47,6 +47,7 @@ set(SOURCES
src/fs/GPT.cpp src/fs/GPT.cpp
src/fs/tmpfs/FileSystem.cpp src/fs/tmpfs/FileSystem.cpp
src/fs/tmpfs/Inode.cpp src/fs/tmpfs/Inode.cpp
src/fs/ext2/FileSystem.cpp
src/fs/devices/DeviceRegistry.cpp src/fs/devices/DeviceRegistry.cpp
src/fs/devices/NullDevice.cpp src/fs/devices/NullDevice.cpp
src/fs/devices/ZeroDevice.cpp src/fs/devices/ZeroDevice.cpp

View File

@ -11,6 +11,7 @@ namespace Ext2
auto maybe_inode = m_inode_cache.try_get(inode); auto maybe_inode = m_inode_cache.try_get(inode);
if (maybe_inode.has_value()) return maybe_inode.value(); if (maybe_inode.has_value()) return maybe_inode.value();
// TODO: Locate the inode's block group descriptor and find it in the block group's inode table.
return err(ENOENT); return err(ENOENT);
} }

View File

@ -34,6 +34,7 @@ namespace Ext2
u32 major_version; u32 major_version;
u16 reserved_block_uid; u16 reserved_block_uid;
u16 reserved_block_gid; u16 reserved_block_gid;
// TODO: Add extended superblock fields.
u8 padding[1024 - 84]; u8 padding[1024 - 84];
}; };

View File

@ -1,4 +1,5 @@
#include "fs/VFS.h" #include "fs/VFS.h"
#include "fs/ext2/FileSystem.h"
#include "fs/tmpfs/FileSystem.h" #include "fs/tmpfs/FileSystem.h"
#include "memory/MemoryManager.h" #include "memory/MemoryManager.h"
#include "sys/Syscall.h" #include "sys/Syscall.h"
@ -8,15 +9,28 @@ Result<u64> sys_mount(Registers*, SyscallArgs args)
{ {
auto target = TRY(MemoryManager::strdup_from_user(args[0])); auto target = TRY(MemoryManager::strdup_from_user(args[0]));
auto fstype = TRY(MemoryManager::strdup_from_user(args[1])); auto fstype = TRY(MemoryManager::strdup_from_user(args[1]));
auto source = TRY(MemoryManager::strdup_from_user(args[2]));
auto* current = Scheduler::current(); auto* current = Scheduler::current();
if (current->auth.euid != 0) return err(EPERM); if (current->auth.euid != 0) return err(EPERM);
auto get_source = [current, &source]() -> Result<SharedPtr<Device>> {
auto inode = TRY(VFS::resolve_path(source.chars(), current->auth, current->current_directory));
if (inode->type() != VFS::InodeType::BlockDevice) return err(ENOTBLK);
dev_t device_id = inode->device_id();
return TRY(DeviceRegistry::fetch_special_device(luna_dev_major(device_id), luna_dev_minor(device_id)));
};
SharedPtr<VFS::FileSystem> fs; SharedPtr<VFS::FileSystem> fs;
if (fstype.view() == "tmpfs") fs = TRY(TmpFS::FileSystem::create()); if (fstype.view() == "tmpfs") fs = TRY(TmpFS::FileSystem::create());
else if (fstype.view() == "devfs") else if (fstype.view() == "devfs")
fs = TRY(DeviceRegistry::create_devfs_instance()); fs = TRY(DeviceRegistry::create_devfs_instance());
else if (fstype.view() == "ext2")
{
auto source_device = TRY(get_source());
fs = TRY(Ext2::FileSystem::create(source_device));
}
else else
return err(ENODEV); return err(ENODEV);

View File

@ -9,7 +9,7 @@ extern "C"
#endif #endif
/* Mount a file system on target. */ /* Mount a file system on target. */
int mount(const char* target, const char* fstype); int mount(const char* target, const char* fstype, const char* source);
/* Unmount the file system mounted on target. */ /* Unmount the file system mounted on target. */
int umount(const char* target); int umount(const char* target);

View File

@ -5,9 +5,9 @@
extern "C" extern "C"
{ {
int mount(const char* target, const char* fstype) int mount(const char* target, const char* fstype, const char* source)
{ {
long rc = syscall(SYS_mount, target, fstype); long rc = syscall(SYS_mount, target, fstype, source);
__errno_return(rc, int); __errno_return(rc, int);
} }

View File

@ -1,6 +1,7 @@
#pragma once #pragma once
#include <luna/Alloc.h> #include <luna/Alloc.h>
#include <luna/Atomic.h> #include <luna/Atomic.h>
#include <luna/Hash.h>
#include <luna/OwnedPtr.h> #include <luna/OwnedPtr.h>
#include <luna/Result.h> #include <luna/Result.h>
#include <luna/ScopeGuard.h> #include <luna/ScopeGuard.h>
@ -84,6 +85,11 @@ template <typename T> class SharedPtr
return *this; return *this;
} }
bool operator==(const SharedPtr<T>& other)
{
return m_ptr == other.m_ptr && m_ref_count == other.m_ref_count;
}
T* ptr() const T* ptr() const
{ {
return m_ptr; return m_ptr;