Skip to content

[SelectionDAG] Add space-optimized forms of OPC_CheckComplexPat #73310

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jan 11, 2024

Conversation

wangpc-pp
Copy link
Contributor

We record the usage of each ComplexPat and sort the ComplexPats
by usage.

For the top 8 ComplexPats, we will emit a OPC_CheckComplexPatN
to save one byte.

Overall this reduces the llc binary size with all in-tree targets by
about 89K.

@wangpc-pp wangpc-pp requested a review from topperc November 24, 2023 10:14
@llvmbot llvmbot added the llvm:SelectionDAG SelectionDAGISel as well label Nov 24, 2023
@wangpc-pp wangpc-pp requested a review from jrtc27 November 24, 2023 10:14
@llvmbot
Copy link
Member

llvmbot commented Nov 24, 2023

@llvm/pr-subscribers-llvm-selectiondag

Author: Wang Pengcheng (wangpc-pp)

Changes

We record the usage of each ComplexPat and sort the ComplexPats
by usage.

For the top 8 ComplexPats, we will emit a OPC_CheckComplexPatN
to save one byte.

Overall this reduces the llc binary size with all in-tree targets by
about 89K.


Full diff: https://github.com/llvm/llvm-project/pull/73310.diff

7 Files Affected:

  • (modified) llvm/include/llvm/CodeGen/SelectionDAGISel.h (+8)
  • (modified) llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp (+12-2)
  • (modified) llvm/test/TableGen/dag-isel-complexpattern.td (+1-1)
  • (modified) llvm/utils/TableGen/CodeGenDAGPatterns.h (+12)
  • (modified) llvm/utils/TableGen/DAGISelMatcher.h (+1-1)
  • (modified) llvm/utils/TableGen/DAGISelMatcherEmitter.cpp (+18-11)
  • (modified) llvm/utils/TableGen/DAGISelMatcherGen.cpp (+5-4)
diff --git a/llvm/include/llvm/CodeGen/SelectionDAGISel.h b/llvm/include/llvm/CodeGen/SelectionDAGISel.h
index e6513eb6abc8749..fd9857159d014e3 100644
--- a/llvm/include/llvm/CodeGen/SelectionDAGISel.h
+++ b/llvm/include/llvm/CodeGen/SelectionDAGISel.h
@@ -176,6 +176,14 @@ class SelectionDAGISel : public MachineFunctionPass {
     OPC_CheckChild2CondCode,
     OPC_CheckValueType,
     OPC_CheckComplexPat,
+    OPC_CheckComplexPat0,
+    OPC_CheckComplexPat1,
+    OPC_CheckComplexPat2,
+    OPC_CheckComplexPat3,
+    OPC_CheckComplexPat4,
+    OPC_CheckComplexPat5,
+    OPC_CheckComplexPat6,
+    OPC_CheckComplexPat7,
     OPC_CheckAndImm,
     OPC_CheckOrImm,
     OPC_CheckImmAllOnesV,
diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
index 7d9bebdca127224..22ca68e24600fb7 100644
--- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
@@ -3279,8 +3279,18 @@ void SelectionDAGISel::SelectCodeCommon(SDNode *NodeToMatch,
         break;
       continue;
     }
-    case OPC_CheckComplexPat: {
-      unsigned CPNum = MatcherTable[MatcherIndex++];
+    case OPC_CheckComplexPat:
+    case OPC_CheckComplexPat0:
+    case OPC_CheckComplexPat1:
+    case OPC_CheckComplexPat2:
+    case OPC_CheckComplexPat3:
+    case OPC_CheckComplexPat4:
+    case OPC_CheckComplexPat5:
+    case OPC_CheckComplexPat6:
+    case OPC_CheckComplexPat7: {
+      unsigned CPNum = Opcode == OPC_CheckComplexPat
+                           ? MatcherTable[MatcherIndex++]
+                           : Opcode - OPC_CheckComplexPat0;
       unsigned RecNo = MatcherTable[MatcherIndex++];
       assert(RecNo < RecordedNodes.size() && "Invalid CheckComplexPat");
 
diff --git a/llvm/test/TableGen/dag-isel-complexpattern.td b/llvm/test/TableGen/dag-isel-complexpattern.td
index 40fd03cc8839424..1bb473a9df5a954 100644
--- a/llvm/test/TableGen/dag-isel-complexpattern.td
+++ b/llvm/test/TableGen/dag-isel-complexpattern.td
@@ -22,7 +22,7 @@ def CP32 : ComplexPattern<i32, 0, "SelectCP32">;
 def INSTR : Instruction {
 // CHECK-LABEL: OPC_CheckOpcode, TARGET_VAL(ISD::STORE)
 // CHECK: OPC_CheckType, MVT::i32
-// CHECK: OPC_CheckComplexPat, /*CP*/0, /*#*/1, // SelectCP32:$
+// CHECK: OPC_CheckComplexPat0, /*#*/1, // SelectCP32:$
 // CHECK: Src: (st (add:{ *:[i32] } (CP32:{ *:[i32] }), (CP32:{ *:[i32] })), i64:{ *:[i64] }:$addr)
   let OutOperandList = (outs);
   let InOperandList = (ins GPR64:$addr);
diff --git a/llvm/utils/TableGen/CodeGenDAGPatterns.h b/llvm/utils/TableGen/CodeGenDAGPatterns.h
index 2611fe06f55ca53..f856f007b1f45d6 100644
--- a/llvm/utils/TableGen/CodeGenDAGPatterns.h
+++ b/llvm/utils/TableGen/CodeGenDAGPatterns.h
@@ -1117,6 +1117,9 @@ class CodeGenDAGPatterns {
   std::map<Record*, DAGDefaultOperand, LessRecordByID> DefaultOperands;
   std::map<Record*, DAGInstruction, LessRecordByID> Instructions;
 
+  /// ComplexPatternUsage - Record the usage of ComplexPattern.
+  std::map<const ComplexPattern *, unsigned> ComplexPatternUsage;
+
   // Specific SDNode definitions:
   Record *intrinsic_void_sdnode;
   Record *intrinsic_w_chain_sdnode, *intrinsic_wo_chain_sdnode;
@@ -1163,6 +1166,15 @@ class CodeGenDAGPatterns {
     return F->second;
   }
 
+  const std::map<const ComplexPattern *, unsigned> &
+  getComplexPatternUsage() const {
+    return ComplexPatternUsage;
+  }
+
+  void increaseComplexPatternUsage(const ComplexPattern *CP) {
+    ComplexPatternUsage[CP]++;
+  }
+
   const CodeGenIntrinsic &getIntrinsic(Record *R) const {
     for (unsigned i = 0, e = Intrinsics.size(); i != e; ++i)
       if (Intrinsics[i].TheDef == R) return Intrinsics[i];
diff --git a/llvm/utils/TableGen/DAGISelMatcher.h b/llvm/utils/TableGen/DAGISelMatcher.h
index e3cf847edd1273b..9e962b14285c395 100644
--- a/llvm/utils/TableGen/DAGISelMatcher.h
+++ b/llvm/utils/TableGen/DAGISelMatcher.h
@@ -34,7 +34,7 @@ namespace llvm {
   class TreePattern;
 
 Matcher *ConvertPatternToMatcher(const PatternToMatch &Pattern,unsigned Variant,
-                                 const CodeGenDAGPatterns &CGP);
+                                 CodeGenDAGPatterns &CGP);
 void OptimizeMatcher(std::unique_ptr<Matcher> &Matcher,
                      const CodeGenDAGPatterns &CGP);
 void EmitMatcherTable(Matcher *Matcher, const CodeGenDAGPatterns &CGP,
diff --git a/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp b/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp
index 4a11991036efc11..aba1f04dfae9b64 100644
--- a/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp
+++ b/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp
@@ -63,7 +63,6 @@ class MatcherTableEmitter {
   StringMap<unsigned> PatternPredicateMap;
   std::vector<std::string> PatternPredicates;
 
-  DenseMap<const ComplexPattern*, unsigned> ComplexPatternMap;
   std::vector<const ComplexPattern*> ComplexPatterns;
 
 
@@ -85,7 +84,15 @@ class MatcherTableEmitter {
 
 public:
   MatcherTableEmitter(const CodeGenDAGPatterns &cgp)
-      : CGP(cgp), OpcodeCounts(Matcher::HighestKind + 1, 0) {}
+      : CGP(cgp), OpcodeCounts(Matcher::HighestKind + 1, 0) {
+    // Sort ComplexPatterns by usage.
+    auto &Usage = cgp.getComplexPatternUsage();
+    std::vector<std::pair<const ComplexPattern *, unsigned>> PatternList(
+        Usage.begin(), Usage.end());
+    sort(PatternList, [](auto &A, auto &B) { return A.second > B.second; });
+    for (auto &Pattern : PatternList)
+      ComplexPatterns.push_back(Pattern.first);
+  }
 
   unsigned EmitMatcherList(const Matcher *N, const unsigned Indent,
                            unsigned StartIdx, raw_ostream &OS);
@@ -146,12 +153,7 @@ class MatcherTableEmitter {
     return Entry-1;
   }
   unsigned getComplexPat(const ComplexPattern &P) {
-    unsigned &Entry = ComplexPatternMap[&P];
-    if (Entry == 0) {
-      ComplexPatterns.push_back(&P);
-      Entry = ComplexPatterns.size();
-    }
-    return Entry-1;
+    return llvm::find(ComplexPatterns, &P) - ComplexPatterns.begin();
   }
 
   unsigned getNodeXFormID(Record *Rec) {
@@ -625,8 +627,13 @@ EmitMatcher(const Matcher *N, const unsigned Indent, unsigned CurrentIdx,
   case Matcher::CheckComplexPat: {
     const CheckComplexPatMatcher *CCPM = cast<CheckComplexPatMatcher>(N);
     const ComplexPattern &Pattern = CCPM->getPattern();
-    OS << "OPC_CheckComplexPat, /*CP*/" << getComplexPat(Pattern) << ", /*#*/"
-       << CCPM->getMatchNumber() << ',';
+    unsigned PatternNo = getComplexPat(Pattern);
+    if (PatternNo < 8)
+      OS << "OPC_CheckComplexPat" << PatternNo << ", /*#*/"
+         << CCPM->getMatchNumber() << ',';
+    else
+      OS << "OPC_CheckComplexPat, /*CP*/" << PatternNo << ", /*#*/"
+         << CCPM->getMatchNumber() << ',';
 
     if (!OmitComments) {
       OS << " // " << Pattern.getSelectFunc();
@@ -638,7 +645,7 @@ EmitMatcher(const Matcher *N, const unsigned Indent, unsigned CurrentIdx,
         OS << " + chain result";
     }
     OS << '\n';
-    return 3;
+    return PatternNo < 8 ? 2 : 3;
   }
 
   case Matcher::CheckAndImm: {
diff --git a/llvm/utils/TableGen/DAGISelMatcherGen.cpp b/llvm/utils/TableGen/DAGISelMatcherGen.cpp
index d08f57b84b95f08..e6f6b7f47a882d7 100644
--- a/llvm/utils/TableGen/DAGISelMatcherGen.cpp
+++ b/llvm/utils/TableGen/DAGISelMatcherGen.cpp
@@ -56,7 +56,7 @@ static MVT::SimpleValueType getRegisterValueType(Record *R,
 namespace {
   class MatcherGen {
     const PatternToMatch &Pattern;
-    const CodeGenDAGPatterns &CGP;
+    CodeGenDAGPatterns &CGP;
 
     /// PatWithNoTypes - This is a clone of Pattern.getSrcPattern() that starts
     /// out with all of the types removed.  This allows us to insert type checks
@@ -102,7 +102,7 @@ namespace {
     /// which should have future checks stuck into its Next position.
     Matcher *CurPredicate;
   public:
-    MatcherGen(const PatternToMatch &pattern, const CodeGenDAGPatterns &cgp);
+    MatcherGen(const PatternToMatch &pattern, CodeGenDAGPatterns &cgp);
 
     bool EmitMatcherCode(unsigned Variant);
     void EmitResultCode();
@@ -146,7 +146,7 @@ namespace {
 } // end anonymous namespace
 
 MatcherGen::MatcherGen(const PatternToMatch &pattern,
-                       const CodeGenDAGPatterns &cgp)
+                       CodeGenDAGPatterns &cgp)
 : Pattern(pattern), CGP(cgp), NextRecordedOperandNo(0),
   TheMatcher(nullptr), CurPredicate(nullptr) {
   // We need to produce the matcher tree for the patterns source pattern.  To do
@@ -601,6 +601,7 @@ bool MatcherGen::EmitMatcherCode(unsigned Variant) {
 
     // Emit a CheckComplexPat operation, which does the match (aborting if it
     // fails) and pushes the matched operands onto the recorded nodes list.
+    CGP.increaseComplexPatternUsage(CP);
     AddMatcher(new CheckComplexPatMatcher(*CP, RecNodeEntry, N->getName(),
                                           NextRecordedOperandNo));
 
@@ -1081,7 +1082,7 @@ void MatcherGen::EmitResultCode() {
 /// the specified variant.  If the variant number is invalid, this returns null.
 Matcher *llvm::ConvertPatternToMatcher(const PatternToMatch &Pattern,
                                        unsigned Variant,
-                                       const CodeGenDAGPatterns &CGP) {
+                                       CodeGenDAGPatterns &CGP) {
   MatcherGen Gen(Pattern, CGP);
 
   // Generate the code for the matcher.

@wangpc-pp wangpc-pp requested review from asb, RKSimon and ilovepi November 24, 2023 10:15
Copy link

github-actions bot commented Nov 24, 2023

✅ With the latest revision this PR passed the C/C++ code formatter.

@wangpc-pp
Copy link
Contributor Author

Ping.

@wangpc-pp wangpc-pp force-pushed the main-matcher-table-check-complex-pat branch from b7bd6ab to 6564183 Compare December 11, 2023 12:40
wangpc-pp added a commit that referenced this pull request Dec 12, 2023
@wangpc-pp wangpc-pp force-pushed the main-matcher-table-check-complex-pat branch 2 times, most recently from a9db2c8 to a84fe55 Compare December 12, 2023 11:29
@wangpc-pp
Copy link
Contributor Author

Ping.

Copy link
Contributor

@ilovepi ilovepi left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fine to me, and in line with the earlier patches. Would you mind adding some documentation about the change somewhere though? I feel like we should at least have a meta comment somewhere noting that the first 8 numbers are special.

You probably want to wait for one of the code owners to give the LGTM before landing, though.

@wangpc-pp
Copy link
Contributor Author

This seems fine to me, and in line with the earlier patches. Would you mind adding some documentation about the change somewhere though? I feel like we should at least have a meta comment somewhere noting that the first 8 numbers are special.

Thanks! I'm working on adding some comments to the opcodes and will create a PR later.

@wangpc-pp wangpc-pp force-pushed the main-matcher-table-check-complex-pat branch from 8c3fd70 to 9d60d04 Compare January 5, 2024 07:46
We record the usage of each `ComplexPat` and sort the `ComplexPat`s
by usage.

For the top 8 `ComplexPat`s, we will emit a `OPC_CheckComplexPatN`
to save one byte.

Overall this reduces the llc binary size with all in-tree targets by
about 89K.
@wangpc-pp wangpc-pp force-pushed the main-matcher-table-check-complex-pat branch from 9d60d04 to 352fd1f Compare January 8, 2024 05:28
@wangpc-pp wangpc-pp requested review from arsenm and ilovepi January 8, 2024 08:19
@wangpc-pp wangpc-pp merged commit 211abe3 into llvm:main Jan 11, 2024
@wangpc-pp wangpc-pp deleted the main-matcher-table-check-complex-pat branch January 11, 2024 07:31
wangpc-pp added a commit to wangpc-pp/llvm-project that referenced this pull request Jan 11, 2024
We record the usage of each `Predicate` and sort them by usage.

For the top 8 `Predicate`s, we will emit a `PC_CheckPredicateN` to
save one byte.

Overall this reduces the llc binary size with all in-tree targets by
about 61K.

This PR is stacked on llvm#73310.
MaskRay added a commit that referenced this pull request Jan 12, 2024
Otherwise `ComplexPatternList` order can be non-deterministic.
justinfargnoli pushed a commit to justinfargnoli/llvm-project that referenced this pull request Jan 28, 2024
…#73310)

We record the usage of each `ComplexPat` and sort the `ComplexPat`s
by usage.

For the top 8 `ComplexPat`s, we will emit a `OPC_CheckComplexPatN`
to save one byte.

Overall this reduces the llc binary size with all in-tree targets by
about 89K.
justinfargnoli pushed a commit to justinfargnoli/llvm-project that referenced this pull request Jan 28, 2024
Otherwise `ComplexPatternList` order can be non-deterministic.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
llvm:SelectionDAG SelectionDAGISel as well
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants