Balance concatenations in DFG (#5598)

The DFG peephole pass converts all associative trees into right leaning,
which is good for simplifying pattern recognition, but can lead to an
excessive amount of wide intermediate results being constructed for
right leaning concatenations.

Add a new pass to balance concatenation trees by trying to:
- Create VL_EDATASIZE (32-bit) sub-terms, so words can then be packed
  easily afterwards
- Try to ensure the operands of a concat are roughly the same width
  within a concatenation tree. This does not yield the shortest tree,
  but it ensures it has many sub-nodes that are small enough to fit into
  machine registers.

This can eliminate a lot of wide intermediate results, which would need
temporaries, and also increases ILP within sub-expressions (assuming the
C compiler can't figure that out itself).

This is over 2x run-time speedup on the high_perf configuration of
VeeR EH2 (which you could arguably also get with -fno-dfg, but oh well).
This commit is contained in:
Geza Lore
2024-11-09 18:14:19 +00:00
committed by GitHub
parent 4969125e5a
commit f073b278f9
12 changed files with 289 additions and 8 deletions
+10 -1
View File
@@ -42,6 +42,11 @@ V3DfgEliminateVarsContext::~V3DfgEliminateVarsContext() {
m_varsRemoved);
}
V3DfgBalanceTreesContext::~V3DfgBalanceTreesContext() {
V3Stats::addStat("Optimizations, DFG " + m_label + " BalanceTrees, concat trees balanced",
m_balancedConcats);
}
static std::string getPrefix(const std::string& label) {
if (label.empty()) return "";
std::string str = VString::removeWhitespace(label);
@@ -332,7 +337,7 @@ void V3DfgPasses::eliminateVars(DfgGraph& dfg, V3DfgEliminateVarsContext& ctx) {
for (AstVar* const varp : replacedVariables) varp->unlinkFrBack()->deleteTree();
}
void V3DfgPasses::optimize(DfgGraph& dfg, V3DfgOptimizationContext& ctx) {
void V3DfgPasses::optimize(DfgGraph& dfg, V3DfgOptimizationContext& ctx, bool lastInvocation) {
// There is absolutely nothing useful we can do with a graph of size 2 or less
if (dfg.size() <= 2) return;
@@ -360,6 +365,10 @@ void V3DfgPasses::optimize(DfgGraph& dfg, V3DfgOptimizationContext& ctx) {
}
// Accumulate patterns for reporting
if (v3Global.opt.stats()) ctx.m_patternStats.accumulate(dfg);
// The peephole pass covnerts all trees to right leaning, so only do this on the last DFG run.
if (lastInvocation) {
apply(4, "balanceTrees", [&]() { balanceTrees(dfg, ctx.m_balanceTreesContext); });
}
apply(4, "regularize", [&]() { regularize(dfg, ctx.m_regularizeContext); });
if (dumpDfgLevel() >= 8) dfg.dumpDotAllVarConesPrefixed(ctx.prefix() + "optimized");
}