aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDenys Vlasenko <vda.linux@googlemail.com>2010-10-24 01:58:04 +0200
committerDenys Vlasenko <vda.linux@googlemail.com>2010-10-24 01:58:04 +0200
commit2b299fed6a77d3aaf7e4e768fb519f2536c2eff0 (patch)
tree1d86a176ddfbc1f853842629b758c0ab4e8ada9a
parent53600591311a129717abd2e3bcaa302622a6ce67 (diff)
downloadbusybox-w32-2b299fed6a77d3aaf7e4e768fb519f2536c2eff0.tar.gz
busybox-w32-2b299fed6a77d3aaf7e4e768fb519f2536c2eff0.tar.bz2
busybox-w32-2b299fed6a77d3aaf7e4e768fb519f2536c2eff0.zip
awk: fix breakage in last commit
While at it, made bb_process_escape_sequence faster (same size) function old new delta nextchar 49 53 +4 bb_process_escape_sequence 138 140 +2 next_token 838 839 +1 static.charmap 20 18 -2 is_assignment 143 135 -8 ------------------------------------------------------------------------------ (add/remove: 0/0 grow/shrink: 3/2 up/down: 7/-10) Total: -3 bytes Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
-rw-r--r--editors/awk.c27
-rw-r--r--libbb/process_escape_sequence.c46
2 files changed, 38 insertions, 35 deletions
diff --git a/editors/awk.c b/editors/awk.c
index fb3bf6b47..9646cedd6 100644
--- a/editors/awk.c
+++ b/editors/awk.c
@@ -684,8 +684,11 @@ static char nextchar(char **s)
684 pps = *s; 684 pps = *s;
685 if (c == '\\') 685 if (c == '\\')
686 c = bb_process_escape_sequence((const char**)s); 686 c = bb_process_escape_sequence((const char**)s);
687 if (c == '\\' && *s == pps) 687 if (c == '\\' && *s == pps) { /* unrecognized \z? */
688 c = *(*s)++; 688 c = *(*s); /* yes, fetch z */
689 if (c)
690 (*s)++; /* advance unless z = NUL */
691 }
689 return c; 692 return c;
690} 693}
691 694
@@ -1007,9 +1010,10 @@ static uint32_t next_token(uint32_t expected)
1007 /* it's a string */ 1010 /* it's a string */
1008 t_string = s = ++p; 1011 t_string = s = ++p;
1009 while (*p != '\"') { 1012 while (*p != '\"') {
1010 char *pp = p; 1013 char *pp;
1011 if (*p == '\0' || *p == '\n') 1014 if (*p == '\0' || *p == '\n')
1012 syntax_error(EMSG_UNEXP_EOS); 1015 syntax_error(EMSG_UNEXP_EOS);
1016 pp = p;
1013 *s++ = nextchar(&pp); 1017 *s++ = nextchar(&pp);
1014 p = pp; 1018 p = pp;
1015 } 1019 }
@@ -2926,22 +2930,21 @@ static int awk_exit(int r)
2926 * otherwise return 0 */ 2930 * otherwise return 0 */
2927static int is_assignment(const char *expr) 2931static int is_assignment(const char *expr)
2928{ 2932{
2929 char *exprc, *s, *s0, *s1; 2933 char *exprc, *val, *s, *s1;
2930 2934
2931 if (!isalnum_(*expr) || (s0 = strchr(expr, '=')) == NULL) { 2935 if (!isalnum_(*expr) || (val = strchr(expr, '=')) == NULL) {
2932 return FALSE; 2936 return FALSE;
2933 } 2937 }
2934 2938
2935 exprc = xstrdup(expr); 2939 exprc = xstrdup(expr);
2936 s0 = exprc + (s0 - expr); 2940 val = exprc + (val - expr);
2937 *s++ = '\0'; 2941 *val++ = '\0';
2938 2942
2939 s = s1 = s0; 2943 s = s1 = val;
2940 while (*s) 2944 while ((*s1 = nextchar(&s)) != '\0')
2941 *s1++ = nextchar(&s); 2945 s1++;
2942 *s1 = '\0';
2943 2946
2944 setvar_u(newvar(exprc), s0); 2947 setvar_u(newvar(exprc), val);
2945 free(exprc); 2948 free(exprc);
2946 return TRUE; 2949 return TRUE;
2947} 2950}
diff --git a/libbb/process_escape_sequence.c b/libbb/process_escape_sequence.c
index dd6e076b0..7b1d97f9c 100644
--- a/libbb/process_escape_sequence.c
+++ b/libbb/process_escape_sequence.c
@@ -18,18 +18,8 @@
18 18
19char FAST_FUNC bb_process_escape_sequence(const char **ptr) 19char FAST_FUNC bb_process_escape_sequence(const char **ptr)
20{ 20{
21 /* bash builtin "echo -e '\ec'" interprets \e as ESC,
22 * but coreutils "/bin/echo -e '\ec'" does not.
23 * manpages tend to support coreutils way.
24 * Update: coreutils added support for \e on 28 Oct 2009. */
25 static const char charmap[] ALIGN1 = {
26 'a', 'b', 'e', 'f', 'n', 'r', 't', 'v', '\\', 0,
27 '\a', '\b', 27, '\f', '\n', '\r', '\t', '\v', '\\', '\\' };
28
29 const char *p;
30 const char *q; 21 const char *q;
31 unsigned num_digits; 22 unsigned num_digits;
32 unsigned r;
33 unsigned n; 23 unsigned n;
34 unsigned base; 24 unsigned base;
35 25
@@ -37,18 +27,17 @@ char FAST_FUNC bb_process_escape_sequence(const char **ptr)
37 base = 8; 27 base = 8;
38 q = *ptr; 28 q = *ptr;
39 29
40#if WANT_HEX_ESCAPES 30 if (WANT_HEX_ESCAPES && *q == 'x') {
41 if (*q == 'x') {
42 ++q; 31 ++q;
43 base = 16; 32 base = 16;
44 ++num_digits; 33 ++num_digits;
45 } 34 }
46#endif
47 35
48 /* bash requires leading 0 in octal escapes: 36 /* bash requires leading 0 in octal escapes:
49 * \02 works, \2 does not (prints \ and 2). 37 * \02 works, \2 does not (prints \ and 2).
50 * We treat \2 as a valid octal escape sequence. */ 38 * We treat \2 as a valid octal escape sequence. */
51 do { 39 do {
40 unsigned r;
52#if !WANT_HEX_ESCAPES 41#if !WANT_HEX_ESCAPES
53 unsigned d = (unsigned char)(*q) - '0'; 42 unsigned d = (unsigned char)(*q) - '0';
54#else 43#else
@@ -60,8 +49,9 @@ char FAST_FUNC bb_process_escape_sequence(const char **ptr)
60 if (WANT_HEX_ESCAPES && base == 16) { 49 if (WANT_HEX_ESCAPES && base == 16) {
61 --num_digits; 50 --num_digits;
62 if (num_digits == 0) { 51 if (num_digits == 0) {
63 /* \x<bad_char> */ 52 /* \x<bad_char>: return '\',
64 --q; /* go back to x */ 53 * leave ptr pointing to x */
54 return '\\';
65 } 55 }
66 } 56 }
67 break; 57 break;
@@ -76,20 +66,30 @@ char FAST_FUNC bb_process_escape_sequence(const char **ptr)
76 ++q; 66 ++q;
77 } while (++num_digits < 3); 67 } while (++num_digits < 3);
78 68
79 if (num_digits == 0) { /* mnemonic escape sequence? */ 69 if (num_digits == 0) {
80 p = charmap; 70 /* Not octal or hex escape sequence.
71 * Is it one-letter one? */
72
73 /* bash builtin "echo -e '\ec'" interprets \e as ESC,
74 * but coreutils "/bin/echo -e '\ec'" does not.
75 * Manpages tend to support coreutils way.
76 * Update: coreutils added support for \e on 28 Oct 2009. */
77 static const char charmap[] ALIGN1 = {
78 'a', 'b', 'e', 'f', 'n', 'r', 't', 'v', '\\',
79 '\a', '\b', 27, '\f', '\n', '\r', '\t', '\v', '\\',
80 };
81 const char *p = charmap;
81 do { 82 do {
82 if (*p == *q) { 83 if (*p == *q) {
83 q++; 84 q++;
84 break; 85 break;
85 } 86 }
86 } while (*++p); 87 } while (*++p != '\\');
87 /* p points to found escape char or NUL, 88 /* p points to found escape char or '\',
88 * advance it and find what it translates to. 89 * advance it and find what it translates to.
89 * Note that unrecognized sequence \z returns '\' 90 * Note that \NUL and unrecognized sequence \z return '\'
90 * and leaves ptr pointing to z. */ 91 * and leave ptr pointing to NUL or z. */
91 p += sizeof(charmap) / 2; 92 n = p[sizeof(charmap) / 2];
92 n = *p;
93 } 93 }
94 94
95 *ptr = q; 95 *ptr = q;