From 07b8121f07056480c54fca99046870d84a657d13 Mon Sep 17 00:00:00 2001 From: Kent Overstreet Date: Sun, 6 Mar 2022 14:04:34 -0500 Subject: [PATCH] bcachefs: Fix pr_tab_rjust() pr_tab_rjust() was broken and leaving a null somewhere in the output string - this patch fixes it and simplifies it a bit. Signed-off-by: Kent Overstreet --- fs/bcachefs/util.c | 37 +++++++++++++++++++++++++++++++++++-- fs/bcachefs/util.h | 22 +++------------------- 2 files changed, 38 insertions(+), 21 deletions(-) diff --git a/fs/bcachefs/util.c b/fs/bcachefs/util.c index 7a896ddc9a22..f290c069c683 100644 --- a/fs/bcachefs/util.c +++ b/fs/bcachefs/util.c @@ -101,8 +101,14 @@ STRTO_H(strtou64, u64) static int bch2_printbuf_realloc(struct printbuf *out, unsigned extra) { - unsigned new_size = roundup_pow_of_two(out->size + extra); - char *buf = krealloc(out->buf, new_size, !out->atomic ? GFP_KERNEL : GFP_ATOMIC); + unsigned new_size; + char *buf; + + if (out->pos + extra + 1 < out->size) + return 0; + + new_size = roundup_pow_of_two(out->size + extra); + buf = krealloc(out->buf, new_size, !out->atomic ? GFP_KERNEL : GFP_ATOMIC); if (!buf) { out->allocation_failure = true; @@ -131,6 +137,33 @@ void bch2_pr_buf(struct printbuf *out, const char *fmt, ...) out->pos += len; } +void bch2_pr_tab_rjust(struct printbuf *buf) +{ + BUG_ON(buf->tabstop > ARRAY_SIZE(buf->tabstops)); + + if (printbuf_linelen(buf) < buf->tabstops[buf->tabstop]) { + unsigned move = buf->pos - buf->last_field; + unsigned shift = buf->tabstops[buf->tabstop] - + printbuf_linelen(buf); + + bch2_printbuf_realloc(buf, shift); + + if (buf->last_field + shift + 1 < buf->size) { + move = min(move, buf->size - 1 - buf->last_field - shift); + + memmove(buf->buf + buf->last_field + shift, + buf->buf + buf->last_field, + move); + memset(buf->buf + buf->last_field, ' ', shift); + buf->pos += shift; + buf->buf[buf->pos] = 0; + } + } + + buf->last_field = buf->pos; + buf->tabstop++; +} + void bch2_hprint(struct printbuf *buf, s64 v) { int u, t = 0; diff --git a/fs/bcachefs/util.h b/fs/bcachefs/util.h index 7667944f9ae4..ba0c4d29c038 100644 --- a/fs/bcachefs/util.h +++ b/fs/bcachefs/util.h @@ -334,27 +334,11 @@ static inline void pr_tab(struct printbuf *buf) buf->tabstop++; } +void bch2_pr_tab_rjust(struct printbuf *); + static inline void pr_tab_rjust(struct printbuf *buf) { - ssize_t shift = min_t(ssize_t, buf->tabstops[buf->tabstop] - - printbuf_linelen(buf), - printbuf_remaining(buf)); - ssize_t move = min_t(ssize_t, buf->pos - buf->last_field, - printbuf_remaining(buf) - shift); - - BUG_ON(buf->tabstop > ARRAY_SIZE(buf->tabstops)); - - if (shift > 0) { - memmove(buf->buf + buf->last_field + shift, - buf->buf + buf->last_field, - move); - memset(buf->buf + buf->last_field, ' ', shift); - buf->pos += shift; - buf->buf[buf->pos] = 0; - } - - buf->last_field = buf->pos; - buf->tabstop++; + bch2_pr_tab_rjust(buf); } void bch2_pr_units(struct printbuf *, s64, s64);