[PATCH 4/5] fs: ext4: reject dirents with too-small direntlen to prevent infinite loops

Sascha Hauer s.hauer at pengutronix.de
Thu Apr 2 03:12:32 PDT 2026


ext4fs_iterate_dir() and ext4fs_get_ino() walk directory entries using
dirent->direntlen from disk to advance the position. If a crafted
filesystem has direntlen == 0, the position never advances, causing an
infinite loop that can only be broken by a reset.

Reject directory entries where direntlen is smaller than the minimum
dirent struct size. This catches the zero case and also prevents
reading overlapping dirents.

Signed-off-by: Sascha Hauer <s.hauer at pengutronix.de>
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply at anthropic.com>
---
 fs/ext4/ext4_common.c | 2 ++
 fs/ext4/ext_barebox.c | 2 ++
 2 files changed, 4 insertions(+)

diff --git a/fs/ext4/ext4_common.c b/fs/ext4/ext4_common.c
index 5d252b4a2c..b0c78f9e9a 100644
--- a/fs/ext4/ext4_common.c
+++ b/fs/ext4/ext4_common.c
@@ -359,6 +359,8 @@ int ext4fs_iterate_dir(struct ext2fs_node *dir, char *name,
 
 			free(fdiro);
 		}
+		if (le16_to_cpu(dirent.direntlen) < sizeof(struct ext2_dirent))
+			return -EINVAL;
 		fpos += le16_to_cpu(dirent.direntlen);
 	}
 	return -ENOENT;
diff --git a/fs/ext4/ext_barebox.c b/fs/ext4/ext_barebox.c
index ef1a71368d..f9a978c10c 100644
--- a/fs/ext4/ext_barebox.c
+++ b/fs/ext4/ext_barebox.c
@@ -106,6 +106,8 @@ static int ext4fs_get_ino(struct ext2fs_node *dir, struct qstr *name, int *inum)
 				return 0;
 			}
 		}
+		if (le16_to_cpu(dirent.direntlen) < sizeof(struct ext2_dirent))
+			return -EINVAL;
 		fpos += le16_to_cpu(dirent.direntlen);
 	}
 

-- 
2.47.3




More information about the barebox mailing list