diff mbox series

e2fsck: allow verity files to have initialized blocks past i_size

Message ID 20180821175937.155466-1-ebiggers@kernel.org
State Accepted, archived
Headers show
Series e2fsck: allow verity files to have initialized blocks past i_size | expand

Commit Message

Eric Biggers Aug. 21, 2018, 5:59 p.m. UTC
From: Eric Biggers <ebiggers@google.com>

Since ext4 verity is going to be an RO_COMPAT feature rather than an
INCOMPAT one, the on-disk i_size of verity inodes needs to be the data
size rather than the full size.  Consequently, verity inodes will have
initialized blocks past i_size, containing the Merkle tree and other
verity metadata.  So e2fsck must not fix the i_size of such inodes as it
normally would.

Signed-off-by: Eric Biggers <ebiggers@google.com>
---
 e2fsck/pass1.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

Comments

Theodore Ts'o Aug. 21, 2018, 8:23 p.m. UTC | #1
On Tue, Aug 21, 2018 at 10:59:37AM -0700, Eric Biggers wrote:
> From: Eric Biggers <ebiggers@google.com>
> 
> Since ext4 verity is going to be an RO_COMPAT feature rather than an
> INCOMPAT one, the on-disk i_size of verity inodes needs to be the data
> size rather than the full size.  Consequently, verity inodes will have
> initialized blocks past i_size, containing the Merkle tree and other
> verity metadata.  So e2fsck must not fix the i_size of such inodes as it
> normally would.
> 
> Signed-off-by: Eric Biggers <ebiggers@google.com>

Thanks, applied.

We should have some tests, in e2fsprogs and/or xfstests that tests
this.  The work-in-progress verity 9XX xfstests don't seem to have a
problem with this, probably because we weren't unmounting a file
system, and then running fsck.  (Since it's a scratch partition,
the test harness doesn't run fsck after any of the 9XX tests.)

Thanks for catching this!

				- Ted
Eric Biggers Aug. 21, 2018, 8:41 p.m. UTC | #2
On Tue, Aug 21, 2018 at 04:23:52PM -0400, Theodore Y. Ts'o wrote:
> On Tue, Aug 21, 2018 at 10:59:37AM -0700, Eric Biggers wrote:
> > From: Eric Biggers <ebiggers@google.com>
> > 
> > Since ext4 verity is going to be an RO_COMPAT feature rather than an
> > INCOMPAT one, the on-disk i_size of verity inodes needs to be the data
> > size rather than the full size.  Consequently, verity inodes will have
> > initialized blocks past i_size, containing the Merkle tree and other
> > verity metadata.  So e2fsck must not fix the i_size of such inodes as it
> > normally would.
> > 
> > Signed-off-by: Eric Biggers <ebiggers@google.com>
> 
> Thanks, applied.
> 
> We should have some tests, in e2fsprogs and/or xfstests that tests
> this.  The work-in-progress verity 9XX xfstests don't seem to have a
> problem with this, probably because we weren't unmounting a file
> system, and then running fsck.  (Since it's a scratch partition,
> the test harness doesn't run fsck after any of the 9XX tests.)
> 
> Thanks for catching this!
> 
> 				- Ted

Actually xfstests does run fsck on the scratch device.  This reason this wasn't
causing problems before is that the ext4 verity kernel patches were leaving the
on-disk i_size as the full size (size of data + verity metadata) rather than
setting it to just the data size.  I actually just changed this today, in order
to match 'verity' being a RO_COMPAT feature, and I've pushed out updates to both
the kernel [1] and xfstests [2] fs-verity patchsets to start using the ext4
feature flag.

So this *is* tested by the work-in-progress xfstests now, though a test could be
added to e2fsprogs too.

[1] https://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git/log/?h=fsverity
[2] https://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/xfstests-dev.git/log/?h=fsverity

Note that we also need to decide whether f2fs will set the on-disk i_size to the
data size as well.  Currently I still have it setting i_size to the full size.

- Eric
diff mbox series

Patch

diff --git a/e2fsck/pass1.c b/e2fsck/pass1.c
index ce43821d..8abf0c33 100644
--- a/e2fsck/pass1.c
+++ b/e2fsck/pass1.c
@@ -3447,7 +3447,8 @@  static void check_blocks(e2fsck_t ctx, struct problem_context *pctx,
 		size = EXT2_I_SIZE(inode);
 		if ((pb.last_init_lblock >= 0) &&
 		    /* Do not allow initialized allocated blocks past i_size*/
-		    (size < (__u64)pb.last_init_lblock * fs->blocksize))
+		    (size < (__u64)pb.last_init_lblock * fs->blocksize) &&
+		    !(inode->i_flags & EXT4_VERITY_FL))
 			bad_size = 3;
 		else if (!(extent_fs && (inode->i_flags & EXT4_EXTENTS_FL)) &&
 			 size > ext2_max_sizes[fs->super->s_log_block_size])