summaryrefslogtreecommitdiffstats
path: root/mdk-stage1/dietlibc/lib/ftw.c
diff options
context:
space:
mode:
Diffstat (limited to 'mdk-stage1/dietlibc/lib/ftw.c')
-rw-r--r--mdk-stage1/dietlibc/lib/ftw.c77
1 files changed, 36 insertions, 41 deletions
diff --git a/mdk-stage1/dietlibc/lib/ftw.c b/mdk-stage1/dietlibc/lib/ftw.c
index a3c04af9a..af13a7f86 100644
--- a/mdk-stage1/dietlibc/lib/ftw.c
+++ b/mdk-stage1/dietlibc/lib/ftw.c
@@ -1,52 +1,47 @@
-#include <linux/stat.h>
+#include <sys/stat.h>
#include <unistd.h>
#include <limits.h>
#include <ftw.h>
#include <dirent.h>
#include <string.h>
#include <stdlib.h>
+#include "dietdirent.h"
-int ftw(const char *dir,int (*fn)(const char *file, const struct stat *sb, int flag), int depth) {
- char *cwd;
- int cwdlen;
- DIR *d;
- struct dirent *de;
+int ftw(const char*dir,int(*f)(const char*file,const struct stat*sb,int flag),int dpth){
+ char* cd;
+ size_t cdl;
+ DIR* d;
+ struct dirent* de;
struct stat sb;
- if (chdir(dir)) return -1;
- cwd=alloca(PATH_MAX+1);
- if (!getcwd(cwd,PATH_MAX)) return -1;
- cwd[PATH_MAX]=0;
- cwdlen=strlen(cwd);
-/* write(1,"ftw in ",7); puts(cwd); */
- if (!(d=opendir("."))) return -1;
- while ((de=readdir(d))) {
- int res;
- int flag;
- int nlen;
- char *filename;
- if (de->d_name[0]=='.' &&
- (de->d_name[1]==0 ||
- (de->d_name[1]=='.' && de->d_name[2]==0))) continue;
- nlen=strlen(de->d_name);
- filename=alloca(nlen+cwdlen+3);
- memmove(filename,cwd,cwdlen);
- filename[cwdlen]='/';
- memmove(filename+cwdlen+1,de->d_name,nlen+1);
- if (!lstat(de->d_name,&sb)) {
- if (S_ISLNK(sb.st_mode)) flag=FTW_SL; else
- if (S_ISDIR(sb.st_mode)) flag=FTW_D; else
- flag=FTW_F;
- } else
- flag=FTW_NS;
- res=fn(filename,&sb,flag);
- if (res) return res;
- if (flag==FTW_D && depth>0) {
- res=ftw(filename,fn,depth-1);
- chdir(dir);
- if (res) return res;
+ int r;
+ unsigned int oldlen=0;
+ char* filename; /* the warning gcc issues here is bogus */
+ if(chdir(dir))return-1;
+ cd=alloca(PATH_MAX+1);
+ if(!getcwd(cd,PATH_MAX))return-1;
+ cd[PATH_MAX]='\0';
+ cdl=strlen(cd);
+ if(!(d=opendir(".")))return-1;
+ while((de=readdir(d))){
+ int flg;
+ size_t nl;
+ if(de->d_name[0]=='.'){if(!de->d_name[1])continue;if(de->d_name[1]=='.'&&!de->d_name[2])continue;}
+ nl=strlen(de->d_name);
+ if (nl+cdl+2>oldlen)
+ filename=alloca(oldlen=nl+cdl+2);
+ memmove(filename,cd,cdl);
+ filename[cdl]='/';
+ memmove(filename+cdl+1,de->d_name,nl+1);
+ if(!lstat(de->d_name,&sb)){
+ if(S_ISLNK(sb.st_mode))flg=FTW_SL;else if(S_ISDIR(sb.st_mode))flg=FTW_D;else flg=FTW_F;
+ }else flg=FTW_NS;
+ r=f(filename,&sb,flg);
+ if(r){closedir(d);return r;}
+ if(flg==FTW_D&&dpth){
+ r=ftw(filename,f,dpth-1);
+ fchdir(d->fd);
+ if (r){closedir(d);return r;}
}
-/* puts(de->d_name); */
}
- closedir(d);
- return 0;
+ return closedir(d);
}