|
Lines 61-67
Link Here
|
| 61 |
static int fts_palloc __P((FTS *, size_t)); |
61 |
static int fts_palloc __P((FTS *, size_t)); |
| 62 |
static FTSENT *fts_sort __P((FTS *, FTSENT *, int)); |
62 |
static FTSENT *fts_sort __P((FTS *, FTSENT *, int)); |
| 63 |
static u_short fts_stat __P((FTS *, FTSENT *, int)); |
63 |
static u_short fts_stat __P((FTS *, FTSENT *, int)); |
| 64 |
static int fts_safe_changedir __P((FTS *, FTSENT *, int)); |
64 |
static int fts_safe_changedir __P((FTS *, FTSENT *, int, char *)); |
| 65 |
|
65 |
|
| 66 |
#define ISDOT(a) (a[0] == '.' && (!a[1] || (a[1] == '.' && !a[2]))) |
66 |
#define ISDOT(a) (a[0] == '.' && (!a[1] || (a[1] == '.' && !a[2]))) |
| 67 |
|
67 |
|
|
Lines 69-75
Link Here
|
| 69 |
#define ISSET(opt) (sp->fts_options & (opt)) |
69 |
#define ISSET(opt) (sp->fts_options & (opt)) |
| 70 |
#define SET(opt) (sp->fts_options |= (opt)) |
70 |
#define SET(opt) (sp->fts_options |= (opt)) |
| 71 |
|
71 |
|
| 72 |
#define CHDIR(sp, path) (!ISSET(FTS_NOCHDIR) && chdir(path)) |
|
|
| 73 |
#define FCHDIR(sp, fd) (!ISSET(FTS_NOCHDIR) && fchdir(fd)) |
72 |
#define FCHDIR(sp, fd) (!ISSET(FTS_NOCHDIR) && fchdir(fd)) |
| 74 |
|
73 |
|
| 75 |
/* fts_build flags */ |
74 |
/* fts_build flags */ |
|
Lines 273-278
Link Here
|
| 273 |
fts_read(sp) |
272 |
fts_read(sp) |
| 274 |
register FTS *sp; |
273 |
register FTS *sp; |
| 275 |
{ |
274 |
{ |
|
|
275 |
struct stat sb; |
| 276 |
register FTSENT *p, *tmp; |
276 |
register FTSENT *p, *tmp; |
| 277 |
register int instr; |
277 |
register int instr; |
| 278 |
register char *t; |
278 |
register char *t; |
|
Lines 349-355
Link Here
|
| 349 |
* FTS_STOP or the fts_info field of the node. |
349 |
* FTS_STOP or the fts_info field of the node. |
| 350 |
*/ |
350 |
*/ |
| 351 |
if (sp->fts_child) { |
351 |
if (sp->fts_child) { |
| 352 |
if (fts_safe_changedir(sp, p, -1)) { |
352 |
if (fts_safe_changedir(sp, p, -1, p->fts_accpath)) { |
| 353 |
p->fts_errno = errno; |
353 |
p->fts_errno = errno; |
| 354 |
p->fts_flags |= FTS_DONTCHDIR; |
354 |
p->fts_flags |= FTS_DONTCHDIR; |
| 355 |
for (p = sp->fts_child; p; p = p->fts_link) |
355 |
for (p = sp->fts_child; p; p = p->fts_link) |
|
Lines 446-456
Link Here
|
| 446 |
return (NULL); |
446 |
return (NULL); |
| 447 |
} |
447 |
} |
| 448 |
(void)close(p->fts_symfd); |
448 |
(void)close(p->fts_symfd); |
| 449 |
} else if (!(p->fts_flags & FTS_DONTCHDIR)) { |
449 |
} else if (!(p->fts_flags & FTS_DONTCHDIR) && |
| 450 |
if (CHDIR(sp, "..")) { |
450 |
fts_safe_changedir(sp, p->fts_parent, -1, "..")) { |
| 451 |
SET(FTS_STOP); |
451 |
SET(FTS_STOP); |
| 452 |
return (NULL); |
452 |
return (NULL); |
| 453 |
} |
|
|
| 454 |
} |
453 |
} |
| 455 |
p->fts_info = p->fts_errno ? FTS_ERR : FTS_DP; |
454 |
p->fts_info = p->fts_errno ? FTS_ERR : FTS_DP; |
| 456 |
return (sp->fts_cur = p); |
455 |
return (sp->fts_cur = p); |
|
Lines 637-643
Link Here
|
| 637 |
*/ |
636 |
*/ |
| 638 |
cderrno = 0; |
637 |
cderrno = 0; |
| 639 |
if (nlinks || type == BREAD) { |
638 |
if (nlinks || type == BREAD) { |
| 640 |
if (fts_safe_changedir(sp, cur, dirfd(dirp))) { |
639 |
if (fts_safe_changedir(sp, cur, dirfd(dirp), NULL)) { |
| 641 |
if (nlinks && type == BREAD) |
640 |
if (nlinks && type == BREAD) |
| 642 |
cur->fts_errno = errno; |
641 |
cur->fts_errno = errno; |
| 643 |
cur->fts_flags |= FTS_DONTCHDIR; |
642 |
cur->fts_flags |= FTS_DONTCHDIR; |
|
Lines 803-809
Link Here
|
| 803 |
*/ |
802 |
*/ |
| 804 |
if (descend && (type == BCHILD || !nitems) && |
803 |
if (descend && (type == BCHILD || !nitems) && |
| 805 |
(cur->fts_level == FTS_ROOTLEVEL ? |
804 |
(cur->fts_level == FTS_ROOTLEVEL ? |
| 806 |
FCHDIR(sp, sp->fts_rfd) : CHDIR(sp, ".."))) { |
805 |
FCHDIR(sp, sp->fts_rfd) : |
|
|
806 |
fts_safe_changedir(sp, cur->fts_parent, -1, ".."))) { |
| 807 |
cur->fts_info = FTS_ERR; |
807 |
cur->fts_info = FTS_ERR; |
| 808 |
SET(FTS_STOP); |
808 |
SET(FTS_STOP); |
| 809 |
return (NULL); |
809 |
return (NULL); |
|
Lines 1075-1084
Link Here
|
| 1075 |
* Assumes p->fts_dev and p->fts_ino are filled in. |
1075 |
* Assumes p->fts_dev and p->fts_ino are filled in. |
| 1076 |
*/ |
1076 |
*/ |
| 1077 |
static int |
1077 |
static int |
| 1078 |
fts_safe_changedir(sp, p, fd) |
1078 |
fts_safe_changedir(sp, p, fd, path) |
| 1079 |
FTS *sp; |
1079 |
FTS *sp; |
| 1080 |
FTSENT *p; |
1080 |
FTSENT *p; |
| 1081 |
int fd; |
1081 |
int fd; |
|
|
1082 |
char *path; |
| 1082 |
{ |
1083 |
{ |
| 1083 |
int ret, oerrno, newfd; |
1084 |
int ret, oerrno, newfd; |
| 1084 |
struct stat sb; |
1085 |
struct stat sb; |
|
Lines 1086-1092
Link Here
|
| 1086 |
newfd = fd; |
1087 |
newfd = fd; |
| 1087 |
if (ISSET(FTS_NOCHDIR)) |
1088 |
if (ISSET(FTS_NOCHDIR)) |
| 1088 |
return (0); |
1089 |
return (0); |
| 1089 |
if (fd < 0 && (newfd = open(p->fts_accpath, O_RDONLY, 0)) < 0) |
1090 |
if (fd < 0 && (newfd = _open(path, O_RDONLY, 0)) < 0) |
| 1090 |
return (-1); |
1091 |
return (-1); |
| 1091 |
if (fstat(newfd, &sb)) { |
1092 |
if (fstat(newfd, &sb)) { |
| 1092 |
ret = -1; |
1093 |
ret = -1; |