Skip to content

Fix capacity overflow panic wrapping a wide char at narrow terminal width - #3886

Open
vjymisal0 wants to merge 1 commit into
sharkdp:masterfrom
vjymisal0:fix/wide-char-wrap-capacity-overflow
Open

Fix capacity overflow panic wrapping a wide char at narrow terminal width#3886
vjymisal0 wants to merge 1 commit into
sharkdp:masterfrom
vjymisal0:fix/wide-char-wrap-capacity-overflow

Conversation

@vjymisal0

Copy link
Copy Markdown

Bug

bat --terminal-width 1 --wrap character aborts with capacity overflow (exit 101) when a line contains a character wider than the terminal (a double-width CJK char or emoji) and a background is painted on the line (--highlight-line, or a theme/style that fills the row background). Reported in #3844.

Root cause

In InteractivePrinter::print_line (src/printer.rs), the character-wrapping branch accumulates cursor by each chunk's display width. When a single character is wider than the remaining max_width, it still gets pushed onto line_buf and its full width added to cursor at flush time — so cursor can end up greater than cursor_max (the terminal width). The end-of-line background fill then computes:

ansi_style.paint(" ".repeat(cursor_max - cursor))

cursor_max - cursor underflows (usize), producing a repeat count near usize::MAX, which aborts inside str::repeat.

This is the same defect class as the --style=snip width-1 panic fixed in #3804 — that fix clamps a different overflow site in the same function; this one is the last remaining unclamped subtraction of the same shape.

Fix

Clamp with saturating_sub, matching the pattern already used a few lines above (line ~789) for the no-wrap branch:

ansi_style.paint(" ".repeat(cursor_max.saturating_sub(cursor)))

When the cursor has overshot the terminal width, the background fill is now empty instead of underflowing — matching the "clamp to empty" behavior bat already uses elsewhere for this exact class of bug.

Testing

Reproduced the panic on current master before the fix:

$ printf '\U0001F4E6\U0001F4E6\n' | bat --highlight-line 1 --terminal-width 1 --wrap character --color always --paging never --theme OneHalfDark
thread 'main' panicked at src/printer.rs:961:49:
attempt to subtract with overflow

After the fix, the same command exits 0 with no panic.

Added a regression test, wide_char_wrap_at_terminal_width_one_with_highlight_does_not_panic, covering this exact case. Ran the full integration suite (cargo test --test integration_tests): 230 passed, 0 failed. Also ran cargo clippy --lib with no new warnings.

Added a changelog entry under Bugfixes per CONTRIBUTING.md.

Closes #3844

…idth

InteractivePrinter::print_line's wrapping branch advances `cursor` by a
chunk's full display width even when that chunk (a double-width CJK
character or emoji) is wider than `cursor_max` (the terminal width).
When a background is painted on the line (e.g. via --highlight-line),
the end-of-line fill computed `" ".repeat(cursor_max - cursor)`, which
underflows when cursor > cursor_max, aborting with "capacity overflow".

Reproduced on current master:

  printf '\U0001F4E6\U0001F4E6\n' | bat --highlight-line 1 \
    --terminal-width 1 --wrap character --color always \
    --paging never --theme OneHalfDark
  # thread 'main' panicked at src/printer.rs:961:49:
  # attempt to subtract with overflow

Fix clamps the fill width with saturating_sub, matching the pattern
already used a few lines above (line 789-793) for the no-wrap branch
and the earlier width-1 snip fix (sharkdp#3804). When cursor exceeds
cursor_max, the background fill is now empty instead of underflowing.

Added a regression test (wide_char_wrap_at_terminal_width_one_with_highlight_does_not_panic)
covering the exact repro. Full integration suite (230 tests) and
clippy pass locally.

Closes sharkdp#3844
Copilot AI lite review requested due to automatic review settings August 10, 2026 15:35

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

bat panics (capacity overflow) on --terminal-width 1 wrapping a double-width char with a background

2 participants