[llvm] 54c93aa - [SandboxVec][Legality] Scaffolding for Legality (#112623)

via llvm-commits llvm-commits at lists.llvm.org
Mon Oct 21 09:17:49 PDT 2024


Author: vporpo
Date: 2024-10-21T09:17:46-07:00
New Revision: 54c93aabec965469fe7db1f4391a190e3d640feb

URL: https://github.com/llvm/llvm-project/commit/54c93aabec965469fe7db1f4391a190e3d640feb
DIFF: https://github.com/llvm/llvm-project/commit/54c93aabec965469fe7db1f4391a190e3d640feb.diff

LOG: [SandboxVec][Legality] Scaffolding for Legality (#112623)

This patch adds a LegalityResultWithReason class for describing the
reason why legality decided not to vectorize the code.

Added: 
    llvm/lib/Transforms/Vectorize/SandboxVectorizer/Legality.cpp

Modified: 
    llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/Legality.h
    llvm/lib/Transforms/Vectorize/CMakeLists.txt
    llvm/lib/Transforms/Vectorize/SandboxVectorizer/Passes/BottomUpVec.cpp
    llvm/unittests/Transforms/Vectorize/SandboxVectorizer/LegalityTest.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/Legality.h b/llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/Legality.h
index 50fa56c5b21940..233abf3efd64e1 100644
--- a/llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/Legality.h
+++ b/llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/Legality.h
@@ -13,6 +13,8 @@
 #define LLVM_TRANSFORMS_VECTORIZE_SANDBOXVECTORIZER_LEGALITY_H
 
 #include "llvm/ADT/ArrayRef.h"
+#include "llvm/Support/Casting.h"
+#include "llvm/Support/raw_ostream.h"
 
 namespace llvm::sandboxir {
 
@@ -20,9 +22,38 @@ class LegalityAnalysis;
 class Value;
 
 enum class LegalityResultID {
+  Pack,  ///> Collect scalar values.
   Widen, ///> Vectorize by combining scalars to a vector.
 };
 
+/// The reason for vectorizing or not vectorizing.
+enum class ResultReason {
+  DiffOpcodes,
+  DiffTypes,
+};
+
+#ifndef NDEBUG
+struct ToStr {
+  static const char *getLegalityResultID(LegalityResultID ID) {
+    switch (ID) {
+    case LegalityResultID::Pack:
+      return "Pack";
+    case LegalityResultID::Widen:
+      return "Widen";
+    }
+  }
+
+  static const char *getVecReason(ResultReason Reason) {
+    switch (Reason) {
+    case ResultReason::DiffOpcodes:
+      return "DiffOpcodes";
+    case ResultReason::DiffTypes:
+      return "DiffTypes";
+    }
+  }
+};
+#endif // NDEBUG
+
 /// The legality outcome is represented by a class rather than an enum class
 /// because in some cases the legality checks are expensive and look for a
 /// particular instruction that can be passed along to the vectorizer to avoid
@@ -35,7 +66,34 @@ class LegalityResult {
   friend class LegalityAnalysis;
 
 public:
+  virtual ~LegalityResult() {}
   LegalityResultID getSubclassID() const { return ID; }
+#ifndef NDEBUG
+  virtual void print(raw_ostream &OS) const {
+    OS << ToStr::getLegalityResultID(ID);
+  }
+  LLVM_DUMP_METHOD void dump() const;
+  friend raw_ostream &operator<<(raw_ostream &OS, const LegalityResult &LR) {
+    LR.print(OS);
+    return OS;
+  }
+#endif // NDEBUG
+};
+
+/// Base class for results with reason.
+class LegalityResultWithReason : public LegalityResult {
+  ResultReason Reason;
+  LegalityResultWithReason(LegalityResultID ID, ResultReason Reason)
+      : LegalityResult(ID), Reason(Reason) {}
+  friend class Pack; // For constructor.
+
+public:
+#ifndef NDEBUG
+  void print(raw_ostream &OS) const override {
+    LegalityResult::print(OS);
+    OS << " Reason: " << ToStr::getVecReason(Reason);
+  }
+#endif
 };
 
 class Widen final : public LegalityResult {
@@ -48,14 +106,37 @@ class Widen final : public LegalityResult {
   }
 };
 
+class Pack final : public LegalityResultWithReason {
+  Pack(ResultReason Reason)
+      : LegalityResultWithReason(LegalityResultID::Pack, Reason) {}
+  friend class LegalityAnalysis; // For constructor.
+
+public:
+  static bool classof(const LegalityResult *From) {
+    return From->getSubclassID() == LegalityResultID::Pack;
+  }
+};
+
 /// Performs the legality analysis and returns a LegalityResult object.
 class LegalityAnalysis {
+  /// Owns the legality result objects created by createLegalityResult().
+  SmallVector<std::unique_ptr<LegalityResult>> ResultPool;
+  /// Checks opcodes, types and other IR-specifics and returns a ResultReason
+  /// object if not vectorizable, or nullptr otherwise.
+  std::optional<ResultReason>
+  notVectorizableBasedOnOpcodesAndTypes(ArrayRef<Value *> Bndl);
+
 public:
   LegalityAnalysis() = default;
-  LegalityResult canVectorize(ArrayRef<Value *> Bndl) {
-    // TODO: For now everything is legal.
-    return Widen();
+  /// A LegalityResult factory.
+  template <typename ResultT, typename... ArgsT>
+  ResultT &createLegalityResult(ArgsT... Args) {
+    ResultPool.push_back(std::unique_ptr<ResultT>(new ResultT(Args...)));
+    return cast<ResultT>(*ResultPool.back());
   }
+  /// Checks if it's legal to vectorize the instructions in \p Bndl.
+  /// \Returns a LegalityResult object owned by LegalityAnalysis.
+  LegalityResult &canVectorize(ArrayRef<Value *> Bndl);
 };
 
 } // namespace llvm::sandboxir

diff  --git a/llvm/lib/Transforms/Vectorize/CMakeLists.txt b/llvm/lib/Transforms/Vectorize/CMakeLists.txt
index fc4355af5af6b9..d769d5100afd23 100644
--- a/llvm/lib/Transforms/Vectorize/CMakeLists.txt
+++ b/llvm/lib/Transforms/Vectorize/CMakeLists.txt
@@ -5,6 +5,7 @@ add_llvm_component_library(LLVMVectorize
   LoopVectorize.cpp
   SandboxVectorizer/DependencyGraph.cpp
   SandboxVectorizer/Interval.cpp
+  SandboxVectorizer/Legality.cpp
   SandboxVectorizer/Passes/BottomUpVec.cpp
   SandboxVectorizer/Passes/RegionsFromMetadata.cpp
   SandboxVectorizer/SandboxVectorizer.cpp

diff  --git a/llvm/lib/Transforms/Vectorize/SandboxVectorizer/Legality.cpp b/llvm/lib/Transforms/Vectorize/SandboxVectorizer/Legality.cpp
new file mode 100644
index 00000000000000..0e2cd83c37b0cd
--- /dev/null
+++ b/llvm/lib/Transforms/Vectorize/SandboxVectorizer/Legality.cpp
@@ -0,0 +1,39 @@
+//===- Legality.cpp -------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "llvm/Transforms/Vectorize/SandboxVectorizer/Legality.h"
+#include "llvm/SandboxIR/Value.h"
+#include "llvm/Support/Debug.h"
+
+namespace llvm::sandboxir {
+
+#ifndef NDEBUG
+void LegalityResult::dump() const {
+  print(dbgs());
+  dbgs() << "\n";
+}
+#endif // NDEBUG
+
+std::optional<ResultReason>
+LegalityAnalysis::notVectorizableBasedOnOpcodesAndTypes(
+    ArrayRef<Value *> Bndl) {
+  // TODO: Unimplemented.
+  return std::nullopt;
+}
+
+LegalityResult &LegalityAnalysis::canVectorize(ArrayRef<Value *> Bndl) {
+  if (auto ReasonOpt = notVectorizableBasedOnOpcodesAndTypes(Bndl))
+    return createLegalityResult<Pack>(*ReasonOpt);
+
+  // TODO: Check for existing vectors containing values in Bndl.
+
+  // TODO: Check with scheduler.
+
+  return createLegalityResult<Widen>();
+}
+} // namespace llvm::sandboxir

diff  --git a/llvm/lib/Transforms/Vectorize/SandboxVectorizer/Passes/BottomUpVec.cpp b/llvm/lib/Transforms/Vectorize/SandboxVectorizer/Passes/BottomUpVec.cpp
index 6171d5e52b5869..f11420e47f3e1f 100644
--- a/llvm/lib/Transforms/Vectorize/SandboxVectorizer/Passes/BottomUpVec.cpp
+++ b/llvm/lib/Transforms/Vectorize/SandboxVectorizer/Passes/BottomUpVec.cpp
@@ -50,6 +50,10 @@ void BottomUpVec::vectorizeRec(ArrayRef<Value *> Bndl) {
     }
     break;
   }
+  case LegalityResultID::Pack: {
+    // TODO: Unimplemented
+    llvm_unreachable("Unimplemented");
+  }
   }
 }
 

diff  --git a/llvm/unittests/Transforms/Vectorize/SandboxVectorizer/LegalityTest.cpp b/llvm/unittests/Transforms/Vectorize/SandboxVectorizer/LegalityTest.cpp
index e16222ddb2d615..76e5a5ce5aed92 100644
--- a/llvm/unittests/Transforms/Vectorize/SandboxVectorizer/LegalityTest.cpp
+++ b/llvm/unittests/Transforms/Vectorize/SandboxVectorizer/LegalityTest.cpp
@@ -55,3 +55,24 @@ define void @foo(ptr %ptr) {
   auto Result = Legality.canVectorize({St0, St1});
   EXPECT_TRUE(isa<sandboxir::Widen>(Result));
 }
+
+#ifndef NDEBUG
+TEST_F(LegalityTest, LegalityResultDump) {
+  auto Matches = [](const sandboxir::LegalityResult &Result,
+                    const std::string &ExpectedStr) -> bool {
+    std::string Buff;
+    raw_string_ostream OS(Buff);
+    Result.print(OS);
+    return Buff == ExpectedStr;
+  };
+  sandboxir::LegalityAnalysis Legality;
+  EXPECT_TRUE(
+      Matches(Legality.createLegalityResult<sandboxir::Widen>(), "Widen"));
+  EXPECT_TRUE(Matches(Legality.createLegalityResult<sandboxir::Pack>(
+                          sandboxir::ResultReason::DiffOpcodes),
+                      "Pack Reason: DiffOpcodes"));
+  EXPECT_TRUE(Matches(Legality.createLegalityResult<sandboxir::Pack>(
+                          sandboxir::ResultReason::DiffTypes),
+                      "Pack Reason: DiffTypes"));
+}
+#endif // NDEBUG


        


More information about the llvm-commits mailing list