1 /* Copyright (C) 1992, 1995 Free Software Foundation, Inc.
2 This file is part of the GNU C Library.
3 Contributed by Ian Lance Taylor (ian@airs.com).
5 The GNU C Library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Library General Public License as
7 published by the Free Software Foundation; either version 2 of the
8 License, or (at your option) any later version.
10 The GNU C Library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Library General Public License for more details.
15 You should have received a copy of the GNU Library General Public
16 License along with the GNU C Library; see the file COPYING.LIB. If
17 not, write to the Free Software Foundation, Inc., 675 Mass Ave,
18 Cambridge, MA 02139, USA. */
26 #include <sys/types.h>
32 #define PATH_MAX 1024 /* XXX */
36 /* Traverse one level of a directory tree. */
39 DEFUN (ftw_dir
, (dirs
, level
, descriptors
, dir
, len
, func
),
40 DIR **dirs AND
int level AND
int descriptors AND
41 char *dir AND
size_t len AND
42 int EXFUN((*func
), (CONST
char *file
, struct stat
*status
,
52 while ((entry
= readdir (dirs
[level
])) != NULL
)
55 int flag
, retval
, newlev
;
59 if (entry
->d_name
[0] == '.'
60 && (entry
->d_namlen
== 1 ||
61 (entry
->d_namlen
== 2 && entry
->d_name
[1] == '.')))
67 if (entry
->d_namlen
+ len
+ 1 > PATH_MAX
)
78 memcpy ((PTR
) (dir
+ len
+ 1), (PTR
) entry
->d_name
,
81 if (stat (dir
, &s
) < 0)
83 if (errno
!= EACCES
&& errno
!= ENOENT
)
87 else if (S_ISDIR (s
.st_mode
))
89 newlev
= (level
+ 1) % descriptors
;
91 if (dirs
[newlev
] != NULL
)
92 closedir (dirs
[newlev
]);
94 dirs
[newlev
] = opendir (dir
);
95 if (dirs
[newlev
] != NULL
)
107 retval
= (*func
) (dir
, &s
, flag
);
112 retval
= ftw_dir (dirs
, newlev
, descriptors
, dir
,
113 entry
->d_namlen
+ len
+ 1, func
);
114 if (dirs
[newlev
] != NULL
)
119 closedir (dirs
[newlev
]);
128 if (dirs
[level
] == NULL
)
133 dirs
[level
] = opendir (dir
);
134 if (dirs
[level
] == NULL
)
140 if (readdir (dirs
[level
]) == NULL
)
141 return errno
== 0 ? 0 : -1;
148 return errno
== 0 ? 0 : -1;
151 /* Call a function on every element in a directory tree. */
154 DEFUN(ftw
, (dir
, func
, descriptors
),
156 int EXFUN((*func
), (CONST
char *file
, struct stat
*status
,
162 char buf
[PATH_MAX
+ 1];
167 if (descriptors
<= 0)
170 dirs
= (DIR **) __alloca (descriptors
* sizeof (DIR *));
175 if (stat (dir
, &s
) < 0)
177 if (errno
!= EACCES
&& errno
!= ENOENT
)
181 else if (S_ISDIR (s
.st_mode
))
183 dirs
[0] = opendir (dir
);
197 memcpy ((PTR
) buf
, (PTR
) dir
, len
+ 1);
199 retval
= (*func
) (buf
, &s
, flag
);
204 retval
= ftw_dir (dirs
, 0, descriptors
, buf
, len
, func
);