#include <stdio.h>#include <sys/types.h>#include <sys/stat.h>#include <unistd.h>#include <dirent.h>#include <errno.h>#include <stdlib.h>#include <string.h>// 最大目錄深度#define MAX_DIR_DEPTH 64#define __LEN 4#define MAX_FILE_LEN 256#define MAX_LEN ((64 * __LEN) + MAX_FILE_LEN)#define MAX_PATH_LEN (64 * 32)void print_dir(const char * file_name, int depth, char *show_c, struct dirent *pDirRes){ int i; int pos = depth * __LEN; show_c[pos - __LEN+1] = '|'; for(i = 0; i < __LEN-1; i++) show_c[pos - i] = '-'; show_c[pos+1] = '\0'; printf("%s%s\n", show_c, file_name); if(!pDirRes) { show_c[pos-__LEN + 1] = ' '; } for(i = 0; i < __LEN-1; i++) show_c[pos - i] = ' ';}void clear_c(int depth, char *show_c ){ show_c[(depth-1) * __LEN + 1] = ' ';}int is_last_dir(DIR *pDir){ return 0;}int __tree_dir(const char* dirname, int depth, char *show_c){ DIR *pDir; struct stat file_stat; struct dirent diren; struct dirent *pDirRes; char *tmpname; if(depth >= MAX_DIR_DEPTH) return -1; tmpname = malloc(MAX_PATH_LEN); if(!tmpname) return -1; /* open dir */ pDir = opendir(dirname); if(NULL == pDir){ printf("%s %s\n", dirname , strerror(errno)); goto ERR; } do{ if(readdir_r(pDir, &diren, &pDirRes)){ closedir(pDir); printf("%s\n", strerror(errno)); goto ERR; } if(!pDirRes) { clear_c(depth, show_c); break; } if(strcmp(".", diren.d_name) == 0 || strcmp("..", diren.d_name)==0) continue; snprintf(tmpname, MAX_PATH_LEN, "%s/%s", dirname , diren.d_name); bzero(&file_stat, sizeof(file_stat)); if(-1 == stat(tmpname, &file_stat)){ closedir(pDir); printf("%s\n", strerror(errno)); goto ERR; } print_dir(diren.d_name, depth, show_c, pDirRes); if(S_ISDIR(file_stat.st_mode)){// if(is_last_dir(pDir)) clear(depth, show_c); __tree_dir(tmpname, depth+1, show_c); } }while(NULL != pDirRes); closedir(pDir); free(tmpname); return 0;ERR: free(tmpname); return -1;}int tree_dir(const char* path){ char *show_c ; int ret; show_c = malloc(MAX_LEN); if(!show_c) return errno; memset(show_c, ' ', MAX_LEN); ret = __tree_dir(path, 1, show_c); free(show_c); return ret;}#define VERSION "version v1.0 : created by Dremi"int main(int argc, char**argv){ if(argc < 2) return -1; if(strcmp("-v", argv[1]) == 0){ printf("%s\n", VERSION); return 0; } return tree_dir(argv[1]);}
版本2:
int __tree_dir(const char* dirname, int depth, char *show_c){ DIR *pDir; struct stat file_stat; struct dirent diren; struct dirent *pDirRes; char *olddir; if(depth >= MAX_DIR_DEPTH) return -1; olddir= malloc(MAX_FILE_LEN); if(!olddir) return -1; getcwd(olddir, MAX_FILE_LEN); if(chdir(dirname)){free(olddir); printf("%s %s\n", dirname, strerror(errno)); return -1; } /* open dir */ pDir = opendir("./"); if(NULL == pDir){free(olddir); printf("%s %s\n", dirname , strerror(errno)); return -1; } do{ if(readdir_r(pDir, &diren, &pDirRes)){ closedir(pDir);free(olddir); printf("%s\n", strerror(errno)); return -1; } if(!pDirRes) { clear_c(depth, show_c); break; } if(strcmp(".", diren.d_name) == 0 || strcmp("..", diren.d_name)==0) continue; bzero(&file_stat, sizeof(file_stat)); if(-1 == stat(diren.d_name, &file_stat)){ closedir(pDir);free(olddir); printf("%s\n", strerror(errno)); return -1; } print_dir(diren.d_name, depth, show_c, pDirRes); if(S_ISDIR(file_stat.st_mode)){// if(is_last_dir(pDir)) clear(depth, show_c); __tree_dir(diren.d_name, depth+1, show_c); } }while(NULL != pDirRes); closedir(pDir); chdir(olddir); free(olddir); return 0;}
效果如下:
|---main_x64 |---main_x86 |---test_asm | |---a.out | |---asm.c | |---get_reg.c |---test_dll | |---main | |---mk_dll.sh | |---test_dll1.c | |---test_dll1.h | |---test_dll2.c | |---test_dll2.h | |---libtestdll1.so | |---libtestdll2.so | |---main.c |---test_log | |---test_log.c | |---a.out |---test1.c |---test2.c |---com_prog