rev.c (1158B)
1 /* See LICENSE file for copyright and license details. */ 2 #include <stdio.h> 3 #include <string.h> 4 #include <unistd.h> 5 6 #include "text.h" 7 #include "util.h" 8 9 static void 10 usage(void) 11 { 12 eprintf("usage: %s [file ...]\n", argv0); 13 } 14 15 static void 16 rev(FILE *fp) 17 { 18 static char *line = NULL; 19 static size_t size = 0; 20 size_t i; 21 ssize_t n; 22 int lf; 23 24 while ((n = getline(&line, &size, fp)) > 0) { 25 lf = n && line[n - 1] == '\n'; 26 i = n -= lf; 27 for (n = 0; i--;) { 28 if ((line[i] & 0xC0) == 0x80) { 29 n++; 30 } else { 31 fwrite(line + i, 1, n + 1, stdout); 32 n = 0; 33 } 34 } 35 if (n) 36 fwrite(line, 1, n, stdout); 37 if (lf) 38 fputc('\n', stdout); 39 } 40 } 41 42 int 43 main(int argc, char *argv[]) 44 { 45 FILE *fp; 46 int ret = 0; 47 48 ARGBEGIN { 49 default: 50 usage(); 51 } ARGEND 52 53 if (!argc) { 54 rev(stdin); 55 } else { 56 for (; *argv; argc--, argv++) { 57 if (!strcmp(*argv, "-")) { 58 *argv = "<stdin>"; 59 fp = stdin; 60 } else if (!(fp = fopen(*argv, "r"))) { 61 weprintf("fopen %s:", *argv); 62 ret = 1; 63 continue; 64 } 65 rev(fp); 66 if (fp != stdin && fshut(fp, *argv)) 67 ret = 1; 68 } 69 } 70 71 ret |= fshut(stdin, "<stdin>") | fshut(stdout, "<stdout>"); 72 73 return ret; 74 }