The attached patch changes the DbgValMap to have set semantics, which fixes the excessive memory allocation followed by a crash reported in PR20893. (http://llvm.org/bugs/show_bug.cgi?id=20893)
When SelectionDAG is combining two SDNodes and then merging their DbgValues via DAG.TransferDbgValues(), SelectionDAG::AddDbgValue() doesn't check whether a DbgValue is already in that SDNode's list of DbgValues and happily adds all of them. In cases like the one in the PR, this can lead to a pathological situation where — when dagcombining a long chain of instructions — the SDNode's DbgValMap is growing exponentially.
Details
Diff Detail
Event Timeline
as for testing - assuming these duplicates get deduplicated elsewhere (could you explain where?) then I doubt there's much to test - this is then just a perf optimization, not a change in any semantics. Maybe dumping MI could be testable, but I'm not sure what the dumping options (& whether they're available in non-asserts builds, etc) are like.
lib/CodeGen/SelectionDAG/SelectionDAG.cpp | ||
---|---|---|
6180 | Could 'Vals' be an actual set of SDDbgValue*s? Are SDDbgValue*s inherently uniqued such that pointer identity would be sufficient? (or do you need that equality comparison added above? Which could hopefully be adjusted to < comparison (or hashing) for a set-like structure) |
Just as a remark, this patch seems to work for fixing the OOM issue occuring in certain FreeBSD ports here: http://docs.freebsd.org/cgi/mid.cgi?542105A3.4090507
So it would be nice if it can go in. :-)
Could 'Vals' be an actual set of SDDbgValue*s?
Are SDDbgValue*s inherently uniqued such that pointer identity would be sufficient? (or do you need that equality comparison added above? Which could hopefully be adjusted to < comparison (or hashing) for a set-like structure)