Skip to content

fix: avoid stack overflow on table separator lines with many columns - #11

Open
uonoko1 wants to merge 1 commit into
masterfrom
fix/table-separator-stackoverflow
Open

uonoko1 wants to merge 1 commit into
masterfrom
fix/table-separator-stackoverflow

Conversation

@uonoko1

@uonoko1 uonoko1 commented Nov 13, 2026

Copy link
Copy Markdown
Collaborator

課題

https://nulab.backlog.jp/view/CASHEW_NUTS-1163

Why

テーブルのヘッダー区切り行(|:-|:-|...)を判定する正規表現が、列数の多い行で StackOverflowError を起こす。列の繰り返しが (?:COL\|)+COL という形で、java.util.regex は貪欲なグループの繰り返しを 1 回ごとに再帰して照合するため、列数に比例してスタックを消費する。1 MB のスタックでは、区切りが :- の行は 500 列で落ちる。

2026-11-12 に backlog-web の本番 Pod がこの形のスタックトレース(java.util.regex.Pattern$... の 13 フレーム周期)を残して終了した。

What

TableParagraphPreProcessor.getTableHeaderSeparator の正規表現を、再帰しない形に書き換えた。

  • 列の繰り返しを独占的量指定子(possessive)にした: (?:COL\|)+COL → COL(?:\|COL)++。独占的な繰り返しは再帰せずループで照合される
  • 列の選択肢を長い順(:-: → :- → -: → -)に並べ替えた。独占的にするとバックトラックしなくなるので、並べ替えないと右寄せ・中央寄せを判定できなくなる

確認したこと

  • 追加した TableSeparatorStackOverflowTest(512 KB のスタックで 5000 列のテーブルを parse して render、寄せ指定 4 種と混在)は、修正前に 5 件中 4 件が StackOverflowError で失敗し、修正後はすべて通る
  • flexmark-ext-tables のテスト 1130 件がすべて通る(mvn -pl flexmark-ext-tables -am test -Dtest='com.vladsch.flexmark.ext.tables.**')
  • | - : 空白 a からなる長さ 10 までの全文字列(約 1,220 万通り)で、修正前後の正規表現の matches() の結果が一致する(minColumnDashes 1〜4、IntelliJ ダミー識別子なし)

リポジトリ全体の mvn test はローカルでは流していない。

🤖 Generated with Claude Code

The header separator pattern repeated a column group greedily
("(?:COL\|)+COL"). java.util.regex matches a greedy group repetition
recursively, so the stack depth grew with the number of columns and a
separator line with several hundred columns threw StackOverflowError.

Repeat the column group possessively so it is matched in a loop, and
order the column alternatives longest first so that alignment markers
are still recognised without backtracking.

Co-Authored-By: Claude Fable 5.2 <[email protected]>

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🟢 Approval recommended

No active review issues are recorded for the table-separator parsing change.

No open issues 🎉

What changed in this PR

This PR prevents stack overflows when the tables extension parses header separator lines with many columns.

Changes:

  • Replaces recursive regex repetition with possessive repetition to avoid stack growth per column.
  • Reorders column alternatives to preserve alignment recognition.
  • Adds small-stack regression tests for 5,000-column tables and a separate mixed-alignment case.
File Description
flexmark-ext-tables/​src/​test/​java/​com/​vladsch/​flexmark/​ext/​tables/​TableSeparatorStackOverflowTest.java Tests wide-table parsing and rendering, plus alignment preservation.
flexmark-ext-tables/​src/​main/​java/​com/​vladsch/​flexmark/​ext/​tables/​internal/​TableParagraphPreProcessor.java Updates the separator regex to avoid recursive column matching and documents the approach.

Review effort: Balanced

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.

3 participants