]> sourceware.org Git - glibc.git/commitdiff
Linux: readdir_r needs to report getdents failures (bug 32124)
authorFlorian Weimer <fweimer@redhat.com>
Fri, 30 Aug 2024 19:52:23 +0000 (21:52 +0200)
committerFlorian Weimer <fweimer@redhat.com>
Thu, 5 Sep 2024 10:05:32 +0000 (12:05 +0200)
Upon error, return the errno value set by the __getdents call
in __readdir_unlocked.  Previously, kernel-reported errors
were ignored.

Reviewed-by: DJ Delorie <dj@redhat.com>
sysdeps/unix/sysv/linux/readdir_r.c

index ffd5262cf5a6f8857cb7b7112f0aa8d70a8ede04..1d595688f78ccd7759cace5099ff2b1de43313a0 100644 (file)
@@ -25,14 +25,22 @@ __readdir_r (DIR *dirp, struct dirent *entry, struct dirent **result)
 {
   struct dirent *dp;
   size_t reclen;
+  int saved_errno = errno;
 
   __libc_lock_lock (dirp->lock);
 
   while (1)
     {
+      /* If errno is changed from 0, the NULL return value indicates
+        an actual error.  It overrides a pending ENAMETOOLONG error.  */
+      __set_errno (0);
       dp = __readdir_unlocked (dirp);
       if (dp == NULL)
-       break;
+       {
+         if (errno != 0)
+           dirp->errcode = errno;
+         break;
+       }
 
       reclen = dp->d_reclen;
       if (reclen <= offsetof (struct dirent, d_name) + NAME_MAX + 1)
@@ -61,6 +69,7 @@ __readdir_r (DIR *dirp, struct dirent *entry, struct dirent **result)
 
   __libc_lock_unlock (dirp->lock);
 
+  __set_errno (saved_errno);
   return dp != NULL ? 0 : dirp->errcode;
 }
 
This page took 0.038644 seconds and 5 git commands to generate.