summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorUlrich Drepper <drepper@redhat.com>2008-03-30 08:51:55 +0000
committerUlrich Drepper <drepper@redhat.com>2008-03-30 08:51:55 +0000
commit221e523037ada3e77b6c5602db7a81ce478af70f (patch)
tree620873f7e75e251a4c5761ab44517b5c258a5997
parent43f6bec195805539de8c3ef717fe3529809478df (diff)
downloadglibc-221e523037ada3e77b6c5602db7a81ce478af70f.tar.gz
* sysdeps/unix/opendir.c (__alloc_dir): If allocation fails for size
provided through st_blksize, try the default size before giving up.
-rw-r--r--ChangeLog5
-rw-r--r--sysdeps/unix/opendir.c28
2 files changed, 25 insertions, 8 deletions
diff --git a/ChangeLog b/ChangeLog
index a43e7c6d52..8ac1f1820c 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,8 @@
+2008-03-30 Ulrich Drepper <drepper@redhat.com>
+
+ * sysdeps/unix/opendir.c (__alloc_dir): If allocation fails for size
+ provided through st_blksize, try the default size before giving up.
+
2008-03-29 Ulrich Drepper <drepper@redhat.com>
* stdio-common/vfprintf.c (vfprintf): Correct overflow test.
diff --git a/sysdeps/unix/opendir.c b/sysdeps/unix/opendir.c
index 0a116247d2..92029c6547 100644
--- a/sysdeps/unix/opendir.c
+++ b/sysdeps/unix/opendir.c
@@ -171,6 +171,8 @@ __alloc_dir (int fd, bool close_fd, const struct stat64 *statp)
goto lose;
}
+ const size_t default_allocation = (BUFSIZ < sizeof (struct dirent64)
+ ? sizeof (struct dirent64) : BUFSIZ);
size_t allocation;
#ifdef _STATBUF_ST_BLKSIZE
if (__builtin_expect ((size_t) statp->st_blksize >= sizeof (struct dirent64),
@@ -178,20 +180,30 @@ __alloc_dir (int fd, bool close_fd, const struct stat64 *statp)
allocation = statp->st_blksize;
else
#endif
- allocation = (BUFSIZ < sizeof (struct dirent64)
- ? sizeof (struct dirent64) : BUFSIZ);
+ allocation = default_allocation;
DIR *dirp = (DIR *) malloc (sizeof (DIR) + allocation);
if (dirp == NULL)
- lose:
{
- if (close_fd)
+#ifdef _STATBUF_ST_BLKSIZE
+ if (allocation == statp->st_blksize
+ && allocation != default_allocation)
{
- int save_errno = errno;
- close_not_cancel_no_status (fd);
- __set_errno (save_errno);
+ allocation = default_allocation;
+ dirp = (DIR *) malloc (sizeof (DIR) + allocation);
+ }
+ if (dirp == NULL)
+#endif
+ lose:
+ {
+ if (close_fd)
+ {
+ int save_errno = errno;
+ close_not_cancel_no_status (fd);
+ __set_errno (save_errno);
+ }
+ return NULL;
}
- return NULL;
}
dirp->fd = fd;