Max OS 0.3
Loading...
Searching...
No Matches
ext2.h
Go to the documentation of this file.
1
9#ifndef MAXOS_FILESYSTEM_EXT2_H
10#define MAXOS_FILESYSTEM_EXT2_H
11
12#include <cstdint>
13#include <common/spinlock.h>
14#include <common/macros.h>
15#include <drivers/disk/disk.h>
16#include <drivers/clock/clock.h>
18#include <memory/memoryIO.h>
19
20
21namespace MaxOS::filesystem::format::ext2 {
22
30 typedef struct PACKED SuperBlock {
31 uint32_t total_inodes;
32 uint32_t total_blocks;
33 uint32_t reserved_blocks;
36 uint32_t starting_block;
37 uint32_t block_size;
38 uint32_t fragment_size;
42 uint32_t last_mount_time;
43 uint32_t late_write_time;
46 uint16_t signature;
47 uint16_t state;
48 uint16_t error_operation;
49 uint16_t version_minor;
50 uint32_t last_check_time;
52 uint32_t os_id;
53 uint32_t version_major;
54 uint16_t reserved_user;
55 uint16_t reserved_group;
56
57 // Extended Fields (version >= 1)
58 uint32_t first_inode;
59 uint16_t inode_size;
64 uint8_t filesystem_id[16];
65 uint8_t volume_name[16];
66 uint8_t last_mount_path[64];
67 uint32_t compression;
70 uint16_t unused;
71 uint8_t journal_id[16];
72 uint32_t journal_inode;
73 uint32_t journal_device;
75 uint8_t free[276];
76
77 } superblock_t;
78
83 enum class FileSystemState {
84 CLEAN = 1,
85 ERROR = 2,
86 };
87
92 enum class ErrorOperation {
93 IGNORE = 1,
94 REMOUNT = 2,
95 PANIC = 3,
96 };
97
104 enum class CreatorOS {
105 LINUX,
106 GNU_HURD,
107 MASIX,
108 FREE_BSD,
109 OTHER_LITES,
110 };
111
116 enum class OptionalFeatures {
117 PREALLOCATE_DIRECTORY = 0x1,
118 AFS_SERVER_INODES = 0x2,
119 JOURNAL_ENABLED = 0x4,
120 ATTRIBUTES_EXTENDED = 0x8,
121 RESIZEABLE = 0x10,
122 HASH_INDEXING = 0x20,
123 };
124
129 enum class RequiredFeatures {
130 COMPRESSION = 0x1,
131 DIRECTORY_HAS_TYPE = 0x2,
132 MUST_REPLAY_JOURNAL = 0x4,
133 JOURNAL_DEVICE = 0x8,
134 };
135
140 enum class ReadOnlyFeatures {
141 SPARSE_SUPER_BLOCKS = 0x1,
142 FILES_64_BIT = 0x2,
143 BINARY_TREE_DIRECTORIES = 0x4,
144 };
145
155 typedef struct PACKED BlockGroupDescriptor {
159 uint16_t free_blocks;
160 uint16_t free_inodes;
162 uint8_t free[14];
163
164 } block_group_descriptor_t;
165
173 typedef struct PACKED Inode {
174 union {
176 struct {
177 uint16_t permissions : 12;
178 uint16_t type : 4;
179 };
180 };
181 uint16_t user_id;
182 uint32_t size_lower;
184 uint32_t creation_time;
186 uint32_t deletion_time;
187 uint16_t group_id;
188 uint16_t hard_links;
189 uint32_t sectors_used;
190 uint32_t flags;
191 uint32_t os_1;
192 uint32_t block_pointers[12];
193 uint32_t l1_indirect;
194 uint32_t l2_indirect;
195 uint32_t l3_indirect;
196 uint32_t generation;
198 uint32_t size_upper;
199 uint32_t os_2[3];
200 } inode_t;
201
206 enum class InodeType {
207 UNKNOWN,
208 FIFO = 0x1000,
209 CHARACTER_DEVICE = 0x2000,
210 DIRECTORY = 0x4000,
211 BLOCK_DEVICE = 0x6000,
212 FILE = 0x8000,
213 SYMBOLIC_LINK = 0xA000,
214 SOCKET = 0xC000,
215 };
216
221 enum class InodePermissions {
222 OTHER_EXECUTE = 0x1,
223 OTHER_WRITE = 0x2,
224 OTHER_READ = 0x4,
225 GROUP_EXECUTE = 0x8,
226 GROUP_WRITE = 0x10,
227 GROUP_READ = 0x20,
228 USER_EXECUTE = 0x40,
229 USER_WRITE = 0x80,
230 USER_READ = 0x100,
231 STICKY = 0x200,
232 GROUP_ID = 0x400,
233 USER_ID = 0x800,
234 };
235
243 FILE = 0x1A4,
244 DIRECTORY = 0x1ED,
245 };
246
251 enum class InodeFlags {
252 SECURE_DELETE = 0x1, // Zero out data on deletion
253 KEEP_DATA = 0x2,
254 FILE_COMPRESSION = 0x4,
255 SYNC_UPDATES = 0x8,
256 FILE_IMMUTABLE = 0x10,
257 APPEND_ONLY = 0x20,
258 DONT_DUMP = 0x40,
259 NO_LAST_ACCESS = 0x80,
260 HASH_INDEXED = 0x10000,
261 AFS_DIRECTORY = 0x20000,
262 JOURNAL_FILE_DATA = 0x40000,
263 };
264
274 typedef struct PACKED InodeOS2Linux {
275 uint8_t fragment;
278 uint16_t high_user_id;
279 uint16_t high_group_id;
280 uint32_t author_id;
281 } linux_os_2_t;
282
290 typedef struct PACKED DirectoryEntry {
291 uint32_t inode;
292 uint16_t size;
293 uint8_t name_length;
294 uint8_t type;
295 // Rest are name chars
296 } directory_entry_t;
297
305 enum class EntryType {
306 UNKNOWN,
307 FILE,
308 DIRECTORY,
309 CHARACTER_DEVICE,
310 BLOCK_DEVICE,
311 FIFO,
312 SOCKET,
313 SYMBOLIC_LINK
314 };
315
323
324 private:
325 common::Vector<uint32_t> allocate_group_blocks(uint32_t block_group, uint32_t amount);
326 void free_group_blocks(uint32_t block_group, uint32_t amount, uint32_t start);
327
328
329 void write_back_block_groups() const;
330 void write_back_superblock();
331
332 public:
334 ~Ext2Volume();
335
338
341
342 size_t block_size;
349
351
352 void write_block(uint32_t block_num, common::buffer_t* buffer) const;
353 void write_inode(uint32_t inode_num, inode_t* inode) const;
354
355 [[nodiscard]] uint32_t create_inode(bool is_directory);
356 void free_inode(uint32_t inode);
357
358 void read_block(uint32_t block_num, common::buffer_t* buffer) const;
359 [[nodiscard]] inode_t read_inode(uint32_t inode_num) const;
360
361 [[nodiscard]] uint32_t allocate_block();
362 [[nodiscard]] common::Vector<uint32_t> allocate_blocks(uint32_t amount);
363 [[nodiscard]] uint32_t bytes_to_blocks(size_t bytes) const;
364
365 void free_blocks(const common::Vector<uint32_t>& blocks);
366 };
367
373
374 private:
375 Ext2Volume* m_volume = nullptr;
376
377 void parse_indirect(uint32_t level, uint32_t block, common::buffer_t* buffer);
378 void write_indirect(uint32_t level, uint32_t& block, size_t& index);
379 void store_blocks(const common::Vector<uint32_t>& blocks);
380
381 public:
382 InodeHandler(Ext2Volume* volume, uint32_t inode);
384
385 uint32_t inode_number;
388
389 [[nodiscard]] size_t size() const;
390 void set_size(size_t size);
391 size_t grow(size_t amount, bool flush = true);
392
393 void save();
394 void free();
395
396 };
397
402 class Ext2File final : public File {
403 private:
404 Ext2Volume* m_volume;
405 InodeHandler m_inode;
406
407 public:
408 Ext2File(Ext2Volume* volume, uint32_t inode, const string& name);
409 ~Ext2File() final;
410
411 void write(common::buffer_t* data, size_t amount) final;
412 void read(common::buffer_t* data, size_t amount) final;
413 void flush() final;
414 };
415
420 class Ext2Directory final : public Directory {
421
422 private:
423 Ext2Volume* m_volume;
424 InodeHandler m_inode;
425
427 common::Vector<string> m_entry_names;
428
429 void write_entries();
430 directory_entry_t create_entry(const string& name, uint32_t inode, bool is_directory = false);
431
432 void parse_block(common::buffer_t* buffer);
433
434 void remove_entry(const string& name, bool is_directory, bool clear = true);
435 void rename_entry(const string& old_name, const string& new_name, bool is_directory);
436
437 public:
438 Ext2Directory(Ext2Volume* volume, uint32_t inode, const string& name);
439 ~Ext2Directory() final;
440
441 void read_from_disk() final;
442
443 File* create_file(const string& name) final;
444 void remove_file(const string& name) final;
445 void rename_file(const string& old_name, const string& new_name) final;
446
447 Directory* create_subdirectory(const string& name) final;
448 void remove_subdirectory(const string& name) final;
449 void rename_subdirectory(const string& old_name, const string& new_name) final;
450 };
451
456 class Ext2FileSystem final : public FileSystem {
457 private:
458 Ext2Volume m_volume;
459
460 public:
461 Ext2FileSystem(drivers::disk::Disk* disk, uint32_t partition_offset);
462 ~Ext2FileSystem() final;
463 };
464
465}
466
467
468#endif // MAXOS_FILESYSTEM_EXT2_H
Wrapper class for a region of bytes in memor in an attempt to add some memory safety....
Definition buffer.h:25
Stores the left, top, width and height of a rectangle.
Definition rectangle.h:22
Enables a resource to be used by only one instance at a time through locking and unlocking.
Definition spinlock.h:21
Generic Disk, handles the reading and writing of data to the hard drive.
Definition disk.h:24
Handles a group of files (directory)
Definition filesystem.h:57
string name()
Get the name of the directory.
Handles the disk operations and file system information.
Definition filesystem.h:96
Handles file operations and information.
Definition filesystem.h:31
string name()
Get the name of the file.
Handles the directory operations on the ext2 filesystem.
Definition ext2.h:420
Directory * create_subdirectory(const string &name) final
Create a new directory in the directory.
Definition ext2.cpp:1128
void remove_subdirectory(const string &name) final
Remove a directory entry from the directory.
Definition ext2.cpp:1151
void read_from_disk() final
read the directory from the inode on the disk
Definition ext2.cpp:959
File * create_file(const string &name) final
Create a new file in the directory.
Definition ext2.cpp:1090
void remove_file(const string &name) final
Delete a file from this directory.
Definition ext2.cpp:1108
void rename_file(const string &old_name, const string &new_name) final
Renames the file from the old name to the new name if it exists.
Definition ext2.cpp:1118
void rename_subdirectory(const string &old_name, const string &new_name) final
Renames the directory from the old name to the new name if it exists.
Definition ext2.cpp:1161
Handles the ext2 filesystem operations.
Definition ext2.h:456
~Ext2FileSystem() final
Destroy the Ext2 File System object and free the root directory.
Definition ext2.cpp:1185
Handles the file operations on the ext2 filesystem.
Definition ext2.h:402
void write(common::buffer_t *data, size_t amount) final
write data to the file (at the current seek position, updated to be += amount)
Definition ext2.cpp:741
void read(common::buffer_t *data, size_t amount) final
read data from the file (at the current seek position, updated to be += amount)
Definition ext2.cpp:795
void flush() final
Flush the file to the disk.
Definition ext2.cpp:841
Common operations for an ext2 volume that are used by both files & directories (like block & inode al...
Definition ext2.h:322
common::Spinlock ext2_lock
Lock for synchronised access to the volume (.
Definition ext2.h:350
size_t block_size
How large each block is (in bytes)
Definition ext2.h:342
block_group_descriptor_t ** block_groups
The block group descriptors.
Definition ext2.h:340
inode_t read_inode(uint32_t inode_num) const
read an inode from the filesystem
Definition ext2.cpp:149
void free_inode(uint32_t inode)
Mark an inode as free. Note: does NOT unallocated the inodes blocks, use free_group_blocks().
Definition ext2.cpp:434
uint32_t block_group_descriptor_table_block
Where the block group descriptor table starts.
Definition ext2.h:343
uint32_t create_inode(bool is_directory)
Allocates a new inode and sets the base metadata. Also allocates block 0 of the inode.
Definition ext2.cpp:370
size_t pointers_per_block
How many block pointers fit in a block.
Definition ext2.h:346
lba_t partition_offset
How far into the disk this partition starts.
Definition ext2.h:337
void write_block(uint32_t block_num, common::buffer_t *buffer) const
write a single block from a buffer into onto the disk
Definition ext2.cpp:80
uint32_t block_group_descriptor_table_size
How many block groups are in the block group descriptor table.
Definition ext2.h:344
superblock_t superblock
The superblock of the ext2 filesystem.
Definition ext2.h:339
uint32_t sectors_per_block
How many sectors does a block take.
Definition ext2.h:348
uint32_t inodes_per_block
How many inodes fit in a block.
Definition ext2.h:347
uint32_t total_block_groups
How many block groups are in the filesystem.
Definition ext2.h:345
void write_inode(uint32_t inode_num, inode_t *inode) const
write an inode to the filesystem
Definition ext2.cpp:102
common::Vector< uint32_t > allocate_blocks(uint32_t amount)
Allocates a set of blocks to be used by an inode.
Definition ext2.cpp:188
uint32_t allocate_block()
Allocates a single block to be used by an inode.
Definition ext2.cpp:177
void read_block(uint32_t block_num, common::buffer_t *buffer) const
Reads a single block from the disk into a buffer.
Definition ext2.cpp:129
drivers::disk::Disk * disk
The disk that this volume is on.
Definition ext2.h:336
uint32_t bytes_to_blocks(size_t bytes) const
How many blocks are needed to contain a set amount of bytes.
Definition ext2.cpp:360
void free_blocks(const common::Vector< uint32_t > &blocks)
Frees a group of blocks. Preferably with adjacent blocks apearing next to each other but not enforced...
Definition ext2.cpp:464
Simplfies the management of an inode & its blocks.
Definition ext2.h:372
uint32_t inode_number
The index of the inode.
Definition ext2.h:385
void free()
Marks this inode's blocks as free and then the inode as free.
Definition ext2.cpp:705
inode_t inode
The inode metadata for this file/directory.
Definition ext2.h:386
size_t grow(size_t amount, bool flush=true)
Increase the size of the inode's storage capacity by allocating new blocks.
Definition ext2.cpp:675
size_t size() const
read the size upper and lower into a single size_t
Definition ext2.cpp:529
common::Vector< uint32_t > block_cache
All the blocks used by this inode.
Definition ext2.h:387
void set_size(size_t size)
store the size of the inode data. (does not write to disk)
Definition ext2.cpp:537
void save()
Writes the inode meta data to disk.
Definition ext2.cpp:697
Defines drivers for the Programmable Interval Timer (PIT) and APIC Clock.
Defines a generic Disk driver for reading and writing data to disk drives.
InodePermissions
The permissions that an inode can have.
Definition ext2.h:221
CreatorOS
The OS which created the filesystem.
Definition ext2.h:104
struct PACKED MaxOS::filesystem::format::ext2::SuperBlock superblock_t
Alias for SuperBlock struct.
InodeType
The type of an inode.
Definition ext2.h:206
InodeFlags
The flags that can be set on an inode.
Definition ext2.h:251
InodePermissionsDefaults
The default permissions for files and directories.
Definition ext2.h:242
ErrorOperation
What to do when an error occurs.
Definition ext2.h:92
ReadOnlyFeatures
What features that are only required in read-only mode.
Definition ext2.h:140
OptionalFeatures
What features that are optional are supported by this filesystem.
Definition ext2.h:116
EntryType
The type of a directory entry.
Definition ext2.h:305
struct PACKED MaxOS::filesystem::format::ext2::DirectoryEntry directory_entry_t
Alias for DirectoryEntry struct.
RequiredFeatures
What features that are required are supported by this filesystem.
Definition ext2.h:129
struct PACKED MaxOS::filesystem::format::ext2::BlockGroupDescriptor block_group_descriptor_t
Alias for BlockGroupDescriptor struct.
struct PACKED MaxOS::filesystem::format::ext2::Inode inode_t
Alias for Inode struct.
FileSystemState
The state of the filesystem.
Definition ext2.h:83
Defines a generic API for a file system, including classes for File, Directory, and FileSystem.
uint32_t lba_t
Logical Block Addressing type.
Definition filesystem.h:24
Defines classes for memory input and output operations of various bit widths (8, 16,...
Defines Spinlock and BlockingLock classes for thread synchronization.
The metadata for a block group in ext2.
Definition ext2.h:155
uint32_t block_inode_bitmap
The block address of the inode usage bitmap.
Definition ext2.h:157
uint32_t inode_table_address
The starting block address of the inode table.
Definition ext2.h:158
uint16_t free_inodes
How many free inodes are in this block group.
Definition ext2.h:160
uint32_t block_usage_bitmap
The block address of the block usage bitmap.
Definition ext2.h:156
uint16_t directory_count
How many directories are in this block group.
Definition ext2.h:161
uint16_t free_blocks
How many free blocks are in this block group.
Definition ext2.h:159
An entry in a directory that points to a file or subdirectory (the name follows this struct)
Definition ext2.h:290
uint32_t inode
The inode number this entry points to (0 = unused)
Definition ext2.h:291
uint16_t size
The total size of this entry (including name)
Definition ext2.h:292
uint8_t name_length
The length of the name.
Definition ext2.h:293
uint8_t type
The type of the entry (see EntryType) (only if the high bit of the superblock's optional_features is ...
Definition ext2.h:294
The OS specific data for Linux created ext2 inodes.
Definition ext2.h:274
uint16_t high_group_id
The high bits of the group ID.
Definition ext2.h:279
uint8_t fragment
The fragment number.
Definition ext2.h:275
uint32_t author_id
The user who created the inode (0xFFFFFFFF if use UID/GID fields)
Definition ext2.h:280
uint16_t high_type_permissions
The high bits of the type & permissions.
Definition ext2.h:277
uint8_t fragment_size
How many 1024 byte fragments are in the file.
Definition ext2.h:276
uint16_t high_user_id
The high bits of the user ID.
Definition ext2.h:278
The metadata for a file or directory in ext2.
Definition ext2.h:173
uint32_t os_1
OS specific value (0 for Linux/HURD, 'transaltor' for Masix)
Definition ext2.h:191
uint32_t extended_attribute
File extended attribute block (Access Control List)
Definition ext2.h:197
uint32_t size_upper
The upper 32 bits of the size of the file in bytes (for files larger than 4GB). If this is a director...
Definition ext2.h:198
uint32_t last_access_time
The seconds (since the epoch) of the last access time.
Definition ext2.h:183
uint32_t l1_indirect
Pointer to a block that contains more block pointers (see block_pointers)
Definition ext2.h:193
uint32_t size_lower
The lower 32 bits of the size of the file in bytes.
Definition ext2.h:182
uint16_t hard_links
How many directory entries point to this inode.
Definition ext2.h:188
uint16_t type
The type of the inode.
Definition ext2.h:178
uint16_t user_id
The ID of the user who owns the inode.
Definition ext2.h:181
uint32_t flags
Flags for the inode (see InodeFlags)
Definition ext2.h:190
uint16_t group_id
The ID of the group who owns the inode.
Definition ext2.h:187
uint32_t deletion_time
The seconds (since the epoch) of the time the inode was marked as not used.
Definition ext2.h:186
uint16_t permissions
The permissions of the inode.
Definition ext2.h:177
uint32_t creation_time
The seconds (since the epoch) of the time the inode was first allocated.
Definition ext2.h:184
uint32_t l3_indirect
Pointer to a block that contains more l2_indirect pointers.
Definition ext2.h:195
uint32_t last_modification_time
The seconds (since the epoch) of the last time the inode was written to.
Definition ext2.h:185
uint32_t generation
File version (used by NFS)
Definition ext2.h:196
uint16_t type_permissions
The type and permissions of the inode.
Definition ext2.h:175
uint32_t sectors_used
How many 512 byte sectors are used by this inode (not blocks) (not including this struct or directory...
Definition ext2.h:189
uint32_t l2_indirect
Pointer to a block that contains more l1_indirect pointers.
Definition ext2.h:194
The metadata of the ext2 filesystem. Found at an offset of 1024 bytes from the start of the partition...
Definition ext2.h:30
uint16_t mounts_since_check
Number of mounts since the last consistency check.
Definition ext2.h:44
uint32_t fragment_size
Fragment size (as a power of 2, so 1024 << fragment_size)
Definition ext2.h:38
uint32_t unallocated_blocks
Number of free blocks.
Definition ext2.h:34
uint32_t total_blocks
Total number of blocks.
Definition ext2.h:32
uint32_t orphan_inodes_start
The start of the list of inodes without a directory entry that need to be deleted.
Definition ext2.h:74
uint32_t compression
Compression algorithm used (0 = none, see RequiredFeatures)
Definition ext2.h:67
uint32_t late_write_time
Last time a block was written to (in seconds since the epoch)
Definition ext2.h:43
uint32_t fragments_per_group
Number of fragments per group.
Definition ext2.h:40
uint8_t file_preallocation_blocks
How many blocks should be allocated when creating a file.
Definition ext2.h:68
uint32_t starting_block
Where the superblock starts (normally 0 but not always)
Definition ext2.h:36
uint32_t blocks_per_group
Number of blocks per group.
Definition ext2.h:39
uint16_t state
The state of the filesystem (see FileSystemState)
Definition ext2.h:47
uint32_t total_inodes
Total number of inodes.
Definition ext2.h:31
uint32_t unallocated_inodes
Number of free inodes.
Definition ext2.h:35
uint32_t last_mount_time
Last time the filesystem was mounted (in seconds since the epoch)
Definition ext2.h:42
uint32_t block_size
Block size (as a power of 2, so 1024 << block_size)
Definition ext2.h:37
uint16_t reserved_user
User ID that can use reserved blocks.
Definition ext2.h:54
uint16_t version_minor
Minor version number (combined with version_major to make version number)
Definition ext2.h:49
uint16_t reserved_group
Group ID that can use reserved blocks.
Definition ext2.h:55
uint8_t directory_preallocation_blocks
How many blocks should be allocated when creating a directory.
Definition ext2.h:69
uint32_t journal_inode
The inode number of the journal file.
Definition ext2.h:72
uint32_t last_check_time
Time of last consistency check (in seconds since the epoch)
Definition ext2.h:50
uint32_t first_inode
Number of the first non-reserved inode (version < 1 this is 11)
Definition ext2.h:58
uint16_t inode_size
Size of each inode structure (version < 1 this is 128 bytes)
Definition ext2.h:59
uint32_t version_major
Major version number (combined with version_minor to make version number)
Definition ext2.h:53
uint16_t signature
Filesystem magic signature (0xEF53)
Definition ext2.h:46
uint32_t optional_features
Features that are not required for read/write support but can help performance (see OptionalFeatures)
Definition ext2.h:61
uint32_t journal_device
The device number of the journal file.
Definition ext2.h:73
uint32_t reserved_blocks
Number of reserved blocks for superuser.
Definition ext2.h:33
uint32_t inodes_per_group
Number of inodes per group.
Definition ext2.h:41
uint32_t os_id
ID of the OS which created the filesystem (see CreatorOS)
Definition ext2.h:52
uint16_t mounts_until_check
Number of mounts allowed before a consistency check is needed (fsck)
Definition ext2.h:45
uint16_t error_operation
What to do when an error is detected (see ErrorOperation)
Definition ext2.h:48
uint16_t read_only_features
Features that are only required in read-only mode (see ReadOnlyFeatures)
Definition ext2.h:63
uint32_t time_until_check
Maximum time between checks (in seconds)
Definition ext2.h:51
uint32_t required_features
Features that must be present for read/write support (see RequiredFeatures)
Definition ext2.h:62
uint16_t superblock_group
If there is a backup superblock, which group it is stored in.
Definition ext2.h:60