Commit graph

60 commits

Author SHA1 Message Date
Andreas Kling
5d08665d9a Ext2FS: Remove unnecessary extra cache lookup in get_inode() 2019-11-17 19:11:19 +01:00
Andreas Kling
ba997c0a72 Ext2FS: Add some FIXME's while browsing this code 2019-11-17 18:59:14 +01:00
Andreas Kling
8d4d63d9b6 Ext2FS: Minor cleanup, remove an unused function 2019-11-16 17:29:09 +01:00
Andreas Kling
59ed235c85 Kernel: Implement O_DIRECT open() flag to bypass disk caches
Files opened with O_DIRECT will now bypass the disk cache in read/write
operations (though metadata operations will still hit the disk cache.)

This will allow us to test actual disk performance instead of testing
disk *cache* performance, if that's what we want. :^)

There's room for improvment here, we're very aggressively flushing any
dirty cache entries for the specific block before reading/writing that
block. This is done by walking the entire cache, which may be slow.
2019-11-05 19:35:12 +01:00
Andreas Kling
721585473b Ext2FS: Don't uncache inodes while they are being watched
If an inode is observed by watch_file(), we won't uncache it.
This allows a program to watch a file without keeping it open.
2019-11-04 17:25:44 +01:00
Andreas Kling
c538648465 Ext2FS: Uncache unused Inodes after flushing contents to disk
Don't keep Inodes around in memory forever after we've interacted with
them once. This is a slight performance pessimization when accessing
the same file repeatedly, but closing it for a while in between.

Longer term we should find a way to keep a limited number of unused
Inodes cached, whichever ones we think are likely to be used again.
2019-11-04 12:23:19 +01:00
Andreas Kling
7e56cf1800 Ext2FS: Lock the filesystem during initialization and during sync
If we get preempted during initialization, we really don't want to try
doing a sync on a partially-initialized filesystem.
2019-11-03 13:56:55 +01:00
Andreas Kling
c1d3ac7108 Ext2FS: Fix unpopulated block list cache after mkdir()
When creating a new directory, we set the initial size to 1 block.
This meant that we were allocating a block up front, but the Inode's
internal block list cache was not populated with this block.

This broke write_bytes() on a new directory, since it assumed that
the block list cache would be up to date if the call to write_bytes()
would not change the directory's size.

This patch fixes the issue in two ways: First, we cache the initial
block list created for new directories.
Second, we now repopulate the block list cache in write_bytes() if it
is empty when we get there. This is basically just a safety fallback
to avoid having this kind of bug in the future.
2019-11-03 10:22:09 +01:00
Andreas Kling
1e36d899f1 Ext2FS: Use KBuffers for the cached bitmap blocks
Also cache the block group descriptor table in a KBuffer on file system
initialization, instead of on first access.

This reduces pressure on the kmalloc heap somewhat.
2019-11-03 00:10:24 +01:00
Andreas Kling
94a6b248ca Ext2FS: Resizing an Inode to its current size should do nothing
We were writing out the full block list whenever Ext2FSInode::resize()
was called, even if the old and new sizes were identical.

This patch makes it a no-op, which drastically improves "cp" speed
since we now take full advantage of the up-front call to ftruncate().
2019-11-02 16:22:29 +01:00
Andreas Kling
5835569527 Ext2FS: Inode resizing should fail with ENOSPC if we lack blocks
If there are not enough free blocks in the filesystem to accomodate
growing an Inode, we should fail with ENOSPC before even starting to
allocate blocks.
2019-11-02 12:53:31 +01:00
Andreas Kling
2ad2210eb4 Ext2FS: Use the bitmap block caching for Inode bitmaps as well
Nothing really shows up on disk_benchmark for this change, but it is
obviously sensible to use the same mechanism here.
2019-11-02 12:34:18 +01:00
Andreas Kling
e52b7eeccc Ext2FS: Rename get_block_bitmap() => get_bitmap_block()
This can be used for Inode bitmaps as well, so let's rename it.
2019-11-02 12:26:20 +01:00
Andreas Kling
1ae9d85de9 Ext2FS: Cache block bitmaps instead of always reading/writing disk
Add a simple cache to Ext2FS where we keep block bitmaps along with a
dirty bit. This allows us to coalesce bitmap flushes, giving us a nice
~3x improvement in disk_benchmark write speeds.
2019-11-02 12:18:43 +01:00
Andreas Kling
3a8b5b405c Ext2FS: Tidy up code related to the Ext2 super block a bit
Store the cached super block as an ext2_super_block member instead of
caching it in a ByteBuffer and using a casting helper everywhere.

This patch also combines reading/writing of the super block into a
single disk device operation (instead of two.)
2019-11-02 11:49:11 +01:00
Andreas Kling
e4b7786b66 Ext2FS: Flush the super block and block group descriptors lazily
Keep dirty bits for these and override flush_writes() so that we can
coalesce writes. Looks like a ~5x write performance bump on the
disk_benchmark.
2019-11-02 11:36:56 +01:00
Andreas Kling
5ab044beae Ext2FS: Make Ext2FSInode::is_directory() fast
This patch overloads Inode::is_directory() with a faster version that
doesn't require instantiating the whole InodeMetadata.

If you have an Ext2FSInode&, calling is_directory() should be instant
since we can just look directly at the raw inode bits.
2019-10-02 13:47:44 +02:00
Andreas Kling
922fd703c9 Kernel: Convert the DiskBackedFS write API to take "const u8*"
This way clients are not required to have instantiated ByteBuffers
and can choose whatever memory scheme works best for them.

Also converted some of the Ext2FS code to use stack buffers instead.
2019-09-30 11:23:36 +02:00
Andreas Kling
1fc2612667 Kernel: Make DiskBackedFS::read_block() write to client-provided memory
Instead of having DiskBackedFS allocate a ByteBuffer, leave it to each
client to provide buffer space.

This is significantly faster in many cases where we can use a stack
buffer and avoid heap allocation entirely.
2019-09-30 11:04:30 +02:00
Andreas Kling
8f45a259fc ByteBuffer: Remove pointer() in favor of data()
We had two ways to get the data inside a ByteBuffer. That was silly.
2019-09-30 08:57:01 +02:00
Conrad Pankoff
062218b4cf Kernel: Support writing doubly-indirect ext2 blocks 2019-09-28 09:29:10 +02:00
Andreas Kling
e364846622 Ext2FS: Don't allocate blocks until we're committed to a new inode
Otherwise we would leak the blocks in case we returned earlier than
expected. :^)
2019-09-22 18:50:24 +02:00
Andreas Kling
bd7c38e7b6 Ext2FS: Oops, fix wrong ENOSPC in create_inode() 2019-09-22 18:44:05 +02:00
Andreas Kling
bff59eff4b Ext2FS: Fix two bugs in block allocation:
1) Off-by-one in block allocation when block size != 1 KB

Due to a quirk in the on-disk layout of ext2, file systems with a block
size of 1 KB have block #1 as their first block, while all others start
on block #0.

2) We had no fallback mechanism when the preferred group was full

We now allocate blocks from the preferred block group as long as it's
possible, and fall back to a simple scan through all groups when the
preferred one is full.
2019-09-22 18:37:17 +02:00
Andreas Kling
b9be6b7bb4 Ext2FS: Trying to create a too-long directory entry should ENAMETOOLONG
Also added some assertions to DirectoryEntry in case someone tries to
instantiate them with names that would overflow the name buffer.

DirectoryEntry is a crappy data structure, and the name buffer is also
crappy. Added a FIXME about replacing it with something nicer.

Before this patch, the DirectoryEntry::name buffer would overflow if
you did "touch extremely-long-file-name". Duh.

Fixes #538.
2019-09-10 21:04:27 +02:00
Andreas Kling
ac7a559d96 Ext2FS: Avoid a String allocation in lookup()
By using find() with a custom finder, we can avoid creating a temporary
key value that's only used for the hash lookup.
2019-08-25 06:45:37 +02:00
Andreas Kling
da7ae52eee Ext2FS: Clean up prepare_to_unmount() a little bit 2019-08-17 13:49:37 +02:00
Jesse Buhagiar
bc22456f89 Kernel: Added unmount ability to VFS
It is now possible to unmount file systems from the VFS via `umount`.
It works via looking up the `fsid` of the filesystem from the `Inode`'s
metatdata so I'm not sure how fragile it is. It seems to work for now
though as something to get us going.
2019-08-17 09:29:54 +02:00
Andreas Kling
4afafeae50 Ext2FS: Make some use of Vector::empend(). 2019-08-01 16:31:05 +02:00
Andreas Kling
ecb1b93d53 Ext2FS: Fix fetching of the major/minor device numbers for st_rdev.
This is how it seems to work:

- If ext2_inode.i_blocks[0] is non-zero, it contains the major/minor.
- Otherwise, it's in ext2_inode.i_blocks[1].
2019-07-31 17:24:54 +02:00
Andreas Kling
3b588b7dc0 Ext2FS: Put most debug logging behind EXT2_DEBUG.
The debug output was basically dominated by Ext2FS spam.
2019-07-21 18:38:14 +02:00
Andreas Kling
5254a320d8 Kernel: Remove use of copy_ref() in favor of regular RefPtr copies.
This is obviously more readable. If we ever run into a situation where
ref count churn is actually causing trouble in the future, we can deal with
it then. For now, let's keep it simple. :^)
2019-07-11 15:40:04 +02:00
Andreas Kling
0e75aba7c3 StringView: Rename characters() to characters_without_null_termination().
This should make you think twice before trying to use the const char* from
a StringView as if it's a null-terminated string.
2019-07-08 15:38:44 +02:00
Andreas Kling
27f699ef0c AK: Rename the common integer typedefs to make it obvious what they are.
These types can be picked up by including <AK/Types.h>:

* u8, u16, u32, u64 (unsigned)
* i8, i16, i32, i64 (signed)
2019-07-03 21:20:13 +02:00
Andreas Kling
90b1354688 AK: Rename RetainPtr => RefPtr and Retained => NonnullRefPtr. 2019-06-21 18:37:47 +02:00
Andreas Kling
77b9fa89dd AK: Rename Retainable => RefCounted.
(And various related renames that go along with it.)
2019-06-21 15:30:03 +02:00
Sergey Bugaev
75df45d709 Kernel: Fix comparing StringViews with strcmp().
StringView character buffer is not guaranteed to be null-terminated;
in particular it will not be null-terminated when making a substring.
This means that the buffer can not be used with C functions that expect
a null-terminated string. Instead, StringView provides a convinient
operator == for comparing it with Strings and C stirngs, so use that.

This fixes /proc/self/... resolution failures in ProcFS, since the name
("self") passed to ProcFSInode::lookup() would not be null-terminated.
2019-06-12 16:14:29 +02:00
Andreas Kling
51d70996ba Ext2FS: The block numbers returned by allocate_blocks() should be 1-based.
e2fsck complained about two inodes sharing the same block, and this was why.
2019-06-09 14:59:46 +02:00
Andreas Kling
7562c0b7bf Ext2FS: Fix wrong file mode being passed from create_inode() to add_child(). 2019-06-09 12:48:34 +02:00
Andreas Kling
6873e7d016 Ext2FS: Move directory writing logic into Ext2FSInode. 2019-06-09 12:46:23 +02:00
Andreas Kling
8258b699db Kernel: Use StringView more in Inode and subclasses. 2019-06-09 10:25:19 +02:00
Andreas Kling
891d4c4834 Kernel: Qualify a bunch of #include statements. 2019-06-07 19:29:34 +02:00
Andreas Kling
bc951ca565 Kernel: Run clang-format on everything. 2019-06-07 11:43:58 +02:00
Andreas Kling
08cd75ac4b Kernel: Rename FileDescriptor to FileDescription.
After reading a bunch of POSIX specs, I've learned that a file descriptor
is the number that refers to a file description, not the description itself.
So this patch renames FileDescriptor to FileDescription, and Process now has
FileDescription* file_description(int fd).
2019-06-07 09:36:51 +02:00
Andreas Kling
bba2c062fe FileSystem: Make Inode::lookup() take a StringView.
This avoids a lot of String allocation during path resolution.
2019-06-01 18:01:28 +02:00
Andreas Kling
2e14e5891c FileSystem: Remove now-unused Inode::parent() and Inode::reverse_lookup().
These were only used to implement the old path resolution algorithm.
2019-06-01 17:46:37 +02:00
Andreas Kling
9ac95d1867 FileSystem: Pass mode_t to Inode::add_child().
This way the Ext2FS code can update its directory entry "file type" fields
correctly based on the file mode. This fixes some e2fsck whining.
2019-05-31 17:41:33 +02:00
Andreas Kling
75b0e5cce5 Ext2FS: Block #0 can terminate an inode block list early.
We were already handling this for the indirect blocks, but the direct ones
would happily consider #0 to be a valid block list entry.
2019-05-25 19:19:43 +02:00
Andreas Kling
728327df8a Ext2FS: Fix build with EXT2_DEBUG enabled, and tweak some variable names. 2019-05-25 17:23:17 +02:00
Andreas Kling
8b249bd09b Kernel+Userland: Implement mknod() syscall and add a /bin/mknod program. 2019-05-03 22:59:58 +02:00