Avoid exhausting stack space in dominator compression

This commit is contained in:
Mark Rousskov 2022-02-23 10:31:26 -05:00
parent c651ba8a54
commit 4d89292785

View File

@ -241,9 +241,19 @@ fn compress(
v: PreorderIndex, v: PreorderIndex,
) { ) {
assert!(is_processed(v, lastlinked)); assert!(is_processed(v, lastlinked));
let u = ancestor[v]; // Compute the processed list of ancestors
if is_processed(u, lastlinked) { //
compress(ancestor, lastlinked, semi, label, u); // We use a heap stack here to avoid recursing too deeply, exhausting the
// stack space.
let mut stack: smallvec::SmallVec<[_; 8]> = smallvec::smallvec![v];
let mut u = ancestor[v];
while is_processed(u, lastlinked) {
stack.push(u);
u = ancestor[u];
}
// Then in reverse order, popping the stack
for &[v, u] in stack.array_windows().rev() {
if semi[label[u]] < semi[label[v]] { if semi[label[u]] < semi[label[v]] {
label[v] = label[u]; label[v] = label[u];
} }