1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
|
/* echo.c - echo supporting -n and -e.
*
* Copyright 2007 Rob Landley <rob@landley.net>
*
* See http://opengroup.org/onlinepubs/9699919799/utilities/echo.html
*
* Deviations from posix: we parse command line options, as Linux has
* consistently done since 1992. Posix defaults -e to on, we require -e.
* We also honor -- to _stop_ option parsing (bash doesn't, we go with
* consistency over compatibility here).
USE_ECHO(NEWTOY(echo, "^?Een[-eE]", TOYFLAG_BIN|TOYFLAG_MAYFORK))
config ECHO
bool "echo"
default y
help
usage: echo [-neE] [ARG...]
Write each argument to stdout, with one space between each, followed
by a newline.
-n No trailing newline
-E Print escape sequences literally (default)
-e Process the following escape sequences:
\\ Backslash
\0NNN Octal values (1 to 3 digits)
\a Alert (beep/flash)
\b Backspace
\c Stop output here (avoids trailing newline)
\f Form feed
\n Newline
\r Carriage return
\t Horizontal tab
\v Vertical tab
\xHH Hexadecimal values (1 to 2 digits)
*/
#define FOR_echo
#include "toys.h"
void echo_main(void)
{
int i = 0, out;
char *arg, *c;
for (;;) {
arg = toys.optargs[i];
if (!arg) break;
if (i++) putchar(' ');
// Should we output arg verbatim?
if (!FLAG(e)) {
xprintf("%s", arg);
continue;
}
// Handle -e
for (c = arg;;) {
if (!(out = *(c++))) break;
// handle \escapes
if (out == '\\' && *c) {
int slash = *(c++), n = unescape(slash);
if (n) out = n;
else if (slash=='c') return;
else if (slash=='0') {
out = 0;
while (*c>='0' && *c<='7' && n++<3) out = (out*8)+*(c++)-'0';
} else if (slash=='x') {
out = 0;
while (n++<2) {
if (*c>='0' && *c<='9') out = (out*16)+*(c++)-'0';
else {
int temp = tolower(*c);
if (temp>='a' && temp<='f') {
out = (out*16)+temp-'a'+10;
c++;
} else {
if (n==1) {
--c;
out = '\\';
}
break;
}
}
}
// Slash in front of unknown character, print literal.
} else c--;
}
putchar(out);
}
}
// Output "\n" if no -n
if (!FLAG(n)) putchar('\n');
}
|