svn commit: r303004 - head/lib/libc/gen
Andrey A. Chernov
ache at FreeBSD.org
Mon Jul 18 16:06:22 UTC 2016
Author: ache
Date: Mon Jul 18 16:06:21 2016
New Revision: 303004
URL: https://svnweb.freebsd.org/changeset/base/303004
Log:
1) POSIX defines well when GLOB_ABORTED can be returned (only for directory
open/read errors and with GLOB_ERR and gl_errfunc processing), so we can't
blindly return it on any MAXPATHLEN overflow. Even our manpage disagrees
with such GLOB_ABORTED usage. Use GLOB_NOSPACE for that now with errno is
set to 0 as for limits.
2) Return GLOB_NOSPACE when valid ~ expansion can't happens due to
MAXPATHLEN overflow too.
3) POSIX (and our manpage) says, if GLOB_ERR is set, GLOB_ABORTED should
be returned immediatelly, without using gl_errfunc. Implement it now.
Modified:
head/lib/libc/gen/glob.c
Modified: head/lib/libc/gen/glob.c
==============================================================================
--- head/lib/libc/gen/glob.c Mon Jul 18 15:50:54 2016 (r303003)
+++ head/lib/libc/gen/glob.c Mon Jul 18 16:06:21 2016 (r303004)
@@ -421,7 +421,7 @@ globtilde(const Char *pattern, Char *pat
continue;
if (*p != EOS && *p != SLASH)
- return (pattern);
+ return (NULL);
*b = EOS;
h = NULL;
@@ -446,8 +446,9 @@ globtilde(const Char *pattern, Char *pat
/*
* Expand a ~user
*/
- if (g_Ctoc(patbuf, (char *)wbuf, sizeof(wbuf)) ||
- (pwd = getpwnam((char *)wbuf)) == NULL)
+ if (g_Ctoc(patbuf, (char *)wbuf, sizeof(wbuf)))
+ return (NULL);
+ if ((pwd = getpwnam((char *)wbuf)) == NULL)
return (pattern);
else
h = pwd->pw_dir;
@@ -474,13 +475,13 @@ globtilde(const Char *pattern, Char *pat
sc += clen;
}
if (too_long)
- return (pattern);
+ return (NULL);
dc = wbuf;
for (b = patbuf; b < eb && *dc != EOS; *b++ = *dc++)
continue;
if (*dc != EOS)
- return (pattern);
+ return (NULL);
/* Append the rest of the pattern */
if (*p != EOS) {
@@ -492,7 +493,7 @@ globtilde(const Char *pattern, Char *pat
}
}
if (too_long)
- return (pattern);
+ return (NULL);
} else
*b = EOS;
@@ -515,6 +516,10 @@ glob0(const Char *pattern, glob_t *pglob
Char *bufnext, c, patbuf[MAXPATHLEN];
qpatnext = globtilde(pattern, patbuf, MAXPATHLEN, pglob);
+ if (qpatnext == NULL) {
+ errno = 0;
+ return (GLOB_NOSPACE);
+ }
oldpathc = pglob->gl_pathc;
bufnext = patbuf;
@@ -638,7 +643,7 @@ glob2(Char *pathbuf, Char *pathend, Char
limit->l_stat_cnt++ >= GLOB_LIMIT_STAT) {
errno = 0;
if (pathend + 1 > pathend_last)
- return (GLOB_ABORTED);
+ return (GLOB_NOSPACE);
*pathend++ = SEP;
*pathend = EOS;
return (GLOB_NOSPACE);
@@ -648,8 +653,10 @@ glob2(Char *pathbuf, Char *pathend, Char
|| (S_ISLNK(sb.st_mode) &&
(g_stat(pathbuf, &sb, pglob) == 0) &&
S_ISDIR(sb.st_mode)))) {
- if (pathend + 1 > pathend_last)
- return (GLOB_ABORTED);
+ if (pathend + 1 > pathend_last) {
+ errno = 0;
+ return (GLOB_NOSPACE);
+ }
*pathend++ = SEP;
*pathend = EOS;
}
@@ -663,8 +670,10 @@ glob2(Char *pathbuf, Char *pathend, Char
while (*p != EOS && *p != SEP) {
if (ismeta(*p))
anymeta = 1;
- if (q + 1 > pathend_last)
- return (GLOB_ABORTED);
+ if (q + 1 > pathend_last) {
+ errno = 0;
+ return (GLOB_NOSPACE);
+ }
*q++ = *p++;
}
@@ -672,8 +681,10 @@ glob2(Char *pathbuf, Char *pathend, Char
pathend = q;
pattern = p;
while (*pattern == SEP) {
- if (pathend + 1 > pathend_last)
- return (GLOB_ABORTED);
+ if (pathend + 1 > pathend_last) {
+ errno = 0;
+ return (GLOB_NOSPACE);
+ }
*pathend++ = *pattern++;
}
} else /* Need expansion, recurse. */
@@ -695,18 +706,21 @@ glob3(Char *pathbuf, Char *pathend, Char
struct dirent *(*readdirfunc)(DIR *);
+ errno = 0;
if (pathend > pathend_last)
- return (GLOB_ABORTED);
+ return (GLOB_NOSPACE);
*pathend = EOS;
- errno = 0;
if ((dirp = g_opendir(pathbuf, pglob)) == NULL) {
/* TODO: don't call for ENOENT or ENOTDIR? */
+ if (pglob->gl_flags & GLOB_ERR)
+ return (GLOB_ABORTED);
if (pglob->gl_errfunc) {
- if (g_Ctoc(pathbuf, buf, sizeof(buf)))
- return (GLOB_ABORTED);
- if (pglob->gl_errfunc(buf, errno) ||
- pglob->gl_flags & GLOB_ERR)
+ if (g_Ctoc(pathbuf, buf, sizeof(buf))) {
+ errno = 0;
+ return (GLOB_NOSPACE);
+ }
+ if (pglob->gl_errfunc(buf, errno))
return (GLOB_ABORTED);
}
return (0);
@@ -732,7 +746,7 @@ glob3(Char *pathbuf, Char *pathend, Char
limit->l_readdir_cnt++ >= GLOB_LIMIT_READDIR) {
errno = 0;
if (pathend + 1 > pathend_last)
- err = GLOB_ABORTED;
+ err = GLOB_NOSPACE;
else {
*pathend++ = SEP;
*pathend = EOS;
@@ -831,6 +845,7 @@ globextend(const Char *path, glob_t *pgl
if ((copy = malloc(len)) != NULL) {
if (g_Ctoc(path, copy, len)) {
free(copy);
+ errno = 0;
return (GLOB_NOSPACE);
}
pathv[pglob->gl_offs + pglob->gl_pathc++] = copy;
More information about the svn-src-all
mailing list