From: Eugene Syromyatnikov Date: Mon, 10 Oct 2016 16:55:54 +0000 (+0300) Subject: util: add support for QUOTE_0_TERMINATED in user_style to ptrintstr_ex X-Git-Tag: v4.15~150 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=fdd97aac538f70c0425cd4380f46996f9cb7d2cf;p=strace util: add support for QUOTE_0_TERMINATED in user_style to ptrintstr_ex This enables printing size-limited (expectedly) ASCIZ strings. This is done by increasing umoven size limit for sized strings by one byte above max_strlen (enabling copying possible NUL byte in case len is greater than max_strlen) and decreasing size after copying by one byte in case QUOTE_0_TERMINATED is set (due to user_style or usage of len of -1). As a result, there is one excess byte for string_quote in case QUOTE_0_TERMINATED is set so string_quote can check for NUL termination of strings up to size bytes in size (which is len or max_strlen, whatever is greater). The catch here is that when string is not properly NUL-terminated and QUOTE_0_TERMINATED is provided in user_style and len is less than max_strlen then last non-NUL byte is not printed. But ellipsis is printed instead, being indication that string is not terminated properly. QUOTE_OMIT_TRAILING_0 should be used instead in case this behaviour is not intended. * util.c (printstr_ex): Copy one excess byte in case of non-negative len provided and it is more than max_strlen; handle case of max_strlen of 0 in case QUOTE_0_TERMINATED is set separately; check for need of printing ellipsis by checking resulting style against QUOTE_0_TERMINATED. --- diff --git a/util.c b/util.c index 05c0e15c..f895f227 100644 --- a/util.c +++ b/util.c @@ -838,13 +838,13 @@ printstr_ex(struct tcb *tcp, long addr, long len, unsigned int user_style) outstr = xmalloc(outstr_size); } - size = max_strlen; + size = max_strlen + 1; if (len == -1) { /* * Treat as a NUL-terminated string: fetch one byte more * because string_quote may look one byte ahead. */ - if (umovestr(tcp, addr, size + 1, str) < 0) { + if (umovestr(tcp, addr, size, str) < 0) { printaddr(addr); return; } @@ -862,11 +862,23 @@ printstr_ex(struct tcb *tcp, long addr, long len, unsigned int user_style) style |= user_style; + if (style & QUOTE_0_TERMINATED) { + if (size) { + --size; + } else { + tprints((len == -1) || (len == 0) ? "\"\"" : "\"\"..."); + return; + } + } + if (size > max_strlen) + size = max_strlen; + /* If string_quote didn't see NUL and (it was supposed to be ASCIZ str * or we were requested to print more than -s NUM chars)... */ ellipsis = (string_quote(str, outstr, size, style) && - (len < 0 || (unsigned long) len > max_strlen)); + ((style & QUOTE_0_TERMINATED) || + (unsigned long) len > max_strlen)); tprints(outstr); if (ellipsis)