PS:模拟实现Ubuntu下的ls -l指令

#include "head.h" // 个人封装的头文件
 
char* Get_Perm(int mode,char* arr) {
	switch (mode & S_IFMT){
		case S_IFSOCK:*arr = 's';break;
		case S_IFLNK: *arr = 'l';break;
		case S_IFREG: *arr = '-';break;
		case S_IFBLK: *arr = 'b';break;
		case S_IFDIR: *arr = 'd';break;
		case S_IFCHR: *arr = 'c';break;
		case S_IFIFO: *arr = 'p';break;
	}
	char per[3] = "rwx";
    for (int i = 0; i < 9; i++) {
        int a = 1 << (8-i);
        if (mode & a) {
            *(arr+i+1) = per[i%3];
			//putchar(per[i%3]);
        } 
		else{
			*(arr+i+1) = '-';
            //putchar('-');
		}
    }
}
 
int main(int argc, const char *argv[])
{
	char path[N];
	char str[N];
	printf("Please input path:");
	//scanf("%s",path);
	gets(path);
	//DIR* dir = opendir("/home/ubuntu/test/");
	DIR* dir = opendir(path); // 打开目录
	if(NULL == dir)
		ERR_MSG("dir");
	printf("opendir success\n");
 
	struct dirent* read = NULL;
	while(1){
		read= readdir(dir);
		if(NULL == read){
			if(0 == errno){
				printf("readdir success\n");
				break;
			}
			else
				ERR_MSG("readdir"); // 错误码输出,封装在头文件中,实际调perror
		}
		if(read->d_name[0] != '.'){
			//puts(read->d_name);	
			//char str[N] = "/home/ubuntu/test/";
			strcpy(str,path);
			strcat(str,read->d_name);
			struct stat buf;
			if(stat(str,&buf) < 0)
				ERR_MSG("stat");
			//printf("stat success\n");
			char a[11];
			Get_Perm(buf.st_mode,a);
			//puts(a);
			printf("%s",a);
			printf(" %ld",buf.st_nlink);
			struct passwd* pwd = getpwuid(buf.st_uid);
			if(NULL == pwd)
				ERR_MSG("getpwuid");
			//puts(pwd->pw_name);
			printf(" %s",pwd->pw_name);
			struct group* gr = getgrgid(buf.st_gid);
			if(NULL == gr)
				ERR_MSG("getgrgid");
			//puts(gr->gr_name);
			printf(" %s",gr->gr_name);
			printf(" %6ld",buf.st_size);
			//printf(" %ld",buf.st_mtime);
			struct tm* cur_time;
			cur_time = localtime(&buf.st_mtime);
			printf(" %d-%02d-%02d %02d:%02d:%02d",\
				cur_time->tm_year+1900,cur_time->tm_mon+1,\
				cur_time->tm_mday,cur_time->tm_hour,\
				cur_time->tm_min,cur_time->tm_sec);
			printf(" %s\n",read->d_name);
		}
	}
 
	closedir(dir);
	return 0;
}

运行效果(gcc + ./):

当然目标目录也可以使用外部参数方式传入,例如:./a.out /home/ubuntu/test/

通过IO文件操作实现读取目录属性_ubuntu

实际命令(ls -l 目录):

通过IO文件操作实现读取目录属性_ubuntu_02