Kernel: Initial work on filesystem
We support now ext2 directory listing. File reading is not yet supported.
This commit is contained in:
@@ -41,7 +41,7 @@ namespace Kernel
|
||||
virtual uint32_t sector_size() const override { return m_sector_words * 2; }
|
||||
virtual const char* type() const override { return "PATA"; }
|
||||
|
||||
virtual bool read(uint32_t lba, uint32_t sector_count, uint8_t* buffer) override;
|
||||
virtual bool read_sectors(uint32_t lba, uint32_t sector_count, uint8_t* buffer) override;
|
||||
|
||||
protected:
|
||||
virtual bool initialize() override;
|
||||
|
||||
@@ -5,17 +5,40 @@
|
||||
namespace Kernel
|
||||
{
|
||||
|
||||
struct GUID
|
||||
{
|
||||
uint32_t data1;
|
||||
uint16_t data2;
|
||||
uint16_t data3;
|
||||
uint8_t data4[8];
|
||||
};
|
||||
|
||||
class DiskDevice
|
||||
{
|
||||
public:
|
||||
struct Partition
|
||||
{
|
||||
uint8_t type_guid[16];
|
||||
uint8_t guid[16];
|
||||
uint64_t start_lba;
|
||||
uint64_t end_lba;
|
||||
uint64_t attributes;
|
||||
char name[72];
|
||||
Partition(DiskDevice&, const GUID&, const GUID&, uint64_t, uint64_t, uint64_t, const char*);
|
||||
|
||||
const GUID& type() const { return m_type; }
|
||||
const GUID& guid() const { return m_guid; }
|
||||
uint64_t lba_start() const { return m_lba_start; }
|
||||
uint64_t lba_end() const { return m_lba_end; }
|
||||
uint64_t attributes() const { return m_attributes; }
|
||||
const char* name() const { return m_name; }
|
||||
const DiskDevice& device() const { return m_device; }
|
||||
|
||||
bool read_sectors(uint32_t lba, uint32_t sector_count, uint8_t* buffer);
|
||||
bool is_used() const { uint8_t zero[16] {}; return memcmp(&m_type, zero, 16); }
|
||||
|
||||
private:
|
||||
DiskDevice& m_device;
|
||||
const GUID m_type;
|
||||
const GUID m_guid;
|
||||
const uint64_t m_lba_start;
|
||||
const uint64_t m_lba_end;
|
||||
const uint64_t m_attributes;
|
||||
char m_name[72];
|
||||
};
|
||||
|
||||
public:
|
||||
@@ -24,9 +47,11 @@ namespace Kernel
|
||||
virtual bool initialize() = 0;
|
||||
bool initialize_partitions();
|
||||
|
||||
virtual bool read(uint32_t lba, uint32_t sector_count, uint8_t* buffer) = 0;
|
||||
virtual bool read_sectors(uint32_t lba, uint32_t sector_count, uint8_t* buffer) = 0;
|
||||
virtual uint32_t sector_size() const = 0;
|
||||
|
||||
BAN::Vector<Partition>& partitions() { return m_partitions; }
|
||||
|
||||
private:
|
||||
BAN::Vector<Partition> m_partitions;
|
||||
};
|
||||
@@ -39,6 +64,7 @@ namespace Kernel
|
||||
|
||||
private:
|
||||
DiskIO();
|
||||
void try_add_device(DiskDevice*);
|
||||
|
||||
private:
|
||||
BAN::Vector<DiskDevice*> m_devices;
|
||||
|
||||
188
kernel/include/kernel/FS/Ext2.h
Normal file
188
kernel/include/kernel/FS/Ext2.h
Normal file
@@ -0,0 +1,188 @@
|
||||
#pragma once
|
||||
|
||||
#include <BAN/String.h>
|
||||
#include <kernel/DiskIO.h>
|
||||
#include <kernel/FS/FileSystem.h>
|
||||
|
||||
namespace Kernel
|
||||
{
|
||||
|
||||
namespace Ext2
|
||||
{
|
||||
|
||||
struct Superblock
|
||||
{
|
||||
uint32_t inodes_count;
|
||||
uint32_t blocks_count;
|
||||
uint32_t r_blocks_count;
|
||||
uint32_t free_blocks_count;
|
||||
uint32_t free_inodes_count;
|
||||
uint32_t first_data_block;
|
||||
uint32_t log_block_size;
|
||||
uint32_t log_frag_size;
|
||||
uint32_t blocks_per_group;
|
||||
uint32_t frags_per_group;
|
||||
uint32_t inodes_per_group;
|
||||
uint32_t mtime;
|
||||
uint32_t wtime;
|
||||
uint16_t mnt_count;
|
||||
uint16_t max_mnt_count;
|
||||
uint16_t magic;
|
||||
uint16_t state;
|
||||
uint16_t errors;
|
||||
uint16_t minor_rev_level;
|
||||
uint32_t lastcheck;
|
||||
uint32_t checkinterval;
|
||||
uint32_t creator_os;
|
||||
uint32_t rev_level;
|
||||
uint16_t def_resuid;
|
||||
uint16_t def_resgid;
|
||||
|
||||
// -- EXT2_DYNAMIC_REV Specific --
|
||||
uint8_t __extension_start[0];
|
||||
uint32_t first_ino;
|
||||
uint16_t inode_size;
|
||||
uint16_t block_group_nr;
|
||||
uint32_t feature_compat;
|
||||
uint32_t feature_incompat;
|
||||
uint32_t feature_ro_compat;
|
||||
uint8_t uuid[16];
|
||||
uint8_t volume_name[16];
|
||||
char last_mounted[64];
|
||||
uint32_t algo_bitmap;
|
||||
|
||||
// -- Performance Hints --
|
||||
uint8_t s_prealloc_blocks;
|
||||
uint8_t s_prealloc_dir_blocks;
|
||||
uint16_t __alignment;
|
||||
|
||||
// -- Journaling Support --
|
||||
uint8_t journal_uuid[16];
|
||||
uint32_t journal_inum;
|
||||
uint32_t journal_dev;
|
||||
uint32_t last_orphan;
|
||||
|
||||
// -- Directory Indexing Support --
|
||||
uint32_t hash_seed[4];
|
||||
uint8_t def_hash_version;
|
||||
uint8_t __padding[3];
|
||||
|
||||
// -- Other options --
|
||||
uint32_t default_mount_options;
|
||||
uint32_t first_meta_bg;
|
||||
};
|
||||
|
||||
struct BlockGroupDescriptor
|
||||
{
|
||||
uint32_t block_bitmap;
|
||||
uint32_t inode_bitmap;
|
||||
uint32_t inode_table;
|
||||
uint16_t free_blocks_count;
|
||||
uint16_t free_inodes_count;
|
||||
uint16_t used_dirs_count;
|
||||
uint16_t __padding;
|
||||
//uint8_t reserved[12];
|
||||
};
|
||||
|
||||
struct Inode
|
||||
{
|
||||
uint16_t mode;
|
||||
uint16_t uid;
|
||||
uint32_t size;
|
||||
uint32_t atime;
|
||||
uint32_t ctime;
|
||||
uint32_t mtime;
|
||||
uint32_t dtime;
|
||||
uint16_t gid;
|
||||
uint16_t links_count;
|
||||
uint32_t blocks;
|
||||
uint32_t flags;
|
||||
uint32_t osd1;
|
||||
uint32_t block[15];
|
||||
uint32_t generation;
|
||||
uint32_t file_acl;
|
||||
uint32_t dir_acl;
|
||||
uint32_t faddr;
|
||||
uint32_t osd2[3];
|
||||
};
|
||||
|
||||
struct LinkedDirectoryEntry
|
||||
{
|
||||
uint32_t inode;
|
||||
uint16_t rec_len;
|
||||
uint8_t name_len;
|
||||
uint8_t file_type;
|
||||
char name[0];
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
class Ext2FS;
|
||||
|
||||
class Ext2Inode : public Inode
|
||||
{
|
||||
public:
|
||||
virtual bool is_directory() const override;
|
||||
virtual bool is_regular_file() const override;
|
||||
|
||||
virtual uint16_t uid() const override { return m_inode.uid; }
|
||||
virtual uint16_t gid() const override { return m_inode.gid; }
|
||||
virtual uint32_t size() const override { return m_inode.size; }
|
||||
|
||||
virtual BAN::StringView name() const override { return m_name; }
|
||||
|
||||
virtual BAN::ErrorOr<BAN::Vector<uint8_t>> read_all() const override;
|
||||
virtual BAN::ErrorOr<BAN::Vector<BAN::RefCounted<Inode>>> directory_inodes() const override;
|
||||
virtual BAN::ErrorOr<BAN::RefCounted<Inode>> directory_find(BAN::StringView) const override;
|
||||
|
||||
private:
|
||||
Ext2Inode() {}
|
||||
Ext2Inode(Ext2FS* fs, Ext2::Inode inode, BAN::StringView name)
|
||||
: m_fs(fs)
|
||||
, m_inode(inode)
|
||||
, m_name(name)
|
||||
{}
|
||||
|
||||
private:
|
||||
Ext2FS* m_fs = nullptr;
|
||||
Ext2::Inode m_inode;
|
||||
BAN::String m_name;
|
||||
|
||||
friend class Ext2FS;
|
||||
};
|
||||
|
||||
class Ext2FS : public FileSystem
|
||||
{
|
||||
public:
|
||||
static BAN::ErrorOr<Ext2FS*> create(DiskDevice::Partition&);
|
||||
|
||||
virtual const BAN::RefCounted<Inode> root_inode() const override { return m_root_inode; }
|
||||
|
||||
private:
|
||||
Ext2FS(DiskDevice::Partition& partition)
|
||||
: m_partition(partition)
|
||||
{}
|
||||
|
||||
BAN::ErrorOr<void> initialize_superblock();
|
||||
BAN::ErrorOr<void> initialize_block_group_descriptors();
|
||||
BAN::ErrorOr<void> initialize_root_inode();
|
||||
|
||||
BAN::ErrorOr<Ext2::Inode> read_inode(uint32_t);
|
||||
BAN::ErrorOr<BAN::Vector<uint8_t>> read_block(uint32_t);
|
||||
|
||||
const Ext2::Superblock& superblock() const { return m_superblock; }
|
||||
|
||||
const Ext2::Inode& ext2_root_inode() const;
|
||||
|
||||
private:
|
||||
DiskDevice::Partition& m_partition;
|
||||
|
||||
BAN::RefCounted<Inode> m_root_inode;
|
||||
|
||||
Ext2::Superblock m_superblock;
|
||||
BAN::Vector<Ext2::BlockGroupDescriptor> m_block_group_descriptors;
|
||||
|
||||
friend class Ext2Inode;
|
||||
};
|
||||
|
||||
}
|
||||
15
kernel/include/kernel/FS/FileSystem.h
Normal file
15
kernel/include/kernel/FS/FileSystem.h
Normal file
@@ -0,0 +1,15 @@
|
||||
#pragma once
|
||||
|
||||
#include <BAN/Memory.h>
|
||||
#include <kernel/FS/Inode.h>
|
||||
|
||||
namespace Kernel
|
||||
{
|
||||
|
||||
class FileSystem
|
||||
{
|
||||
public:
|
||||
virtual const BAN::RefCounted<Inode> root_inode() const = 0;
|
||||
};
|
||||
|
||||
}
|
||||
28
kernel/include/kernel/FS/Inode.h
Normal file
28
kernel/include/kernel/FS/Inode.h
Normal file
@@ -0,0 +1,28 @@
|
||||
#pragma once
|
||||
|
||||
#include <BAN/ForwardList.h>
|
||||
#include <BAN/Memory.h>
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
namespace Kernel
|
||||
{
|
||||
|
||||
class Inode
|
||||
{
|
||||
public:
|
||||
virtual bool is_directory() const = 0;
|
||||
virtual bool is_regular_file() const = 0;
|
||||
|
||||
virtual uint16_t uid() const = 0;
|
||||
virtual uint16_t gid() const = 0;
|
||||
virtual uint32_t size() const = 0;
|
||||
|
||||
virtual BAN::StringView name() const = 0;
|
||||
|
||||
virtual BAN::ErrorOr<BAN::Vector<uint8_t>> read_all() const = 0;
|
||||
virtual BAN::ErrorOr<BAN::Vector<BAN::RefCounted<Inode>>> directory_inodes() const = 0;
|
||||
virtual BAN::ErrorOr<BAN::RefCounted<Inode>> directory_find(BAN::StringView) const = 0;
|
||||
};
|
||||
|
||||
}
|
||||
26
kernel/include/kernel/FS/VirtualFileSystem.h
Normal file
26
kernel/include/kernel/FS/VirtualFileSystem.h
Normal file
@@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include <kernel/FS/FileSystem.h>
|
||||
|
||||
namespace Kernel
|
||||
{
|
||||
|
||||
class VirtualFileSystem : public FileSystem
|
||||
{
|
||||
public:
|
||||
static void initialize(BAN::RefCounted<Inode> root_inode);
|
||||
static VirtualFileSystem& get();
|
||||
static bool is_initialized();
|
||||
|
||||
virtual const BAN::RefCounted<Inode> root_inode() const override { return m_root_inode; }
|
||||
|
||||
private:
|
||||
VirtualFileSystem(BAN::RefCounted<Inode> root_inode)
|
||||
: m_root_inode(root_inode)
|
||||
{}
|
||||
|
||||
private:
|
||||
BAN::RefCounted<Inode> m_root_inode;
|
||||
};
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user