mirror of
https://github.com/intel/llvm.git
synced 2026-01-13 11:02:04 +08:00
[DAG] SDPatternMatch - Replace runtime data structures with lengths known at compile time (#172064)
Following the suggestions in #170061, I replaced `SmallVector<SDValue>` with `std::array<SDValue, NumPatterns>` and `SmallBitVector` with `Bitset<NumPatterns>`. I had to make some changes to the `collectLeaves` and `reassociatableMatchHelper` functions. In `collectLeaves` specifically, I changed the return type so I could propagate a failure in case the number of found leaves is greater than the number of expected patterns. I also added a new unit test that, together with the one already present in the previous line, checks if the matching fails in the cases where the number of patterns is less or more than the number of leaves. I don't think this is going to completely address the increased compile time reported in #169644, but hopefully it leads to an improvement.
This commit is contained in:
committed by
GitHub
parent
f785ca0d72
commit
755a693299
@@ -1302,20 +1302,20 @@ inline BinaryOpc_match<ValTy, AllOnes_match, true> m_Not(const ValTy &V) {
|
||||
template <typename... PatternTs> struct ReassociatableOpc_match {
|
||||
unsigned Opcode;
|
||||
std::tuple<PatternTs...> Patterns;
|
||||
constexpr static size_t NumPatterns =
|
||||
std::tuple_size_v<std::tuple<PatternTs...>>;
|
||||
|
||||
ReassociatableOpc_match(unsigned Opcode, const PatternTs &...Patterns)
|
||||
: Opcode(Opcode), Patterns(Patterns...) {}
|
||||
|
||||
template <typename MatchContext>
|
||||
bool match(const MatchContext &Ctx, SDValue N) {
|
||||
constexpr size_t NumPatterns = std::tuple_size_v<std::tuple<PatternTs...>>;
|
||||
|
||||
SmallVector<SDValue> Leaves;
|
||||
collectLeaves(N, Leaves);
|
||||
if (Leaves.size() != NumPatterns)
|
||||
std::array<SDValue, NumPatterns> Leaves;
|
||||
size_t LeavesIdx = 0;
|
||||
if (!(collectLeaves(N, Leaves, LeavesIdx) && (LeavesIdx == NumPatterns)))
|
||||
return false;
|
||||
|
||||
SmallBitVector Used(NumPatterns);
|
||||
Bitset<NumPatterns> Used;
|
||||
return std::apply(
|
||||
[&](auto &...P) -> bool {
|
||||
return reassociatableMatchHelper(Ctx, Leaves, Used, P...);
|
||||
@@ -1323,36 +1323,41 @@ template <typename... PatternTs> struct ReassociatableOpc_match {
|
||||
Patterns);
|
||||
}
|
||||
|
||||
void collectLeaves(SDValue V, SmallVector<SDValue> &Leaves) {
|
||||
bool collectLeaves(SDValue V, std::array<SDValue, NumPatterns> &Leaves,
|
||||
std::size_t &LeafIdx) {
|
||||
if (V->getOpcode() == Opcode) {
|
||||
for (size_t I = 0, N = V->getNumOperands(); I < N; I++)
|
||||
collectLeaves(V->getOperand(I), Leaves);
|
||||
if ((LeafIdx == NumPatterns) ||
|
||||
!collectLeaves(V->getOperand(I), Leaves, LeafIdx))
|
||||
return false;
|
||||
} else {
|
||||
Leaves.emplace_back(V);
|
||||
Leaves[LeafIdx] = V;
|
||||
LeafIdx++;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
// Searchs for a matching leaf for every sub-pattern.
|
||||
template <typename MatchContext, typename PatternHd, typename... PatternTl>
|
||||
[[nodiscard]] inline bool
|
||||
reassociatableMatchHelper(const MatchContext &Ctx, ArrayRef<SDValue> Leaves,
|
||||
SmallBitVector &Used, PatternHd &HeadPattern,
|
||||
Bitset<NumPatterns> &Used, PatternHd &HeadPattern,
|
||||
PatternTl &...TailPatterns) {
|
||||
for (size_t Match = 0, N = Used.size(); Match < N; Match++) {
|
||||
if (Used[Match] || !(sd_context_match(Leaves[Match], Ctx, HeadPattern)))
|
||||
continue;
|
||||
Used[Match] = true;
|
||||
Used.set(Match);
|
||||
if (reassociatableMatchHelper(Ctx, Leaves, Used, TailPatterns...))
|
||||
return true;
|
||||
Used[Match] = false;
|
||||
Used.reset(Match);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
template <typename MatchContext>
|
||||
[[nodiscard]] inline bool reassociatableMatchHelper(const MatchContext &Ctx,
|
||||
ArrayRef<SDValue> Leaves,
|
||||
SmallBitVector &Used) {
|
||||
[[nodiscard]] inline bool
|
||||
reassociatableMatchHelper(const MatchContext &Ctx, ArrayRef<SDValue> Leaves,
|
||||
Bitset<NumPatterns> &Used) {
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
@@ -803,6 +803,8 @@ TEST_F(SelectionDAGPatternMatchTest, matchReassociatableOp) {
|
||||
SDValue ADD = DAG->getNode(ISD::ADD, DL, Int32VT, ADD01, ADD23);
|
||||
|
||||
EXPECT_FALSE(sd_match(ADD01, m_ReassociatableAdd(m_Value())));
|
||||
EXPECT_FALSE(
|
||||
sd_match(ADD01, m_ReassociatableAdd(m_Value(), m_Value(), m_Value())));
|
||||
EXPECT_TRUE(sd_match(ADD01, m_ReassociatableAdd(m_Value(), m_Value())));
|
||||
EXPECT_TRUE(sd_match(ADD23, m_ReassociatableAdd(m_Value(), m_Value())));
|
||||
EXPECT_TRUE(sd_match(
|
||||
|
||||
Reference in New Issue
Block a user