#include #include #include #include #include #include #include #include #define CAT_USAGE "Usage: cat [-u] [file...]\n" #define STDIN_ARG "-" #define BUFFER_SIZE 20480 static void close_file(int fd) { if (fd != STDIN_FILENO) { close(fd); } } static bool print_file_content(const char *path) { char buffer[BUFFER_SIZE]; int input = -1; ssize_t ret = -1; if (strcmp(path, STDIN_ARG) == 0) { input = STDIN_FILENO; } else { if ((input = open(path, O_RDONLY)) == -1) { fprintf(stderr,"Can't open file '%s': %s\n", path, strerror(errno)); return false; } } do { ret = read(input, buffer, BUFFER_SIZE); if (ret > 0) { write(STDOUT_FILENO, buffer, ret); } } while (ret > 0); if (ret == -1) { fprintf(stderr, "Failed to read file '%s': %s\n", path, strerror(errno)); } close_file(input); return ret == 0; } int cat_main(int argc, char *argv[]) { int opt = 0; bool ret = false; while ((opt = getopt(argc, argv, "u")) != -1) { if (opt != 'u') { perror(CAT_USAGE); return EXIT_FAILURE; } } for (int i = optind; i < argc; i++) { ret = print_file_content(argv[i]); if (!ret) { break; } } /* If no argument was provided, we use stdin by default */ if (argc - optind == 0) { ret = print_file_content(STDIN_ARG); } return ret ? EXIT_SUCCESS : EXIT_FAILURE; }