From 32d1e45d3df061e6ccba6db7fdce92db29e345d8 Mon Sep 17 00:00:00 2001 From: Sebastian Thiel Date: Mon, 23 Mar 2026 10:59:42 +0800 Subject: [PATCH] Bound common-line pruning to the local window Fix should_prune_common_line() so the backward scan starts at pos.saturating_sub(WINDOW_SIZE) instead of the absolute WINDOW_SIZE index. The old bound made the scanned range grow with pos, which turned the preprocessing heuristic into an increasingly expensive rescan on highly repetitive inputs and caused the gix-merge clusterfuzz testcase to time out. Add a regression test that proves distant context outside the local window does not affect the pruning decision. Co-authored-by: GPT 5.4 --- src/myers/preprocess.rs | 22 +++++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-) diff --git a/src/myers/preprocess.rs b/src/myers/preprocess.rs index b1ca778..2ef5deb 100644 --- a/src/myers/preprocess.rs +++ b/src/myers/preprocess.rs @@ -137,7 +137,7 @@ fn should_prune_common_line(token_status: &[Occurrences], pos: usize) -> bool { let mut unmatched_before = 0; let mut common_before = 0; - let start = if pos > WINDOW_SIZE { WINDOW_SIZE } else { 0 }; + let start = pos.saturating_sub(WINDOW_SIZE); for status in token_status[start..pos].iter().rev() { match status { Occurrences::None => { @@ -178,3 +178,23 @@ fn should_prune_common_line(token_status: &[Occurrences], pos: usize) -> bool { unmatched > 3 * common } + +#[cfg(test)] +mod tests { + use super::{should_prune_common_line, Occurrences}; + + #[test] + fn common_line_pruning_ignores_distant_context() { + let mut token_status = vec![Occurrences::Some; 700]; + token_status[100..400].fill(Occurrences::None); + token_status[400..450].fill(Occurrences::None); + token_status[450..500].fill(Occurrences::Common); + token_status[500..550].fill(Occurrences::Common); + token_status[550..600].fill(Occurrences::None); + + assert!( + !should_prune_common_line(&token_status, 500), + "only the last 100 items before the current line should contribute to the backward scan" + ); + } +}