Uppercase hex output of small char arrays is moderately frequently used. Add a mechanism to support the %*ph output as uppercase using 'X'. Signed-off-by: Joe Perches <joe@xxxxxxxxxxx> --- Documentation/core-api/printk-formats.rst | 7 ++++- lib/vsprintf.c | 48 ++++++++++++++++++++----------- 2 files changed, 37 insertions(+), 18 deletions(-) diff --git a/Documentation/core-api/printk-formats.rst b/Documentation/core-api/printk-formats.rst index e08bbe9b0cbf3..01944b0c8adf3 100644 --- a/Documentation/core-api/printk-formats.rst +++ b/Documentation/core-api/printk-formats.rst @@ -285,12 +285,17 @@ Raw buffer as a hex string :: %*ph 00 01 02 ... 3f + %*phX 00 01 02 ... 3F %*phC 00:01:02: ... :3f + %*phCX 00:01:02: ... :3F %*phD 00-01-02- ... -3f + %*phDX 00-01-02- ... -3F %*phN 000102 ... 3f + %*phNX 000102 ... 3F For printing small buffers (up to 64 bytes long) as a hex string with a -certain separator. For larger buffers consider using +certain separator. Typical output is lowercase, formats with X are uppercase. +For larger buffers consider using :c:func:`print_hex_dump`. MAC/FDDI addresses diff --git a/lib/vsprintf.c b/lib/vsprintf.c index 134216c45980e..6aca95d5a99f0 100644 --- a/lib/vsprintf.c +++ b/lib/vsprintf.c @@ -1147,7 +1147,10 @@ char *hex_string(char *buf, char *end, u8 *addr, struct printf_spec spec, { int i, len = 1; /* if we pass '%ph[CDN]', field width remains negative value, fallback to the default */ - char separator; + char separator = ' '; + int count = 1; + bool found = true; + bool ucase = false; if (spec.field_width == 0) /* nothing to print */ @@ -1156,30 +1159,41 @@ char *hex_string(char *buf, char *end, u8 *addr, struct printf_spec spec, if (check_pointer(&buf, end, addr, spec)) return buf; - switch (fmt[1]) { - case 'C': - separator = ':'; - break; - case 'D': - separator = '-'; - break; - case 'N': - separator = 0; - break; - default: - separator = ' '; - break; - } + do { + switch (fmt[count++]) { + case 'C': + separator = ':'; + break; + case 'D': + separator = '-'; + break; + case 'N': + separator = 0; + break; + case 'X': + ucase = true; + break; + default: + found = false; + break; + } + } while (found); if (spec.field_width > 0) len = min_t(int, spec.field_width, 64); for (i = 0; i < len; ++i) { - if (buf < end) + if (buf < end) { *buf = hex_asc_hi(addr[i]); + if (ucase) + *buf = toupper(*buf); + } ++buf; - if (buf < end) + if (buf < end) { *buf = hex_asc_lo(addr[i]); + if (ucase) + *buf = toupper(*buf); + } ++buf; if (separator && i != len - 1) {