/* ls2.c * purpose list contents of directory or directories * action if no args, use . else list files in args * note uses stat and pwd.h and grp.h * BUG: try ls2 /tmp */
voiddo_ls(char dirname[]) /* * list files in directory called dirname */ { DIR *dir_ptr; // the directory structdirent * direntp;// each entry
if ((dir_ptr = opendir(dirname)) == NULL) fprintf(stderr, "ls1: cannot open %s\n", dirname); else { while ((direntp = readdir(dir_ptr)) != NULL) dostat(direntp->d_name); closedir(dir_ptr); } }
voiddostat(char *filename) { structstatinfo; if (stat(filename, &info) == -1) // cannot stat perror(filename); // say why else show_file_info(filename, &info); }
voidshow_file_info(char *filename, struct stat * info_p) /* * display the info about filename. * the info is stored in struct at * info_p */ { char * uid_to_name(), *ctime(), *gid_to_name(), *filemode(); voidmode_to_letters(); char modestr[11];
/* * This function takes a mode value and a char array * and puts into the char array the file type and the * nine letters that correspnd to the bits in mode. * NOTE: It does not code setuid, setgid, and sticky * codes */ voidmode_to_letters(int mode, char str[]) { strcpy(str, "----------"); // default = no perms if (S_ISDIR(mode)) str[0] = 'd'; // directory if (S_ISCHR(mode)) str[0] = 'c'; // char devices if (S_ISBLK(mode)) str[0] = 'l'; // block device
if (mode & S_IRUSR) str[1] = 'r'; // 3 bits for user if (mode & S_IWUSR) str[2] = 'w'; if (mode & S_IXUSR) str[3] = 'x';
if (mode & S_IRGRP) str[4] = 'r'; // 3 bits for group if (mode & S_IWGRP) str[5] = 'w'; if (mode & S_IXGRP) str[6] = 'x';
if (mode & S_IROTH) str[7] = 'r'; // 3 bits for other if (mode & S_IWOTH) str[8] = 'w'; if (mode & S_IXOTH) str[9] = 'x'; }
char * gid_to_name(gid_t gid) /* * returns pointer to group number gid, used getgrid(3) */ { struct group * getgrpid(), *grp_ptr; staticchar numstr[10];