Darrick J. Wong [Fri, 15 Aug 2025 16:25:58 +0000 (09:25 -0700)]
libext2fs: relock CACHE_MTX after calling ->write_error
In the UNIX I/O manager, we drop CACHE_MTX before calling the
->write_error handler in case it decides to retry the failed write.
Therefore, we must retake the lock after it returns, to ensure
consistent lock state when flush_cached_blocks returns.
Cc: <linux-ext4@vger.kernel.org> # v1.46.6 Fixes: 0e0c7537eb5fdc ("libext2fs: unix_io: fix_potential error path deadlock in flush_cached_blocks()") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Thu, 14 Aug 2025 00:14:21 +0000 (17:14 -0700)]
fuse2fs: disable fallocate/zero range on indirect files
Indirect mapped files can't have unwritten extents, so we can't do
unwritten preallocation or zero-range because both depend on unwritten
extents.
Cc: <linux-ext4@vger.kernel.org> # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Wed, 13 Aug 2025 22:34:14 +0000 (15:34 -0700)]
fuse2fs: set EXT2_ERROR_FS when recording errors
Set the ERROR_FS bit when recording errors in the superblock so that
e2fsck will actually scan the filesystem without -f.
Cc: <linux-ext4@vger.kernel.org> # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Wed, 13 Aug 2025 18:00:49 +0000 (11:00 -0700)]
fuse2fs: don't write inode when inactivation fails
remove_inode has this weird behavior where it writes the inode to disk
even if the attempts to inactivate it (remove xattrs, truncate data)
fail. Worse yet, it doesn't even return the original error code, so it
masks failures. Fix this too.
Cc: <linux-ext4@vger.kernel.org> # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Wed, 13 Aug 2025 17:57:21 +0000 (10:57 -0700)]
fuse2fs: interpret error codes in remove_ea_inodes correctly
remove_ea_inodes should translate libext2fs error codes into errnos so
that fs developers can trace exactly where a failure occurred. Also
don't squash EA inode removal errors.
Cc: <linux-ext4@vger.kernel.org> # v1.47.3 Fixes: 3045aed621117f ("fuse2fs: fix removing ea inodes when freeing a file") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Tue, 8 Jul 2025 23:04:35 +0000 (16:04 -0700)]
fuse2fs: check for recorded fs errors before touching things
Refuse the mount if there are errors recorded in the superblock. We
should not be trying to replay the journal on damaged filesystems.
Cc: <linux-ext4@vger.kernel.org> # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Tue, 12 Aug 2025 21:18:33 +0000 (14:18 -0700)]
fuse2fs: don't run fallible operations in op_init
There's no way to return an error from the op_init function and have
libfuse tear down the mount, aside from calling fuse_session_exit and
aborting the program. Even that's not useful, because libfuse has
already daemonized us at that point, so the error messages are screamed
into a void.
Move the code that clears the VALID_FS bit to main() so that we can
abort the mount with a useful error message if that write fails.
Cc: <linux-ext4@vger.kernel.org> # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Fri, 8 Aug 2025 18:58:12 +0000 (11:58 -0700)]
fuse2fs: don't let ENOENT escape from ioctl_fitrim
If ext2fs_find_first_set_block_bitmap2 returns ENOENT to indicate
that there are no bits set between start and b, then the entire region
is free space and we can discard it. In that case, zero out err so that
it won't get returned as an error.
Cc: <linux-ext4@vger.kernel.org> # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Thu, 12 Jun 2025 00:13:34 +0000 (17:13 -0700)]
fuse2fs: allow O_APPEND and O_TRUNC opens
Commit 9f69dfc4e275cc didn't quite get the permissions checking correct:
generic/362 - output mismatch (see /var/tmp/fstests/generic/362.out.bad)
--- tests/generic/362.out 2025-04-30 16:20:44.563833050 -0700
+++ /var/tmp/fstests/generic/362.out.bad 2025-06-11 17:04:24.061193618 -0700
@@ -1,2 +1,3 @@
QA output created by 362
+Failed to open/create file: Operation not permitted
Silence is golden
...
(Run 'diff -u /run/fstests/bin/tests/generic/362.out /var/tmp/fstests/generic/362.out.bad' to see the entire diff)
The kernel allows opening a file for append and truncation. What it
doesn't allow is opening an append-only file for truncation. Note that
this causes generic/079 to regress, but the root cause of that problem
is actually that fuse oddly supports FS_IOC_[GS]ETFLAGS but doesn't
actually set the VFS inode flags.
Darrick J. Wong [Fri, 8 Aug 2025 16:27:39 +0000 (09:27 -0700)]
fuse2fs: fix various problems in get_req_groups
get_req_groups has two problems: first, it doesn't free the array if
fuse_getgroups errors out; and it passes errors to its caller. The
memory leak is an obvious fix, but in the error case we actually want to
fall back to checking the sole gid that the fuse request context gave
us. Fix both of these errors.
Cc: <linux-ext4@vger.kernel.org> # v1.47.3 Fixes: 3469e6ff606af8 ("fuse2fs: fix group membership checking in op_chmod") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Thu, 7 Aug 2025 17:30:34 +0000 (10:30 -0700)]
fuse2fs: fix readlink failure
For readlink of slow symlinks, an IO error when reading the link target
cause memory corruption. This happens because the error case for
ext2fs_file_read closes the file, translates the error, but then jumps
down to the regular termination code, which re-closes the file and is
hence a UAF. Straighten out the error paths to eliminate the UAF.
Also fix the bug that short target reads aren't flagged as corruption
as is done in the kernel.
Cc: <linux-ext4@vger.kernel.org> # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Thu, 31 Jul 2025 00:51:12 +0000 (17:51 -0700)]
mke2fs: don't print warnings about dax to stderr
mke2fs prints a warning to standard error if the target device supports
fsdax but the fs block size doesn't match the page size. This isn't an
error since we don't abort the format and the filesystem will work just
fine if the user doesn't care about fsdax.
Therefore, print the warning to stdout, not stderr.
Cc: <linux-ext4@vger.kernel.org> # v1.45.7 Fixes: f4979dd566acc4 ("mke2fs: Warn if fs block size is incompatible with DAX") Signed-off-by: "Darrick J. Wong" <djwong@kernel.org>
Darrick J. Wong [Wed, 30 Jul 2025 17:23:24 +0000 (10:23 -0700)]
fuse2fs: fix block parameter truncation on 32-bit
Use the blk64_t variants of the io channel read/write methods when we
have to do partial block zeroing for hole punching because otherwise
we corrupt large 64-bit filesystems on 32-bit fuse2fs due to integer
truncation.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250730172324.GR2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Sat, 26 Jul 2025 16:28:48 +0000 (09:28 -0700)]
fuse2fs: fix punching post-EOF blocks during truncate
ext2fs_punch() can update the inode that's passed in, so we need to
write it back. This should fix some fstests failures where the test
file system ends up with inodes where all extent records fit within the
inode but inexplicably have extents beyond EOF. While we're at it, add
the fuse2fs prefix to the two helper functions.
Cc: linux-ext4@vger.kernel.org # v1.47.3 Fixes: 4581ac60eb53ec ("fuse2fs: fix post-EOF preallocation clearing on truncation") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250726162848.GQ2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Fri, 25 Jul 2025 15:56:10 +0000 (08:56 -0700)]
fuse2fs: don't record every errno in the superblock as an fs failure
fstests just blew up because somewhere in the fuse iomap code we
returned an ESTALE, which was then passed to translate_error. That
function decided it was a Serious Error and wrote it to the superblock,
so every subsequent mount attempt failed.
I should go figure out why the iomap cache upsert operation returned
ESTALE, but that's not a sign that the *ondisk* filesystem is corrupt.
Prior to commit 71f046a788adba we wouldn't have written that to the
superblock either.
Fix this by isolating the handful of errno that usually mean corruption
problems in filesystems and writing those to the superblock; the other
errno are merely operational errors that can be passed back to the
kernel and up to userspace.
I'm not sure why e2fsck doesn't flag when s_error_count > 0. That might
be an error on its own.
Cc: linux-ext4@vger.kernel.org # v1.47.3 Fixes: 71f046a788adba ("fuse2fs: correctly handle system errno values in __translate_error()") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250725155610.GP2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Tue, 22 Jul 2025 19:40:53 +0000 (12:40 -0700)]
fuse2fs: fix logging redirection
Someone pointed out that you can't just go around reassigning stdout and
stderr because section 7.23.1 paragraph 4 of a recent C2y draft says
that stdin, stdout, and stderr “are expressions of type "pointer to
FILE" that point to the FILE objects associated, respectively, with the
standard error, input, and output streams.”
The use of the word "expression" should have been the warning sign that
a symbol that can be mostly used as a pointer is not simply a pointer.
Seven pages later, footnote 318 of the C2y draft clarifies that stdin,
stdout, and stderr “need not be modifiable lvalues to which the value
returned by the fopen function could be assigned.”
"need not be" is the magic phrasing that means that glibc, musl, and
mingw (for example) have very different declarations of stdout:
glibc:
extern FILE *stdout; /* Standard output stream. */
musl:
extern FILE *const stdout;
mingw:
#define stdout (&_iob[STDOUT_FILENO])
All three are following the specification, yet you can write C code that
fails to compile what otherwise looks like a normal assignment on two of
the libraries:
int main(int argc, char *argv[])
{
fark = NULL;
crows = NULL;
stupid = NULL;
}
/tmp/a.c: In function ‘main’:
/tmp/a.c:20:14: error: assignment of read-only variable ‘fark’
20 | fark = NULL;
| ^
/tmp/a.c:21:15: error: lvalue required as left operand of assignment
21 | crows = NULL;
| ^
What a useless specification! You don't even get the same error!
Unfortunately, this leadership vacuum means that each implementation of
a so-called standard C library is perfectly within its right to do this.
IOWs, the authors decided that every C programmer must divert some of
the brainpower they could spend on their program's core algorithms to be
really smart about this quirk.
A whole committee of very smart programmers collectively decided this
was a good way to run things decades ago so that C library authors in
the 1980s wouldn't have to change their code, and subsequent gatherings
have reaffirmed this "practical" decision. Their suggestion to reassign
stdout and stderr is to use freopen, but that walks the specified path,
which is racy if you want both streams to point to the same file. You
could pass /dev/fd/XX to solve the race, but then you lose portability.
In other words, they "engineered" an incomplete solution with problems
to achieve a short term goal that nobody should care about 40 years
later.
Fix fuse2fs by rearranging the code to change STD{OUT,ERR}_FILENO to
point to the same open logfile via dup2 and then try to use freopen on
/dev/fd/XX to capture any stdout/err usage by the libraries that fuse2fs
depends on.
Note that we must do the whole thing over again in op_init because
libfuse will dup2 STD{OUT,ERR}_FILE to /dev/null as part of daemonizing
the server.
start and end are both zero, so we call ext2fs_punch with those
arguments. ext2fs_punch interprets [start, end] as a closed interval
and removes block 0, which is not what we asked for!
The computation of end is also too subtle -- the dividend is the
expression (0 + 1 - 4096) which produces a negative number because off_t
is defined to be long long, at least on amd64 Linux. We rely on the
behavior that dividing a negative dividend by a positive divisor
produces a quotient of zero.
Really what we should do here is round offset up to the next fsblock
and offset+len down to the nearest fsblock. The first quantity is the
first byte of the range to punch and the second quantity is the next
byte past the range to punch. Using those as the basis to compute start
and end, the punch should only happen if start < end, and we should pass
[start, end - 1] to ext2fs_punch because it expects a closed interval.
Improve the comments here so that I don't have to work all this out
again the next time I read through here.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Here we can clearly see that the first byte of the block has not been
zeroed, even though that's what the caller wanted us to do. This is due
to an incorrect check of the residue variable that was most likely copy
pasted from clean_block_edge years ago.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Darrick J. Wong [Thu, 17 Jul 2025 14:59:50 +0000 (07:59 -0700)]
libext2fs: fix data corruption when writing to inline data files
Fix various bugs in ext2fs_file_write_inline_data:
- "count = nbytes - pos" makes no sense since nbytes is already a
length value and results in short writes if pos > 0.
- Pass the correct file size to ext2fs_inline_data_set because count
will not be the file size if pos > 0.
- Simplify the decision to increase the file size.
- Don't let a huge write corrupt memory beyond file->buf.
- Zero the buffer between isize and pos if we're doing a sparse write
past EOF.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 54e880b870f7fe ("libext2fs: handle inline data in read/write function") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250717145950.GJ2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Thu, 17 Jul 2025 14:59:33 +0000 (07:59 -0700)]
libext2fs: fix data read corruption in ext2fs_file_read_inline_data
Fix numerous problems in the function that reads data from an inlinedata
file:
- Reads starting after isize should be returned as short reads.
- Reads past the end of the inline data should return zeroes.
- Reads from the inline data buffer must not exceed isize.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 54e880b870f7fe ("libext2fs: handle inline data in read/write function") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250717145933.GI2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Thu, 17 Jul 2025 14:59:10 +0000 (07:59 -0700)]
fuse2fs: fix ST_RDONLY setting
Only set ST_RDONLY if the filesystem isn't writable.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250717145910.GH2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Wed, 9 Jul 2025 16:51:52 +0000 (09:51 -0700)]
fuse2fs: fix race condition in op_destroy
On a regular fuse server (i.e. one not running in fuseblk mode), libfuse
synthesizes and dispatches a FUSE_DESTROY command as soon as the event
dispatch loop terminates after the kernel disconnects /dev/fuse.
Unfortunately, this is done without coordinating with any other threads
that may have already received a real FUSE command from the kernel.
In other words, FUSE_DESTROY can run in parallel with other
fuse_operations. Therefore, we must guard the body of this function
with the BKL just like any other fuse operation or risk races within
libext2fs. If we're lucky, we trash the ext2_filsys state and
generic/488 will crash.
If we're not lucky, it corrupts the ondisk filesystem resulting in a
e2fsck complaining as well.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250709165152.GE2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
and the second mount attempt succeeds where it really shouldn't. This
is due to the use of fopen(..., "w"), because "w" means "truncate or
create". It does /not/ imply O_CREAT | O_EXCL, which fails if the file
already exists. Theoretically that could have been done with mode
string "wx", but that's a glibc extension.
Fix this by calling open() directly with the O_ modes that we want.
Cc: linux-ext4@vger.kernel.org # v1.47.3-rc3 Fixes: e50fbaa4d156a6 ("fuse2fs: clean up the lockfile handling") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250708173333.GD2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Mon, 7 Jul 2025 16:05:25 +0000 (09:05 -0700)]
fuse2fs: fix relatime comparisons
generic/192 fails like this even before we start adding iomap code:
--- tests/generic/192.out 2025-04-30 16:20:44.512675591 -0700
+++ tests/generic/192.out.bad 2025-07-06 22:26:11.666015735 -0700
@@ -1,5 +1,6 @@
QA output created by 192
sleep for 5 seconds
test
-delta1 is in range
+delta1 has value of 0
+delta1 is NOT in range 5 .. 7
delta2 is in range
The cause of this regression is that the timestamp comparisons account
only for seconds, not nanoseconds. If a write came in 100ms after the
last read but still in the same second, then we fail to update atime on
a subsequent read.
Fix this by converting the timespecs to doubles so that we can include
the nanoseconds component, and then perform the comparison in floating
point mode.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250707160525.GC2672022@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Sun, 6 Jul 2025 18:32:34 +0000 (11:32 -0700)]
fuse2fs: fix incorrect unit conversion at the end of FITRIM
generic/260 also points out that the bytes cleared are in the wrong
units -- they're supposed to be in bytes, but the "cleared" variable is
in units of fsblocks. Fix that.
Darrick J. Wong [Thu, 31 Jul 2025 14:38:21 +0000 (10:38 -0400)]
fuse2fs: fix incorrect EOFS input handling in FITRIM
FITRIM isn't well documented, which means that I missed that
len == -1ULL always means "trim to end of filesystem". generic/260 has
been failing with:
--- a/tests/generic/260.out 2025-04-30 16:20:44.532797310 -0700
+++ b/tests/generic/260.out.bad 2025-07-03 11:44:26.946394170 -0700
@@ -11,4 +11,5 @@
[+] Default length with start set (should succeed)
[+] Length beyond the end of fs (should succeed)
[+] Length beyond the end of fs with start set (should succeed)
+After the full fs discard 0 bytes were discarded however the file system is 10401542144 bytes long.
Test done
because the addition used to compute end suffered an integer overflow,
resulting in end < start, which meant nothing happened. Fix this by
explicitly checking for -1ULL.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Darrick J. Wong [Sun, 6 Jul 2025 18:31:47 +0000 (11:31 -0700)]
fuse2fs: fix gid inheritance on sgid parent directories
When a child file is created inside a setgid parent directory, the child
is supposed to inherit the gid of the parent, not the fsgid of the
creating process. Fix this error, which was discovered by generic/633,
generic/696, and generic/697.
Darrick J. Wong [Sun, 6 Jul 2025 18:31:16 +0000 (11:31 -0700)]
libext2fs: fix arguments passed to ->block_alloc_stats_range
In ext2fs_block_alloc_stats_range, we use @num as the loop counter but
then pass it to the callback and @blk as the loop cursor. This means
that the range passed to e2fsck_block_alloc_stats_range starts beyond
the range that was actually freed and has a length of zero, which is not
at all correct.
Fix this by saving the original values and passing those instead.
Darrick J. Wong [Sun, 6 Jul 2025 18:31:00 +0000 (11:31 -0700)]
libext2fs: fix off-by-one bug in punch_extent_blocks
punch_extent_blocks tries to validate its input parameters to make sure
that the physical range of blocks being punched do not go past the end
of the filesystem. Unfortunately, there's an off-by-one bug in the
valiation, because start==0 count==10 is a perfectly valid range on a
10-block filesystem.
fuse2fs: fix normal (non-kernel) permissions checking
Commit 9f69dfc4e275 ("fuse2fs: implement O_APPEND correctly") defined
a new flag, A_OK, to add support for testing whether the file is valid
for append operations. This is relevant for the check_iflags_access()
function, but when are later testing operations mask against the inode
permissions, this new flag gets in the way and causes non-root users
attempting to create new inodes in a directory to fail. Fix this by
masking off A_OK before doing these tests.
Avoid redefining CACHE_LINE_SIZE if system provides it.
FreeBSD 14.3 complains about our trying to redefine
the CACHE_LINE_SIZE, which happens to be 1 << 6 == 64
on amd64 but not arm64.
Just check and only #define unless it's already:
../../../lib/ext2fs/unix_io.c:563: warning: "CACHE_LINE_SIZE" redefined
563 | #define CACHE_LINE_SIZE 64
|
In file included from /usr/include/sys/param.h:163,
from /usr/include/bsm/audit.h:41,
from /usr/include/sys/ucred.h:42,
from /usr/include/sys/mount.h:37,
from ../../../lib/ext2fs/unix_io.c:53:
/usr/include/machine/param.h:92: note: this is the location of the previous definition
92 | #define CACHE_LINE_SIZE (1 << CACHE_LINE_SHIFT)
|
On FreeBSD 14.3, machine/param.h
- for arm64 and powerpc define CACHE_LINE_SIZE to (128),
- for i386, amd64, arm (32) and riscv define (64).
Care was taken to make sure where to quote and where not to; variable
assignments with EGREP=@EGREP@ need quoting in order not to split the
variable into tokens; expansions in places where we used to invoke egrep
need not because they actually need to split $EGREP contents in case
it's "grep -E".
This fixes "egrep is obsolescent" warnings on newer coreutils.
Samuel Smith [Sat, 28 Jun 2025 05:14:15 +0000 (00:14 -0500)]
e2scrub: honor fstrim setting in e2scrub.conf
The systemd service unconditionally passes -t to e2scrub, forcing
fstrim to run after every scrub regardless of the fstrim setting
in /etc/e2scrub.conf. Removing the hardcoded flag will allow users to
control the behavior via the configuration file.
Matthias Andree [Thu, 26 Jun 2025 20:28:40 +0000 (22:28 +0200)]
m_offset: make self-test reliable with non-GNU yes(1)
m_offset has been failing sporadically on FreeBSD, and always because
crc_exp(ected) was different from all other CRC values (which were
mutually equal, first1, first2, last).
The test scrsipt uses yes(1) to write into dd(1),
but FreeBSD's "yes a" use sizes of 8192 - length-of-pattern, meaning
8190 with "a\n" (meaning a + LF).
GNU yes from coreutils 9.1 instead dispatches 1024-sized writes.
The peculiar thing is that dd bs=1k count=512 will dispatch 512 read
attempts of 1 k each, but due to yes and dd running concurrently, dd
will sometimes see a short read block, resulting in an overall shorter
output file fed into crcsum, leading to a mismatched crc_exp value.
Fix: Add iflag=fullblock to ensure the proper output size will be fed
into crcsum, even if that means doing more than 512 reads internally.
Darrick J. Wong [Mon, 16 Jun 2025 15:06:14 +0000 (08:06 -0700)]
fuse2fs: clean up the lockfile handling
Fix various problems with the new lockfile code in fuse2fs: the printfs
should use the actual logging function err_printf, the messages should
be looked up in gettext, we should actually exit main properly on
error instead of calling exit(), and the error message printing for the
final lockfile unlink is broken.
debian: use dpkg-shlibdeps for library dependency calculation
* Drop old shlibs.local. The file is not needed and "This file should
normally not be used" according to:
https://www.debian.org/doc/debian-policy/ch-sharedlibs.html#the-shlibs-files-present-on-the-system
* Remove manual dependency on libcom-err2 as dpkg-shlibdeps will compute
and add it to ${shlibs:Depends}.
Theodore Ts'o [Sun, 15 Jun 2025 10:30:05 +0000 (06:30 -0400)]
Use static linking for libarchive by default on MacOS
Apparently dlopen() path searching doesn't work or is unreliable on
MacOS; it appears to not search LD_LIBRARY_PATH, DYLD_LIBRARY_PATH, or
DYLD_FALLBACK_LIBRARY_PATH as documented by the dlopen(3) man page.
Furthmore setting any of these variables to include /opt/local/lib,
which is where MacPort drops libarchive.13.dylib, can cause all manner
of warnings when running other dynamically linked programs, such as
"grep". What a mess. It appears dlopen(2) support in MacOS is a
disaster, and it's not really needed since we don't care about the
size of mke2fs on installation media on non-Linux systems. So default
to using --with-libarchive=direct for MacOS.
Theodore Ts'o [Sat, 14 Jun 2025 20:47:26 +0000 (16:47 -0400)]
Use the fuse3 libraries reported by pkg-config
It used to be that PKG_CHECK_MODULES would set foo_LDFLAGS; not it
just sets the foo_LIBS with the required -L and -l options. Fix this
up for fuse3 support.
Darrick J. Wong [Thu, 12 Jun 2025 22:18:26 +0000 (15:18 -0700)]
libext2fs: fix bounding error in the extent fallocate code
generic/361 popped up this weird error:
generic/361 [failed, exit status 1]- output mismatch (see /var/tmp/fstests/generic/361.out.bad)
--- tests/generic/361.out 2025-04-30 16:20:44.563589363 -0700
+++ /var/tmp/fstests/generic/361.out.bad 2025-06-11 10:40:07.475036412 -0700
@@ -1,2 +1,2 @@
QA output created by 361
-Silence is golden
+mkfs.fuse.ext4: Input/output error while writing out and closing file system
...
(Run 'diff -u /run/fstests/bin/tests/generic/361.out /var/tmp/fstests/generic/361.out.bad' to see the entire diff)
The test formats a small filesystem, creates a larger sparse file, loop
mounts it, and tries to format an ext4 filesystem on the loopdev. The
loop driver sends fallocate zero_range requests to fuse2fs, but stumbles
over this extent tree layout when fallocating 16 blocks at offset 145:
EXTENTS:
(262128-262143[u]):2127-2142
fallocate goes to offset 145, and sees the right-extent at 262128.
Oddly, it then tries to allocate 262128-145 blocks instead of the 16
that were asked for, so it tries to allocate a huge number of blocks
but then crashes and burns when it runs out of space.
Fix this by constraining the len parameter to ext_falloc_helper to the
correct value.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 5aad5b8e0e3cfa ("libext2fs: implement fallocate") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Link: https://lore.kernel.org/r/20250612221826.GE6134@frogsfrogsfrogs Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Wed, 11 Jun 2025 16:44:01 +0000 (09:44 -0700)]
fuse2fs: fix error bailout in op_create
Tim Woodall pointed out that op_create returns garbage error codes if
the ext2fs_extent_open2 in op_create fails. Worse than that, it also
neglects to drop the bfl and leaks temp_path. Let's fix all that.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Reported-by: Tim Woodall <debianbugs@woodall.me.uk> Signed-off-by: Darrick J. Wong <djwong@kernel.org> Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Darrick J. Wong [Wed, 11 Jun 2025 16:43:45 +0000 (09:43 -0700)]
libext2fs: fix spurious warnings from fallocate
generic/522 routinely produces error messages from fuse2fs like this:
FUSE2FS (sde): Illegal block number passed to ext2fs_test_block_bitmap #9321 for block bitmap for /dev/sde
Curiously, these don't actually result in errors being thrown up to the
kernel. Digging into the program (which was more difficult than it
needed to be because of the weird bitmap base + errcode weirdness)
produced a left record:
e_lblk = 16
e_pblk = 9293
e_len = 6
e_flags = 0
and a right record:
e_lblk = 45
e_pblk = 9321
e_len = 6
e_flags = 0
Thus we end up in the "Merge both extents together, perhaps?" section of
ext_falloc_helper. Unfortunately, the merge selection code isn't smart
enough to notice that the two mappings aren't actually physically
contiguous, so it scans the bitmap with a negative length, which is why
the assertion trips.
The simple fix here is not to try to merge the adjacent extents if
they're not actually physically contiguous.
Cc: linux-ext4@vger.kernel.org # v1.43 Fixes: 5aad5b8e0e3cfa ("libext2fs: implement fallocate") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Theodore Ts'o [Thu, 12 Jun 2025 16:33:44 +0000 (14:03 -0230)]
fuse2fs: correctly handle system errno values in __translate_error()
Fixes: 81cbf1ef4f5dab ("misc: add fuse2fs, a FUSE server for e2fsprogs") Reported-by: "Darrick J. Wong" <djwong@kernel.org> Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Theodore Ts'o [Tue, 10 Jun 2025 17:04:08 +0000 (13:04 -0400)]
debian: fix typo in fuse2fs.postrm which breaks a /usr-move mitigation
A space was accidenally introduced into the fuse2fs.postrm which
breaks the /usr-move replacement of fusext2 from an older legacy
package that had been abandoned upstream. Specifically, what was
broken was the cleanup of the protective diversions:
Theodore Ts'o [Fri, 6 Jun 2025 22:52:13 +0000 (18:52 -0400)]
libext2fs: fix ext2fs_link() when the directory has an extent tree depth > 1
Ext2fs_link() was passing the wrong inode number to ext2fs_bmap(); as
a result, when a directory inode was using extents and the extent tree
depth was greater than 1, the extent tree checksum would be
incorrectly calculated resulting in a error that the extent tree block
checksum was incorrect.
Fixes: 53aa6c54224f ("libext2fs: add the EXT2FS_LINK_APPEND flag ...)
Addresses-Debian-Bug: #1106854 Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Theodore Ts'o [Fri, 6 Jun 2025 13:07:11 +0000 (09:07 -0400)]
libext2fs: fix a extent tree corruption bug in ext2fs_extent_set_bmap()
In the case where we are moving a particular logical block mapping
from a particular extent tree entry, to the immediately precending
entry (when the physical block or uninitialized flag is changing so it
can be coalesced with the precending entry) and the precending entry
is in a different extent tree block, the resulting extent tree can get
corrupted.
Fix this by removing the original logical block mapping before adding
the new logical block mapping. Per the warning in the comments before
ext2fs_extents_fix_parents():
Note a subtlety of this function -- if there happen to be two extents
mapping the same lblk and someone calls fix_parents on the second of
the two extents, the position of the extent handle after the call will
be the second extent if nothing happened, or the first extent if
something did. A caller in this situation must use
ext2fs_extent_goto() after calling this function. Or simply don't map
the same lblk with two extents, ever.
Theodore Ts'o [Wed, 4 Jun 2025 00:16:30 +0000 (00:16 +0000)]
misc: define alternative errno if OS doesn't provide ENODATA
FreeBSD doesn't define ENODATA, and uses ENOATTR when an extended
attribute is not found. So map ENODATA to ENOATTR to fix a build
failure for platforms that don't define ENODATA.
Theodore Ts'o [Tue, 3 Jun 2025 23:06:37 +0000 (23:06 +0000)]
debian: add a Built-Using field to the e2fsck-static package
We will probably want to eventually revert this commit and replace it
with a change using dh-builtusing, such as can be found in [1], but
dh-builtusing is only available in Debian 13 (trixie) and we don't
want to make life difficult for people who need to backport to Debian
Stable or Ubuntu LTS.