diff options
author | Andreas Kling <kling@serenityos.org> | 2021-01-09 22:05:05 +0100 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2021-01-09 22:08:53 +0100 |
commit | 77656aed8e7b0b79e50f8e4f79a4b18be59e0563 (patch) | |
tree | 639a339083d99d80d89cec4b59c63bde75f6cb86 /Kernel/FileSystem | |
parent | f0093e5d59a28e3a3493407bd38f9f8aaae87dc2 (diff) | |
download | serenity-77656aed8e7b0b79e50f8e4f79a4b18be59e0563.zip |
Ext2FS: Zero out new space when growing an inode
Before this change, truncating an Ext2FS inode to a larger size than it
was before would give you uninitialized on-disk data.
Fix this by zeroing out all the new space when doing an inode resize.
This is pretty naively implemented via Inode::write_bytes() and there's
lots of room for cleverness here in the future.
Diffstat (limited to 'Kernel/FileSystem')
-rw-r--r-- | Kernel/FileSystem/Ext2FileSystem.cpp | 18 |
1 files changed, 18 insertions, 0 deletions
diff --git a/Kernel/FileSystem/Ext2FileSystem.cpp b/Kernel/FileSystem/Ext2FileSystem.cpp index 429c42d720..2037c75313 100644 --- a/Kernel/FileSystem/Ext2FileSystem.cpp +++ b/Kernel/FileSystem/Ext2FileSystem.cpp @@ -804,6 +804,24 @@ KResult Ext2FSInode::resize(u64 new_size) set_metadata_dirty(true); m_block_list = move(block_list); + + if (new_size > old_size) { + // If we're growing the inode, make sure we zero out all the new space. + // FIXME: There are definitely more efficient ways to achieve this. + size_t bytes_to_clear = new_size - old_size; + size_t clear_from = old_size; + u8 zero_buffer[PAGE_SIZE]; + memset(zero_buffer, 0, sizeof(zero_buffer)); + while (bytes_to_clear) { + auto nwritten = write_bytes(clear_from, min(sizeof(zero_buffer), bytes_to_clear), UserOrKernelBuffer::for_kernel_buffer(zero_buffer), nullptr); + if (nwritten < 0) + return KResult(-nwritten); + ASSERT(nwritten != 0); + bytes_to_clear -= nwritten; + clear_from += nwritten; + } + } + return KSuccess; } |