]> git.ipfire.org Git - thirdparty/e2fsprogs.git/commit - e2fsck/pass1.c
Use i_size to determine whether a symlink is a fast symlink
authorTahsin Erdogan <tahsin@google.com>
Fri, 30 Jun 2017 01:31:59 +0000 (18:31 -0700)
committerTheodore Ts'o <tytso@mit.edu>
Wed, 5 Jul 2017 04:06:30 +0000 (00:06 -0400)
commitcf0be23436880a7c9658e2e24259e93cdcb4cc86
treee6bdfe7133ab2c69095b59cbe2c9281abe1751b7
parent0446b9907fbdc8f130ec35726bc8b9cdd493a1cb
Use i_size to determine whether a symlink is a fast symlink

Current way of determining whether a symlink is in fast symlink
format is to call ext2fs_inode_data_blocks2(). If number of data
blocks is zero and EXT4_INLINE_DATA_FL flag is not set, then symlink
data must be in inode->i_block.

This heuristic is becoming increasingly hard to maintain because
inode->i_blocks count can also be incremented for blocks used by
extended attributes. Before ea_inode feature, extra block could come
from xattr block, now more blocks can be added because of xattr
inodes.

To address the issue, add a ext2fs_is_fast_symlink() function that
gives a direct answer based on inode->i_size field. This is
equivalent to kernel's ext4_inode_is_fast_symlink() function.

This patch also fixes a few issues related to fast symlink handling:

  - Both rdump_symlink() and follow_link() interpreted symlinks with
    0 data blocks to always mean fast symlinks. This is incorrect
    because symlinks that are stored as inline data also have
    0 data blocks. Thus, they try to read everything from
    inode->i_block and miss the symlink suffix in inode extra area.

  - e2fsck_pass1_check_symlink() had code to handle inode with
    EXT4_INLINE_DATA_FL flag twice. The first if block always returns
    from the function so the second one is unreachable code.

Signed-off-by: Tahsin Erdogan <tahsin@google.com>
Signed-off-by: Theodore Ts'o <tytso@mit.edu>
debugfs/debugfs.c
debugfs/dump.c
e2fsck/pass1.c
lib/ext2fs/alloc.c
lib/ext2fs/ext2fs.h
lib/ext2fs/namei.c
lib/ext2fs/swapfs.c
lib/ext2fs/symlink.c
misc/fuse2fs.c