[Midnightbsd-cvs] src: libc/gen: Do not read away the target directory entry when

laffer1 at midnightbsd.org laffer1 at midnightbsd.org
Sun May 11 23:16:02 EDT 2008


Log Message:
-----------
Do not read away the target directory entry when encountering deleted
files after a seekdir().

The seekdir shall set the position for the next readdir operation.
When the _readdir_unlocked() encounters deleted entry, dd_loc is
already advanced. Continuing the loop leads to premature read of
the target entry.

Submitted by:	Marc Balmer <mbalmer at openbsd org>
Obtained from:	OpenBSD

Modified Files:
--------------
    src/lib/libc/gen:
        readdir.c (r1.2 -> r1.3)
        telldir.c (r1.1.1.1 -> r1.2)
        telldir.h (r1.1.1.1 -> r1.2)

-------------- next part --------------
Index: telldir.h
===================================================================
RCS file: /home/cvs/src/lib/libc/gen/telldir.h,v
retrieving revision 1.1.1.1
retrieving revision 1.2
diff -L lib/libc/gen/telldir.h -L lib/libc/gen/telldir.h -u -r1.1.1.1 -r1.2
--- lib/libc/gen/telldir.h
+++ lib/libc/gen/telldir.h
@@ -59,7 +59,7 @@
 	long	td_loccnt;	/* index of entry for sequential readdir's */
 };
 
-struct dirent	*_readdir_unlocked(DIR *);
+struct dirent	*_readdir_unlocked(DIR *, int);
 void 		_reclaim_telldir(DIR *);
 void 		_seekdir(DIR *, long);
 
Index: readdir.c
===================================================================
RCS file: /home/cvs/src/lib/libc/gen/readdir.c,v
retrieving revision 1.2
retrieving revision 1.3
diff -L lib/libc/gen/readdir.c -L lib/libc/gen/readdir.c -u -r1.2 -r1.3
--- lib/libc/gen/readdir.c
+++ lib/libc/gen/readdir.c
@@ -47,8 +47,9 @@
  * get next entry in a directory.
  */
 struct dirent *
-_readdir_unlocked(dirp)
+_readdir_unlocked(dirp, skip)
 	DIR *dirp;
+	int skip;
 {
 	struct dirent *dp;
 
@@ -71,7 +72,7 @@
 		    dp->d_reclen > dirp->dd_len + 1 - dirp->dd_loc)
 			return (NULL);
 		dirp->dd_loc += dp->d_reclen;
-		if (dp->d_ino == 0)
+		if (dp->d_ino == 0 && skip)
 			continue;
 		if (dp->d_type == DT_WHT && (dirp->dd_flags & DTF_HIDEW))
 			continue;
@@ -87,11 +88,11 @@
 
 	if (__isthreaded) {
 		_pthread_mutex_lock((pthread_mutex_t *)&dirp->dd_lock);
-		dp = _readdir_unlocked(dirp);
+		dp = _readdir_unlocked(dirp, 1);
 		_pthread_mutex_unlock((pthread_mutex_t *)&dirp->dd_lock);
 	}
 	else
-		dp = _readdir_unlocked(dirp);
+		dp = _readdir_unlocked(dirp, 1);
 	return (dp);
 }
 
@@ -108,11 +109,11 @@
 	errno = 0;
 	if (__isthreaded) {
 		_pthread_mutex_lock((pthread_mutex_t *)&dirp->dd_lock);
-		if ((dp = _readdir_unlocked(dirp)) != NULL)
+		if ((dp = _readdir_unlocked(dirp, 1)) != NULL)
 			memcpy(entry, dp, _GENERIC_DIRSIZ(dp));
 		_pthread_mutex_unlock((pthread_mutex_t *)&dirp->dd_lock);
 	}
-	else if ((dp = _readdir_unlocked(dirp)) != NULL)
+	else if ((dp = _readdir_unlocked(dirp, 1)) != NULL)
 		memcpy(entry, dp, _GENERIC_DIRSIZ(dp));
 
 	if (errno != 0) {
Index: telldir.c
===================================================================
RCS file: /home/cvs/src/lib/libc/gen/telldir.c,v
retrieving revision 1.1.1.1
retrieving revision 1.2
diff -L lib/libc/gen/telldir.c -L lib/libc/gen/telldir.c -u -r1.1.1.1 -r1.2
--- lib/libc/gen/telldir.c
+++ lib/libc/gen/telldir.c
@@ -10,10 +10,6 @@
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. All advertising materials mentioning features or use of this software
- *    must display the following acknowledgement:
- *	This product includes software developed by the University of
- *	California, Berkeley and its contributors.
  * 4. Neither the name of the University nor the names of its contributors
  *    may be used to endorse or promote products derived from this software
  *    without specific prior written permission.
@@ -102,7 +98,7 @@
 	dirp->dd_seek = lp->loc_seek;
 	dirp->dd_loc = 0;
 	while (dirp->dd_loc < lp->loc_loc) {
-		dp = _readdir_unlocked(dirp);
+		dp = _readdir_unlocked(dirp, 0);
 		if (dp == NULL)
 			break;
 	}


More information about the Midnightbsd-cvs mailing list