#include #include #include #include #include #include #include int main(int argc, char *argv[]) { struct stat file_stat; struct passwd *file_pd; int argc_decr; mode_t *ft; extern int errno; argc_decr = argc; /* K&R 117(ยง5.10) warns against decrementing argc directly */ if(argc <= 1 || argc >= 5) { printf("USAGE: %s [-o, -c]\n", argv[0]); return 1; } else if(stat(argv[1], &file_stat)) { if(errno == ENOENT) printf("provided file does not exist.\n"); else if(errno == EACCES) printf("improper permissions to read from file.\n"); else if(errno == ENAMETOOLONG) printf("provided path is too long.\n"); else if(errno == ENOTDIR) printf("provided path contains a non-existant directory.\n"); else if(errno == EOVERFLOW) printf("provided file cannot be properly contained into a stat buf.\n"); else if(errno == ELOOP) printf("provided file points to an irresolvable symlink chain.\n"); return errno; } printf("file size in bytes: %llu\n", file_stat.st_size); while(argc_decr > 2) { if(!strncmp(argv[argc_decr - 1], "-o", 5)) { if((file_pd = getpwuid(file_stat.st_uid)) != NULL) printf("file owned by user %s.\n", file_pd->pw_name); else printf("file owned by uid %d.\n", file_stat.st_uid); } else if(!strncmp(argv[argc_decr - 1], "-t", 5)) { printf("file is a "); ft = &(file_stat.st_mode); if (S_ISBLK(*ft)) printf("block device.\n"); else if(S_ISCHR(*ft)) printf("character device.\n"); else if(S_ISFIFO(*ft)) printf("fifo pipe.\n"); else if(S_ISREG(*ft)) printf("regular file.\n"); else if(S_ISDIR(*ft)) printf("directory.\n"); else if(S_ISLNK(*ft)) printf("symbolic link.\n"); } else { printf("provided argument is invalid, must be '-t' or '-o'.\n"); return 1; } argc_decr--; } return 0; }