Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 11 Jul 2025 20:43:51 GMT
From:      Dag-Erling =?utf-8?Q?Sm=C3=B8rgrav?= <des@FreeBSD.org>
To:        src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-main@FreeBSD.org
Subject:   git: 920b2183919e - main - readdir: Fix error check.
Message-ID:  <202507112043.56BKhpGc086930@gitrepo.freebsd.org>

next in thread | raw e-mail | index | archive | help
The branch main has been updated by des:

URL: https://cgit.FreeBSD.org/src/commit/?id=920b2183919e430cf85c4aa1fa337bfded12aee5

commit 920b2183919e430cf85c4aa1fa337bfded12aee5
Author:     Dag-Erling Smørgrav <des@FreeBSD.org>
AuthorDate: 2025-07-11 20:43:20 +0000
Commit:     Dag-Erling Smørgrav <des@FreeBSD.org>
CommitDate: 2025-07-11 20:43:32 +0000

    readdir: Fix error check.
    
    Now that dd_size is unsigned, we need to check if the return value from
    getdirentries() was negative before assigning it to dd_size.
    
    While here, simplify the scandir_error test case slightly, and verify
    that calling readdir() again after EOF still returns NULL.
    
    Fixes:          42e613018da5
    Sponsored by:   Klara, Inc.
    Reviewed by:    kevans
    Differential Revision:  https://reviews.freebsd.org/D51266
---
 lib/libc/gen/readdir.c            |  7 +++++--
 lib/libc/tests/gen/opendir_test.c |  1 +
 lib/libc/tests/gen/scandir_test.c | 12 +++++-------
 3 files changed, 11 insertions(+), 9 deletions(-)

diff --git a/lib/libc/gen/readdir.c b/lib/libc/gen/readdir.c
index 32603c0b4677..b70102954df1 100644
--- a/lib/libc/gen/readdir.c
+++ b/lib/libc/gen/readdir.c
@@ -50,6 +50,7 @@ _readdir_unlocked(DIR *dirp, int flags)
 	struct dirent *dp;
 	off_t initial_seek;
 	size_t initial_loc = 0;
+	ssize_t ret;
 
 	for (;;) {
 		if (dirp->dd_loc >= dirp->dd_size) {
@@ -61,11 +62,13 @@ _readdir_unlocked(DIR *dirp, int flags)
 		}
 		if (dirp->dd_loc == 0 &&
 		    !(dirp->dd_flags & (__DTF_READALL | __DTF_SKIPREAD))) {
+			dirp->dd_size = 0;
 			initial_seek = dirp->dd_seek;
-			dirp->dd_size = _getdirentries(dirp->dd_fd,
+			ret = _getdirentries(dirp->dd_fd,
 			    dirp->dd_buf, dirp->dd_len, &dirp->dd_seek);
-			if (dirp->dd_size <= 0)
+			if (ret <= 0)
 				return (NULL);
+			dirp->dd_size = (size_t)ret;
 			_fixtelldir(dirp, initial_seek, initial_loc);
 		}
 		dirp->dd_flags &= ~__DTF_SKIPREAD;
diff --git a/lib/libc/tests/gen/opendir_test.c b/lib/libc/tests/gen/opendir_test.c
index 89be2becc607..b7481255654f 100644
--- a/lib/libc/tests/gen/opendir_test.c
+++ b/lib/libc/tests/gen/opendir_test.c
@@ -46,6 +46,7 @@ opendir_check(const struct atf_tc *tc, DIR *dirp)
 	ATF_CHECK_STREQ("subdir", ent->d_name);
 	ATF_CHECK_EQ(DT_DIR, ent->d_type);
 	ATF_CHECK(readdir(dirp) == NULL);
+	ATF_CHECK(readdir(dirp) == NULL);
 }
 
 ATF_TC(opendir_ok);
diff --git a/lib/libc/tests/gen/scandir_test.c b/lib/libc/tests/gen/scandir_test.c
index f7b52b5e3616..afd25bf7c0b2 100644
--- a/lib/libc/tests/gen/scandir_test.c
+++ b/lib/libc/tests/gen/scandir_test.c
@@ -157,7 +157,7 @@ ATF_TC_BODY(scandir_error, tc)
 {
 	char path[16];
 	struct dirent **namelist = NULL;
-	int fd, i, ret;
+	int fd, i;
 
 	ATF_REQUIRE_EQ(0, mkdir("dir", 0755));
 	for (i = 0; i < 1024; i++) {
@@ -170,9 +170,8 @@ ATF_TC_BODY(scandir_error, tc)
 	scandir_error_count = 0;
 	scandir_error_fd = fd;
 	scandir_error_select_return = 0;
-	ret = fdscandir(fd, &namelist, scandir_error_select, NULL);
-	ATF_CHECK_EQ(-1, ret);
-	ATF_CHECK_ERRNO(EBADF, ret < 0);
+	ATF_CHECK_ERRNO(EBADF,
+	    fdscandir(fd, &namelist, scandir_error_select, NULL) < 0);
 	ATF_CHECK_EQ(NULL, namelist);
 
 	/* second pass, select everything */
@@ -180,9 +179,8 @@ ATF_TC_BODY(scandir_error, tc)
 	scandir_error_count = 0;
 	scandir_error_fd = fd;
 	scandir_error_select_return = 1;
-	ret = fdscandir(fd, &namelist, scandir_error_select, NULL);
-	ATF_CHECK_EQ(-1, ret);
-	ATF_CHECK_ERRNO(EBADF, ret < 0);
+	ATF_CHECK_ERRNO(EBADF,
+	    fdscandir(fd, &namelist, scandir_error_select, NULL) < 0);
 	ATF_CHECK_EQ(NULL, namelist);
 }
 



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?202507112043.56BKhpGc086930>