X-Git-Url: http://erislabs.net/gitweb/?a=blobdiff_plain;f=lib%2Ffts.c;h=8666cff871ce1e185b4e5eeaad8e1a48b178f3cf;hb=f84215faa43d2933011459dd42ba518df63e34c4;hp=d3bef85f3823fbdbd80880566928c560f7f74475;hpb=359c0a71713e606f440d40f55a43c77349df2aaa;p=gnulib.git diff --git a/lib/fts.c b/lib/fts.c index d3bef85f3..8666cff87 100644 --- a/lib/fts.c +++ b/lib/fts.c @@ -1,6 +1,6 @@ /* Traverse a file hierarchy. - Copyright (C) 2004, 2005 Free Software Foundation, Inc. + Copyright (C) 2004, 2005, 2006 Free Software Foundation, Inc. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -71,6 +71,10 @@ static char sccsid[] = "@(#)fts.c 8.6 (Berkeley) 8/14/94"; #include #include +#if ! _LIBC +# include "lstat.h" +#endif + #if defined _LIBC # include # define NAMLEN(dirent) _D_EXACT_NAMLEN (dirent) @@ -111,15 +115,6 @@ static char sccsid[] = "@(#)fts.c 8.6 (Berkeley) 8/14/94"; # define internal_function /* empty */ #endif -/* Arrange to make lstat calls go through the wrapper function - on systems with an lstat function that does not dereference symlinks - that are specified with a trailing slash. */ -#if ! _LIBC && ! LSTAT_FOLLOWS_SLASHED_SYMLINK -int rpl_lstat (const char *, struct stat *); -# undef lstat -# define lstat(Name, Stat_buf) rpl_lstat(Name, Stat_buf) -#endif - #ifndef __set_errno # define __set_errno(Val) errno = (Val) #endif @@ -152,10 +147,9 @@ static bool enter_dir (FTS *fts, FTSENT *ent) { return true; } static void leave_dir (FTS *fts, FTSENT *ent) {} static bool setup_dir (FTS *fts) { return true; } static void free_dir (FTS *fts) {} -static int fd_safer (int fd) { return fd; } #else +# include "fcntl--.h" # include "fts-cycle.c" -# include "unistd-safer.h" #endif #ifndef MAX @@ -209,10 +203,7 @@ static int internal_function diropen (char const *dir) { - int fd = open (dir, O_RDONLY | O_DIRECTORY); - if (fd < 0) - fd = open (dir, O_WRONLY | O_DIRECTORY); - return fd; + return open (dir, O_RDONLY | O_DIRECTORY | O_NOCTTY | O_NONBLOCK); } FTS * @@ -250,8 +241,11 @@ fts_open (char * const *argv, #ifndef MAXPATHLEN # define MAXPATHLEN 1024 #endif - if (! fts_palloc(sp, MAX(fts_maxarglen(argv), MAXPATHLEN))) - goto mem1; + { + size_t maxarglen = fts_maxarglen(argv); + if (! fts_palloc(sp, MAX(maxarglen, MAXPATHLEN))) + goto mem1; + } /* Allocate/initialize root's parent. */ if ((parent = fts_alloc(sp, "", 0)) == NULL) @@ -530,6 +524,7 @@ next: tmp = p; if (p->fts_level == FTS_ROOTLEVEL) { if (FCHDIR(sp, sp->fts_rfd)) { SET(FTS_STOP); + sp->fts_cur = p; return (NULL); } fts_load(sp, p); @@ -700,7 +695,9 @@ fts_children (register FTS *sp, int instr) return (sp->fts_child = NULL); sp->fts_child = fts_build(sp, instr); if (fchdir(fd)) { + int saved_errno = errno; (void)close(fd); + __set_errno (saved_errno); return (NULL); } (void)close(fd); @@ -1029,7 +1026,7 @@ fts_cross_check (FTS const *sp) struct Active_dir ad; ad.ino = t->fts_statp->st_ino; ad.dev = t->fts_statp->st_dev; - if ( ! hash_lookup (sp->active_dir_ht, &ad)) + if ( ! hash_lookup (sp->fts_cycle.ht, &ad)) printf ("ERROR: active dir, %s, not in tree\n", t->fts_path); } @@ -1040,8 +1037,8 @@ fts_cross_check (FTS const *sp) || ent->fts_info == FTS_D)) { struct Active_dir *ad; - for (ad = hash_get_first (sp->active_dir_ht); ad != NULL; - ad = hash_get_next (sp->active_dir_ht, ad)) + for (ad = hash_get_first (sp->fts_cycle.ht); ad != NULL; + ad = hash_get_next (sp->fts_cycle.ht, ad)) { find_matching_ancestor (ent, ad); } @@ -1073,7 +1070,8 @@ fts_stat(FTS *sp, register FTSENT *p, bool follow) if (ISSET(FTS_LOGICAL) || follow) { if (stat(p->fts_accpath, sbp)) { saved_errno = errno; - if (!lstat(p->fts_accpath, sbp)) { + if (errno == ENOENT + && lstat(p->fts_accpath, sbp) == 0) { __set_errno (0); return (FTS_SLNONE); } @@ -1319,7 +1317,7 @@ fts_safe_changedir (FTS *sp, FTSENT *p, int fd, char const *dir) newfd = fd; if (ISSET(FTS_NOCHDIR)) return (0); - if (fd < 0 && (newfd = fd_safer (diropen (dir))) < 0) + if (fd < 0 && (newfd = diropen (dir)) < 0) return (-1); if (fstat(newfd, &sb)) { ret = -1;