diff options
Diffstat (limited to '')
-rw-r--r-- | src/commands/tail.c | 80 |
1 files changed, 80 insertions, 0 deletions
diff --git a/src/commands/tail.c b/src/commands/tail.c new file mode 100644 index 0000000..04f7f42 --- /dev/null +++ b/src/commands/tail.c @@ -0,0 +1,80 @@ +#include "../command.h" + +#include <stdio.h> +#include <string.h> +#include <sys/stat.h> + +static void tail_file(FILE* file) { + char* ring[10]; + memset(ring, 0, sizeof(char*) * 10); + + int ring_len[10]; + + int index = 0; + int size = 0; + + int read; + size_t len = 0; + char* line = NULL; + while ((read = getline(&line, &len, file)) != -1) { + + if (ring[index] != NULL) free(ring[index]); + ring[index] = line; + ring_len[index] = read; + + index++; + index %= 10; + if (size < 10) size++; + + line = NULL; + } + + index += 10 - size; + index %= 10; + + for (int i = 0; i < size; i++) { + fwrite(ring[index], ring_len[index], 1, stdout); + free(ring[index]); + index += 1; + index %= 10; + } + + free(line); + fclose(file); +} + +static void help() { + printf("Usage: tail [FILE]...\n\n"); + printf("Print last 10 lines of FILEs (or stdin) to.\n"); + printf("With more than one FILE, precede each with a filename header.\n"); + exit(EXIT_SUCCESS); +} + +COMMAND(tail) { + if (argc < 1) { + tail_file(stdin); + return EXIT_SUCCESS; + } + + if (streql(argv[0], "--help")) help(); + + if (argc == 1) { + FILE* file = get_file(argv[0], "r"); + tail_file(file); + return EXIT_SUCCESS; + } + + for (int i = 0; i < argc; i++) { + FILE* file; + if (streql("-", argv[i])) { + file = stdin; + } else { + file = get_file_s(argv[i], "r"); + if (file == NULL) continue; + } + printf("\n==> %s <==\n", argv[i]); + tail_file(file); + } + + return EXIT_SUCCESS; +} |