1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23#include "libbb.h"
24#include "unicode.h"
25
26#undef CHAR_T
27#if ENABLE_UNICODE_SUPPORT
28# define CHAR_T wchar_t
29#else
30# define CHAR_T char
31#endif
32
33
34static void strrev(CHAR_T *s, int len)
35{
36 int i;
37
38 if (len != 0) {
39 len--;
40 if (len != 0 && s[len] == '\n')
41 len--;
42 }
43
44 for (i = 0; i < len; i++, len--) {
45 CHAR_T c = s[i];
46 s[i] = s[len];
47 s[len] = c;
48 }
49}
50
51int rev_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
52int rev_main(int argc UNUSED_PARAM, char **argv)
53{
54 int retval;
55 size_t bufsize;
56 char *buf;
57
58 init_unicode();
59
60 getopt32(argv, "");
61 argv += optind;
62 if (!argv[0])
63 argv = (char **)&bb_argv_dash;
64
65 retval = EXIT_SUCCESS;
66 bufsize = 256;
67 buf = xmalloc(bufsize);
68 do {
69 size_t pos;
70 FILE *fp;
71
72 fp = fopen_or_warn_stdin(*argv++);
73 if (!fp) {
74 retval = EXIT_FAILURE;
75 continue;
76 }
77
78 pos = 0;
79 while (1) {
80
81 buf[bufsize - 1] = 1;
82 if (!fgets(buf + pos, bufsize - pos, fp))
83 break;
84 if (buf[bufsize - 1] == '\0'
85 && buf[bufsize - 2] != '\n'
86 && !feof(fp)
87 ) {
88
89 pos = bufsize - 1;
90 bufsize += 64 + bufsize / 8;
91 buf = xrealloc(buf, bufsize);
92 continue;
93 }
94
95
96#if ENABLE_UNICODE_SUPPORT
97 {
98 wchar_t *tmp = xmalloc(bufsize * sizeof(wchar_t));
99
100 int len = mbstowcs(tmp, buf, bufsize);
101 if (len >= 0) {
102 strrev(tmp, len);
103
104 wcstombs(buf, tmp, bufsize);
105 }
106 free(tmp);
107 }
108#else
109 strrev(buf, strlen(buf));
110#endif
111 fputs_stdout(buf);
112 pos = 0;
113 }
114 fclose(fp);
115 } while (*argv);
116
117 if (ENABLE_FEATURE_CLEAN_UP)
118 free(buf);
119
120 fflush_stdout_and_exit(retval);
121}
122