dft: ScanStitch::Stitch dereferences std::deque::end() on chains of 3+ cells
Maintainers usually reply within 1 day
@mmporong is already working on this.
Since Oct 26, 2026.
Assessment
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Newbie friendliness
- 75/100
- Issue type
- Bug
- Clarity
- Clearly specified
- Activity status
- Active
- Tech stack
- cpp
- Domain
- testing-qa
Research direction
Start in src/dft/src/stitch/ScanStitch.cpp at ScanStitch::Stitch and trace how the deque is formed and how the first and last cells are connected. The issue gives src/dft/test/scan_architect_no_mix_sky130.tcl as a reproducer; run it with a hardened standard library or ASan to expose the invalid access. Done when chains of three or more cells connect in order without dereferencing past the deque, while preserving the stated connection order.
Written by the indexing model from the issue text.
Description
ScanStitch::Stitch(block, scan_chain, ordinal) in src/dft/src/stitch/ScanStitch.cpp dereferences std::deque::end() when a chain has 3 or more cells, which is undefined behaviour.
The chain's cells are copied into a std::deque, the first and last are popped off, and the middle cells are walked with:
for (auto it = scan_cells.begin(); it != scan_cells.end(); ++it) {
const std::unique_ptr<ScanCell>& current = *it;
const std::unique_ptr<ScanCell>& next = *(it + 1);
next->connectScanIn(current->getScanOut());
}
On the last middle cell, it + 1 == scan_cells.end(), so next is read from past the end.
Why the regressions pass anyway: with libc++, the slot just past the end still holds the element that pop_back() removed, which is the last cell of the chain. So the read returns the last cell, and the last cell's scan-in ends up connected to the last middle cell's scan-out. Nothing else connects the last cell when there are 3+ cells; the explicit "connect the last cell" branch only runs when the middle is empty. The correct result therefore depends on the stale slot.
Reproducer: any execute_dft_plan that builds a chain of 3 or more cells, e.g. src/dft/test/scan_architect_no_mix_sky130.tcl. A hardened standard library (libc++ hardened mode, _GLIBCXX_ASSERTIONS) or ASan should flag the dereference. A different standard library, or a deque layout where that slot is no longer the popped element, could connect the wrong cell or crash.
Suggested fix: connect the cells pairwise in chain order instead of popping both ends, e.g. after connecting the first cell's scan-in, for i in 1..n: cells[i]->connectScanIn(cells[i-1]->getScanOut()), then the last cell's scan-out as today. The connections, and the order they are made in, stay what the current binary produces.
Seen at 27288f5c90 and still present on master (3c92de5213).
- Dominant language
- Verilog
- Stars
- 3.2k
- Forks
- 1.1k
- Avg merge
- 2d 9h
- Merged PRs (30d)
- 270
Getting set up
- Ships a Dockerfile or Docker Compose file
- Has a pull request template
- Read the contributing guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
More from The-OpenROAD-Project/OpenROAD
-
odb: Bazel build fails on linux/aarch64 — char fc compared to EOF in def/lef lexersPossibly taken A pull request linked to this issue is open or already merged. Openbazel bug odb
Difficulty 1/5 Under an hour Newbie friendliness 80/100
The-OpenROAD-Project/OpenROAD#12095 · 1 comment ·
Maintainers usually reply within 1 day
-
OpenRCX: extMeasure::calcRes0 segfaults on a null getRes() result when a rules file has sparse per-layer tablesPossibly taken @AcKoucher claimed this 1 day ago. Openbug rcx
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
The-OpenROAD-Project/OpenROAD#12052 · 2 comments · 1 assignee ·
Maintainers usually reply within 1 day
-
syn: acd_resynth -apply segfaults on a database resynthesized in an earlier processPossibly taken @zzf2024 claimed this 2 days ago. Openbug syn
Difficulty 2/5 1-3 hours Newbie friendliness 77/100
The-OpenROAD-Project/OpenROAD#12046 · 2 comments ·
Maintainers usually reply within 1 day
-
check_placement: padding check flags a legal cell above a fixed block whose bottom is in the upper half of a rowPossibly taken @gudeh claimed this 1 day ago. Openbug dpl
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
The-OpenROAD-Project/OpenROAD#12038 · 1 comment · 1 assignee ·
Maintainers usually reply within 1 day
-
[cts] -useful_skew: add a test to document and enforce the intent at block boundariesPossibly taken @precisionmoon claimed this 3 days ago. Opencts documentation question rsz
The-OpenROAD-Project/OpenROAD#12088 · 2 comments · 1 assignee ·
Maintainers usually reply within 1 day
All issues in The-OpenROAD-Project/OpenROAD
Similar issues
-
area:agent-manager community needs-triage
Difficulty 2/5 1-3 hours Newbie friendliness 76/100
Maintainers usually reply within 1 day
-
bug
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
jejjohnson/gaussx#721 ·
Maintainers usually reply within 1 day
-
Android cucumber config still points to the v1.0.8 demo appPossibly taken @RaphaelFakhri claimed this today. Open
Difficulty 1/5 Under an hour Newbie friendliness 85/100
webdriverio/appium-boilerplate#613 ·
Maintainers usually reply within 4 days
-
[MNT] Tests with a strict `<` between two dates can fail on WindowsPossibly taken @codeuxius claimed this today. Open
Difficulty 2/5 1-3 hours Newbie friendliness 76/100
aiondemand/AIOD-rest-api#759 ·
-
missing `catch.hpp`Open
Difficulty 2/5 1-3 hours Newbie friendliness 68/100
microsoft/inflatelib#34 · 1 comment ·