hexdump: fix numerous bugs in handling of backslashes
Was: t=48\\ t=45\\ t=4c\\ t=4c\\ t=4f\\ t=0a\\ Now: =48=\n =45=\n =4c=\n =4c=\n =4f=\n =0a=\n Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
This commit is contained in:
parent
b6355e2bb5
commit
d3d7f085eb
51
libbb/dump.c
51
libbb/dump.c
@ -157,7 +157,7 @@ static NOINLINE void rewrite(priv_dumper_t *dumper, FS *fs)
|
|||||||
/*
|
/*
|
||||||
* figure out the byte count for each conversion;
|
* figure out the byte count for each conversion;
|
||||||
* rewrite the format as necessary, set up blank-
|
* rewrite the format as necessary, set up blank-
|
||||||
* pbb_dump_adding for end of data.
|
* padding for end of data.
|
||||||
*/
|
*/
|
||||||
if (*p1 == 'c') {
|
if (*p1 == 'c') {
|
||||||
pr->flags = F_CHAR;
|
pr->flags = F_CHAR;
|
||||||
@ -466,14 +466,14 @@ static void bpad(PR *pr)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static const char conv_str[] ALIGN1 =
|
static const char conv_str[] ALIGN1 =
|
||||||
"\0\\0\0"
|
"\0" "\\""0""\0"
|
||||||
"\007\\a\0" /* \a */
|
"\007""\\""a""\0" /* \a */
|
||||||
"\b\\b\0"
|
"\b" "\\""b""\0"
|
||||||
"\f\\b\0"
|
"\f" "\\""f""\0"
|
||||||
"\n\\n\0"
|
"\n" "\\""n""\0"
|
||||||
"\r\\r\0"
|
"\r" "\\""r""\0"
|
||||||
"\t\\t\0"
|
"\t" "\\""t""\0"
|
||||||
"\v\\v\0"
|
"\v" "\\""v""\0"
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|
||||||
@ -485,7 +485,7 @@ static void conv_c(PR *pr, unsigned char *p)
|
|||||||
do {
|
do {
|
||||||
if (*p == *str) {
|
if (*p == *str) {
|
||||||
++str;
|
++str;
|
||||||
goto strpr;
|
goto strpr; /* map e.g. '\n' to "\\n" */
|
||||||
}
|
}
|
||||||
str += 4;
|
str += 4;
|
||||||
} while (*str);
|
} while (*str);
|
||||||
@ -702,8 +702,6 @@ int FAST_FUNC bb_dump_dump(dumper_t *pub_dumper, char **argv)
|
|||||||
void FAST_FUNC bb_dump_add(dumper_t* pub_dumper, const char *fmt)
|
void FAST_FUNC bb_dump_add(dumper_t* pub_dumper, const char *fmt)
|
||||||
{
|
{
|
||||||
const char *p;
|
const char *p;
|
||||||
char *p1;
|
|
||||||
char *p2;
|
|
||||||
FS *tfs;
|
FS *tfs;
|
||||||
FU *tfu, **nextfupp;
|
FU *tfu, **nextfupp;
|
||||||
const char *savep;
|
const char *savep;
|
||||||
@ -779,29 +777,42 @@ void FAST_FUNC bb_dump_add(dumper_t* pub_dumper, const char *fmt)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
tfu->fmt = xstrndup(savep, p - savep);
|
tfu->fmt = xstrndup(savep, p - savep);
|
||||||
/* escape(tfu->fmt); */
|
|
||||||
|
|
||||||
p1 = tfu->fmt;
|
|
||||||
|
|
||||||
/* alphabetic escape sequences have to be done in place */
|
/* alphabetic escape sequences have to be done in place */
|
||||||
|
strcpy_and_process_escape_sequences(tfu->fmt, tfu->fmt);
|
||||||
|
/* unknown mappings are not changed: "\z" -> '\\' 'z' */
|
||||||
|
/* trailing backslash, if any, is preserved */
|
||||||
|
#if 0
|
||||||
|
char *p1;
|
||||||
|
char *p2;
|
||||||
|
p1 = tfu->fmt;
|
||||||
for (p2 = p1;; ++p1, ++p2) {
|
for (p2 = p1;; ++p1, ++p2) {
|
||||||
if (*p1 == '\0') {
|
*p2 = *p1;
|
||||||
*p2 = *p1;
|
if (*p1 == '\0')
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
if (*p1 == '\\') {
|
if (*p1 == '\\') {
|
||||||
const char *cs = conv_str + 4;
|
const char *cs;
|
||||||
++p1;
|
|
||||||
|
p1++;
|
||||||
*p2 = *p1;
|
*p2 = *p1;
|
||||||
|
if (*p1 == '\0') {
|
||||||
|
/* "...\" trailing backslash. Eaten. */
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
cs = conv_str + 4; /* skip NUL element */
|
||||||
do {
|
do {
|
||||||
|
/* map e.g. "\n" -> '\n' */
|
||||||
if (*p1 == cs[2]) {
|
if (*p1 == cs[2]) {
|
||||||
*p2 = cs[0];
|
*p2 = cs[0];
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
cs += 4;
|
cs += 4;
|
||||||
} while (*cs);
|
} while (*cs);
|
||||||
|
/* unknown mappings remove bkslash: "\z" -> 'z' */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
p++;
|
p++;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user