用C语言实现linux下的ls -l命令。与文件相关的结构体、函数等等知识请看"stat结构体以及文件相关函数"
#include
#include
#include
#include
#include
#include
#include
#include
void do_ls(char *dirname);
void dostat(char *filename);
void show_file_info(char *filename, struct stat *info_p);
void mode_to_letters(int mode, char * str);
char *uid_to_name(uid_t uid);
char *gid_to_name(gid_t gid);
int main(int argc, char **argv)
{
if (argc == 1)
{
do_ls( "." );
}
else
{
while ( --argc )
{
printf("%s:\n", *++argv );
chdir(*argv); //切换到指定目录后再显示该目录的内容
do_ls( *argv );
chdir(""); //再回到当前工作目录来
}
}
return 0;
}
void do_ls( char * dirname )
{
DIR *dir_ptr;
struct dirent *direntp;
if ( ( dir_ptr = opendir( dirname ) ) == NULL )
{
fprintf(stderr,"ls1: cannot open %s, not a directory. treat as a file shown below:\n", dirname);
dostat( dirname ); //如果不是目录就当作文件来显示其属性
}
else
{
while ( ( direntp = readdir( dir_ptr ) ) != NULL )
{
dostat( direntp->d_name );
}
closedir(dir_ptr);
}
}
void dostat( char *filename )
{
struct stat info;
if ( stat(filename, &info) == -1 )
{
perror( filename );
}
else
{
show_file_info( filename, &info );
}
}
void show_file_info(char *filename, struct stat *info_p)
{
char modestr[11];
mode_to_letters(info_p->st_mode, modestr);
printf("%s" , modestr);
//st_nlink连接该文件的硬链接数,刚建立的文件值为1
printf("%4d " , (int) info_p->st_nlink);
printf("%-8s " , uid_to_name(info_p->st_uid));
printf("%-8s " , gid_to_name(info_p->st_gid));
printf("%8ld " , (long)info_p->st_size);
printf("%.12s ", 4+ctime(&info_p->st_mtime));
printf("%s\n" , filename);
}
void mode_to_letters(int mode, char * str)
{
strcpy(str, "----------");
if (S_ISDIR(mode))
str[0] = 'd';
if (S_ISCHR(mode))
str[0] = 'c';
if (S_ISBLK(mode))
str[0] = 'b';
if (mode & S_IRUSR)
str[1] = 'r';
if (mode & S_IWUSR)
str[2] = 'w';
if (mode & S_IXUSR)
str[3] = 'x';
if (mode & S_IRGRP)
str[4] = 'r';
if (mode & S_IWGRP)
str[5] = 'w';
if (mode & S_IXGRP)
str[6] = 'x';
if (mode & S_IROTH)
str[7] = 'r';
if (mode & S_IWOTH)
str[8] = 'w';
if (mode & S_IXOTH)
str[9] = 'x';
}
char *uid_to_name(uid_t uid)
{
struct passwd *pw_ptr;
static char numstr[10];
//获取用户ID
if ((pw_ptr = getpwuid(uid)) == NULL)
{
sprintf(numstr,"%d", uid);
return numstr;
}
else
{
return pw_ptr->pw_name ;
}
}
char *gid_to_name( gid_t gid )
{
struct group *grp_ptr;
static char numstr[10];
//获取组ID
if ((grp_ptr = getgrgid(gid)) == NULL)
{
sprintf(numstr,"%d", gid);
return numstr;
}
else
{
return grp_ptr->gr_name;
}
}