[llvm-branch-commits] [llvm] 92f6036 - Revert "[AMDGPU] Add AMDGPU-specific module splitting (#89245)"

via llvm-branch-commits llvm-branch-commits at lists.llvm.org
Thu May 23 23:44:24 PDT 2024


Author: Vitaly Buka
Date: 2024-05-23T23:44:21-07:00
New Revision: 92f6036dfea9e64b141dcba8f8329ab17e53c3a5

URL: https://github.com/llvm/llvm-project/commit/92f6036dfea9e64b141dcba8f8329ab17e53c3a5
DIFF: https://github.com/llvm/llvm-project/commit/92f6036dfea9e64b141dcba8f8329ab17e53c3a5.diff

LOG: Revert "[AMDGPU] Add AMDGPU-specific module splitting (#89245)"

This reverts commit d7c37130008374341e79c355ad85cc48942136ff.

Added: 
    

Modified: 
    llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.cpp
    llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.h
    llvm/lib/Target/AMDGPU/CMakeLists.txt

Removed: 
    llvm/lib/Target/AMDGPU/AMDGPUSplitModule.cpp
    llvm/lib/Target/AMDGPU/AMDGPUSplitModule.h
    llvm/test/tools/llvm-split/AMDGPU/address-taken-externalize-with-call.ll
    llvm/test/tools/llvm-split/AMDGPU/address-taken-externalize.ll
    llvm/test/tools/llvm-split/AMDGPU/debug-name-hiding.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-alias-dependencies.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-cost-ranking.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-dependencies.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-duplication.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-external.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-indirect.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-overridable.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-global-variables-noexternal.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-global-variables.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-load-balancing.ll
    llvm/test/tools/llvm-split/AMDGPU/kernels-no-dependencies.ll
    llvm/test/tools/llvm-split/AMDGPU/large-kernels-merging.ll
    llvm/test/tools/llvm-split/AMDGPU/lit.local.cfg


################################################################################
diff  --git a/llvm/lib/Target/AMDGPU/AMDGPUSplitModule.cpp b/llvm/lib/Target/AMDGPU/AMDGPUSplitModule.cpp
deleted file mode 100644
index 56e275ce707b6..0000000000000
--- a/llvm/lib/Target/AMDGPU/AMDGPUSplitModule.cpp
+++ /dev/null
@@ -1,744 +0,0 @@
-//===- AMDGPUSplitModule.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
-//
-//===----------------------------------------------------------------------===//
-//
-/// \file Implements a module splitting algorithm designed to support the
-/// FullLTO --lto-partitions option for parallel codegen. This is completely
-/// 
diff erent from the common SplitModule pass, as this system is designed with
-/// AMDGPU in mind.
-///
-/// The basic idea of this module splitting implementation is the same as
-/// SplitModule: load-balance the module's functions across a set of N
-/// partitions to allow parallel codegen. However, it does it very
-/// 
diff erently than the target-agnostic variant:
-///   - Kernels are used as the module's "roots".
-///     They're known entry points on AMDGPU, and everything else is often
-///     internal only.
-///   - Each kernel has a set of dependencies, and when a kernel and its
-///     dependencies is considered "big", we try to put it in a partition where
-///     most dependencies are already imported, to avoid duplicating large
-///     amounts of code.
-///   - There's special care for indirect calls in order to ensure
-///     AMDGPUResourceUsageAnalysis can work correctly.
-///
-/// This file also includes a more elaborate logging system to enable
-/// users to easily generate logs that (if desired) do not include any value
-/// names, in order to not leak information about the source file.
-/// Such logs are very helpful to understand and fix potential issues with
-/// module splitting.
-
-#include "AMDGPUSplitModule.h"
-#include "AMDGPUTargetMachine.h"
-#include "Utils/AMDGPUBaseInfo.h"
-#include "llvm/ADT/DenseMap.h"
-#include "llvm/ADT/SmallVector.h"
-#include "llvm/ADT/StringExtras.h"
-#include "llvm/ADT/StringRef.h"
-#include "llvm/Analysis/CallGraph.h"
-#include "llvm/Analysis/TargetTransformInfo.h"
-#include "llvm/IR/Function.h"
-#include "llvm/IR/Instruction.h"
-#include "llvm/IR/Module.h"
-#include "llvm/IR/User.h"
-#include "llvm/IR/Value.h"
-#include "llvm/Support/Casting.h"
-#include "llvm/Support/Debug.h"
-#include "llvm/Support/FileSystem.h"
-#include "llvm/Support/Path.h"
-#include "llvm/Support/Process.h"
-#include "llvm/Support/SHA256.h"
-#include "llvm/Support/Threading.h"
-#include "llvm/Support/raw_ostream.h"
-#include "llvm/Transforms/Utils/Cloning.h"
-#include <algorithm>
-#include <cassert>
-#include <iterator>
-#include <memory>
-#include <utility>
-#include <vector>
-
-using namespace llvm;
-
-#define DEBUG_TYPE "amdgpu-split-module"
-
-namespace {
-
-static cl::opt<float> LargeKernelFactor(
-    "amdgpu-module-splitting-large-kernel-threshold", cl::init(2.0f),
-    cl::Hidden,
-    cl::desc(
-        "consider a kernel as large and needing special treatment when it "
-        "exceeds the average cost of a partition by this factor; e;g. 2.0 "
-        "means if the kernel and its dependencies is 2 times bigger than "
-        "an average partition; 0 disables large kernels handling entirely"));
-
-static cl::opt<float> LargeKernelOverlapForMerge(
-    "amdgpu-module-splitting-large-kernel-merge-overlap", cl::init(0.8f),
-    cl::Hidden,
-    cl::desc("defines how much overlap between two large kernel's dependencies "
-             "is needed to put them in the same partition"));
-
-static cl::opt<bool> NoExternalizeGlobals(
-    "amdgpu-module-splitting-no-externalize-globals", cl::Hidden,
-    cl::desc("disables externalization of global variable with local linkage; "
-             "may cause globals to be duplicated which increases binary size"));
-
-static cl::opt<std::string>
-    LogDirOpt("amdgpu-module-splitting-log-dir", cl::Hidden,
-              cl::desc("output directory for AMDGPU module splitting logs"));
-
-static cl::opt<bool>
-    LogPrivate("amdgpu-module-splitting-log-private", cl::Hidden,
-               cl::desc("hash value names before printing them in the AMDGPU "
-                        "module splitting logs"));
-
-using CostType = InstructionCost::CostType;
-using PartitionID = unsigned;
-
-static bool isEntryPoint(const Function *F) {
-  return AMDGPU::isEntryFunctionCC(F->getCallingConv());
-}
-
-static std::string getName(const Value &V) {
-  static bool HideNames;
-
-  static llvm::once_flag HideNameInitFlag;
-  llvm::call_once(HideNameInitFlag, [&]() {
-    if (LogPrivate.getNumOccurrences())
-      HideNames = LogPrivate;
-    else {
-      const auto EV = sys::Process::GetEnv("AMD_SPLIT_MODULE_LOG_PRIVATE");
-      HideNames = (EV.value_or("0") != "0");
-    }
-  });
-
-  if (!HideNames)
-    return V.getName().str();
-  return toHex(SHA256::hash(arrayRefFromStringRef(V.getName())),
-               /*LowerCase=*/true);
-}
-
-/// Main logging helper.
-///
-/// Logging can be configured by the following environment variable.
-///   AMD_SPLIT_MODULE_LOG_DIR=<filepath>
-///     If set, uses <filepath> as the directory to write logfiles to
-///     each time module splitting is used.
-///   AMD_SPLIT_MODULE_LOG_PRIVATE
-///     If set to anything other than zero, all names are hidden.
-///
-/// Both environment variables have corresponding CL options which
-/// takes priority over them.
-///
-/// Any output printed to the log files is also printed to dbgs() when -debug is
-/// used and LLVM_DEBUG is defined.
-///
-/// This approach has a small disadvantage over LLVM_DEBUG though: logging logic
-/// cannot be removed from the code (by building without debug). This probably
-/// has a small performance cost because if some computation/formatting is
-/// needed for logging purpose, it may be done everytime only to be ignored
-/// by the logger.
-///
-/// As this pass only runs once and is not doing anything computationally
-/// expensive, this is likely a reasonable trade-off.
-///
-/// If some computation should really be avoided when unused, users of the class
-/// can check whether any logging will occur by using the bool operator.
-///
-/// \code
-///   if (SML) {
-///     // Executes only if logging to a file or if -debug is available and
-///     used.
-///   }
-/// \endcode
-class SplitModuleLogger {
-public:
-  SplitModuleLogger(const Module &M) {
-    std::string LogDir = LogDirOpt;
-    if (LogDir.empty())
-      LogDir = sys::Process::GetEnv("AMD_SPLIT_MODULE_LOG_DIR").value_or("");
-
-    // No log dir specified means we don't need to log to a file.
-    // We may still log to dbgs(), though.
-    if (LogDir.empty())
-      return;
-
-    // If a log directory is specified, create a new file with a unique name in
-    // that directory.
-    int Fd;
-    SmallString<0> PathTemplate;
-    SmallString<0> RealPath;
-    sys::path::append(PathTemplate, LogDir, "Module-%%-%%-%%-%%-%%-%%-%%.txt");
-    if (auto Err =
-            sys::fs::createUniqueFile(PathTemplate.str(), Fd, RealPath)) {
-      report_fatal_error("Failed to create log file at '" + Twine(LogDir) +
-                             "': " + Err.message(),
-                         /*CrashDiag=*/false);
-    }
-
-    FileOS = std::make_unique<raw_fd_ostream>(Fd, /*shouldClose=*/true);
-  }
-
-  bool hasLogFile() const { return FileOS != nullptr; }
-
-  raw_ostream &logfile() {
-    assert(FileOS && "no logfile!");
-    return *FileOS;
-  }
-
-  /// \returns true if this SML will log anything either to a file or dbgs().
-  /// Can be used to avoid expensive computations that are ignored when logging
-  /// is disabled.
-  operator bool() const {
-    return hasLogFile() || (DebugFlag && isCurrentDebugType(DEBUG_TYPE));
-  }
-
-private:
-  std::unique_ptr<raw_fd_ostream> FileOS;
-};
-
-template <typename Ty>
-static SplitModuleLogger &operator<<(SplitModuleLogger &SML, const Ty &Val) {
-  static_assert(
-      !std::is_same_v<Ty, Value>,
-      "do not print values to logs directly, use handleName instead!");
-  LLVM_DEBUG(dbgs() << Val);
-  if (SML.hasLogFile())
-    SML.logfile() << Val;
-  return SML;
-}
-
-/// Calculate the cost of each function in \p M
-/// \param SML Log Helper
-/// \param TM TargetMachine instance used to retrieve TargetTransformInfo.
-/// \param M Module to analyze.
-/// \param CostMap[out] Resulting Function -> Cost map.
-/// \return The module's total cost.
-static CostType
-calculateFunctionCosts(SplitModuleLogger &SML, const AMDGPUTargetMachine &TM,
-                       Module &M,
-                       DenseMap<const Function *, CostType> &CostMap) {
-  CostType ModuleCost = 0;
-  CostType KernelCost = 0;
-
-  for (auto &Fn : M) {
-    if (Fn.isDeclaration())
-      continue;
-
-    CostType FnCost = 0;
-    TargetTransformInfo TTI = TM.getTargetTransformInfo(Fn);
-
-    for (const auto &BB : Fn) {
-      for (const auto &I : BB) {
-        auto Cost =
-            TTI.getInstructionCost(&I, TargetTransformInfo::TCK_CodeSize);
-        assert(Cost != InstructionCost::getMax());
-        // Assume expensive if we can't tell the cost of an instruction.
-        CostType CostVal =
-            Cost.getValue().value_or(TargetTransformInfo::TCC_Expensive);
-        assert((FnCost + CostVal) >= FnCost && "Overflow!");
-        FnCost += CostVal;
-      }
-    }
-
-    assert(FnCost != 0);
-
-    CostMap[&Fn] = FnCost;
-    assert((ModuleCost + FnCost) >= ModuleCost && "Overflow!");
-    ModuleCost += FnCost;
-
-    if (isEntryPoint(&Fn))
-      KernelCost += FnCost;
-  }
-
-  CostType FnCost = (ModuleCost - KernelCost);
-  SML << "=> Total Module Cost: " << ModuleCost << '\n'
-      << "  => KernelCost: " << KernelCost << " ("
-      << format("%0.2f", (float(KernelCost) / ModuleCost) * 100) << "%)\n"
-      << "  => FnsCost: " << FnCost << " ("
-      << format("%0.2f", (float(FnCost) / ModuleCost) * 100) << "%)\n";
-
-  return ModuleCost;
-}
-
-static bool canBeIndirectlyCalled(const Function &F) {
-  if (F.isDeclaration() || isEntryPoint(&F))
-    return false;
-  return !F.hasLocalLinkage() ||
-         F.hasAddressTaken(/*PutOffender=*/nullptr,
-                           /*IgnoreCallbackUses=*/false,
-                           /*IgnoreAssumeLikeCalls=*/true,
-                           /*IgnoreLLVMUsed=*/true,
-                           /*IgnoreARCAttachedCall=*/false,
-                           /*IgnoreCastedDirectCall=*/true);
-}
-
-/// When a kernel or any of its callees performs an indirect call, this function
-/// takes over \ref addAllDependencies and adds all potentially callable
-/// functions to \p Fns so they can be counted as dependencies of the kernel.
-///
-/// This is needed due to how AMDGPUResourceUsageAnalysis operates: in the
-/// presence of an indirect call, the function's resource usage is the same as
-/// the most expensive function in the module.
-/// \param M    The module.
-/// \param Fns[out] Resulting list of functions.
-static void addAllIndirectCallDependencies(const Module &M,
-                                           DenseSet<const Function *> &Fns) {
-  for (const auto &Fn : M) {
-    if (canBeIndirectlyCalled(Fn))
-      Fns.insert(&Fn);
-  }
-}
-
-/// Adds the functions that \p Fn may call to \p Fns, then recurses into each
-/// callee until all reachable functions have been gathered.
-///
-/// \param SML Log Helper
-/// \param CG Call graph for \p Fn's module.
-/// \param Fn Current function to look at.
-/// \param Fns[out] Resulting list of functions.
-/// \param HadIndirectCall[out] Set to true if an indirect call was seen at some
-/// point, either in \p Fn or in one of the function it calls. When that
-/// happens, we fall back to adding all callable functions inside \p Fn's module
-/// to \p Fns.
-static void addAllDependencies(SplitModuleLogger &SML, const CallGraph &CG,
-                               const Function &Fn,
-                               DenseSet<const Function *> &Fns,
-                               bool &HadIndirectCall) {
-  assert(!Fn.isDeclaration());
-
-  const Module &M = *Fn.getParent();
-  SmallVector<const Function *> WorkList({&Fn});
-  while (!WorkList.empty()) {
-    const auto &CurFn = *WorkList.pop_back_val();
-    assert(!CurFn.isDeclaration());
-
-    // Scan for an indirect call. If such a call is found, we have to
-    // conservatively assume this can call all non-entrypoint functions in the
-    // module.
-
-    for (auto &CGEntry : *CG[&CurFn]) {
-      auto *CGNode = CGEntry.second;
-      auto *Callee = CGNode->getFunction();
-      if (!Callee) {
-        // Functions have an edge towards CallsExternalNode if they're external
-        // declarations, or if they do an indirect call. As we only process
-        // definitions here, we know this means the function has an indirect
-        // call. We then have to conservatively assume this can call all
-        // non-entrypoint functions in the module.
-        if (CGNode != CG.getCallsExternalNode())
-          continue; // this is another function-less node we don't care about.
-
-        SML << "Indirect call detected in " << getName(CurFn)
-            << " - treating all non-entrypoint functions as "
-               "potential dependencies\n";
-
-        // TODO: Print an ORE as well ?
-        addAllIndirectCallDependencies(M, Fns);
-        HadIndirectCall = true;
-        return;
-      }
-
-      if (Callee->isDeclaration())
-        continue;
-
-      auto [It, Inserted] = Fns.insert(Callee);
-      if (Inserted)
-        WorkList.push_back(Callee);
-    }
-  }
-}
-
-/// Contains information about a kernel and its dependencies.
-struct KernelWithDependencies {
-  KernelWithDependencies(SplitModuleLogger &SML, CallGraph &CG,
-                         const DenseMap<const Function *, CostType> &FnCosts,
-                         const Function *Fn)
-      : Fn(Fn) {
-    addAllDependencies(SML, CG, *Fn, Dependencies, HasIndirectCall);
-    TotalCost = FnCosts.at(Fn);
-    for (const auto *Dep : Dependencies) {
-      TotalCost += FnCosts.at(Dep);
-
-      // We cannot duplicate functions with external linkage, or functions that
-      // may be overriden at runtime.
-      HasNonDuplicatableDependecy |=
-          (Dep->hasExternalLinkage() || !Dep->isDefinitionExact());
-    }
-  }
-
-  const Function *Fn = nullptr;
-  DenseSet<const Function *> Dependencies;
-  /// Whether \p Fn or any of its \ref Dependencies contains an indirect call.
-  bool HasIndirectCall = false;
-  /// Whether any of \p Fn's dependencies cannot be duplicated.
-  bool HasNonDuplicatableDependecy = false;
-
-  CostType TotalCost = 0;
-
-  /// \returns true if this kernel and its dependencies can be considered large
-  /// according to \p Threshold.
-  bool isLarge(CostType Threshold) const {
-    return TotalCost > Threshold && !Dependencies.empty();
-  }
-};
-
-/// Calculates how much overlap there is between \p A and \p B.
-/// \return A number between 0.0 and 1.0, where 1.0 means A == B and 0.0 means A
-/// and B have no shared elements. Kernels do not count in overlap calculation.
-static float calculateOverlap(const DenseSet<const Function *> &A,
-                              const DenseSet<const Function *> &B) {
-  DenseSet<const Function *> Total;
-  for (const auto *F : A) {
-    if (!isEntryPoint(F))
-      Total.insert(F);
-  }
-
-  if (Total.empty())
-    return 0.0f;
-
-  unsigned NumCommon = 0;
-  for (const auto *F : B) {
-    if (isEntryPoint(F))
-      continue;
-
-    auto [It, Inserted] = Total.insert(F);
-    if (!Inserted)
-      ++NumCommon;
-  }
-
-  return static_cast<float>(NumCommon) / Total.size();
-}
-
-/// Performs all of the partitioning work on \p M.
-/// \param SML Log Helper
-/// \param M Module to partition.
-/// \param NumParts Number of partitions to create.
-/// \param ModuleCost Total cost of all functions in \p M.
-/// \param FnCosts Map of Function -> Cost
-/// \param WorkList Kernels and their dependencies to process in order.
-/// \returns The created partitions (a vector of size \p NumParts )
-static std::vector<DenseSet<const Function *>>
-doPartitioning(SplitModuleLogger &SML, Module &M, unsigned NumParts,
-               CostType ModuleCost,
-               const DenseMap<const Function *, CostType> &FnCosts,
-               const SmallVector<KernelWithDependencies> &WorkList) {
-
-  SML << "\n--Partitioning Starts--\n";
-
-  // Calculate a "large kernel threshold". When more than one kernel's total
-  // import cost exceeds this value, we will try to merge it with other,
-  // similarly large kernels.
-  //
-  // e.g. let two kernels X and Y have a import cost of ~10% of the module, we
-  // assign X to a partition as usual, but when we get to Y, we check if it's
-  // worth also putting it in Y's partition.
-  const CostType LargeKernelThreshold =
-      LargeKernelFactor ? ((ModuleCost / NumParts) * LargeKernelFactor)
-                        : std::numeric_limits<CostType>::max();
-
-  std::vector<DenseSet<const Function *>> Partitions;
-  Partitions.resize(NumParts);
-
-  // Assign a partition to each kernel, and try to keep the partitions more or
-  // less balanced. We do that through a priority queue sorted in reverse, so we
-  // can always look at the partition with the least content.
-  //
-  // There are some cases where we will be deliberately unbalanced though.
-  //  - Large kernels: we try to merge with existing partitions to reduce code
-  //  duplication.
-  //  - Kernels with indirect or external calls always go in the first partition
-  //  (P0).
-  auto ComparePartitions = [](const std::pair<PartitionID, CostType> &a,
-                              const std::pair<PartitionID, CostType> &b) {
-    // When two partitions have the same cost, assign to the one with the
-    // biggest ID first. This allows us to put things in P0 last, because P0 may
-    // have other stuff added later.
-    if (a.second == b.second)
-      return a.first < b.first;
-    return a.second > b.second;
-  };
-
-  // We can't use priority_queue here because we need to be able to access any
-  // element. This makes this a bit inefficient as we need to sort it again
-  // everytime we change it, but it's a very small array anyway (likely under 64
-  // partitions) so it's a cheap operation.
-  std::vector<std::pair<PartitionID, CostType>> BalancingQueue;
-  for (unsigned I = 0; I < NumParts; ++I)
-    BalancingQueue.push_back(std::make_pair(I, 0));
-
-  // Helper function to handle assigning a kernel to a partition. This takes
-  // care of updating the balancing queue.
-  const auto AssignToPartition = [&](PartitionID PID,
-                                     const KernelWithDependencies &KWD) {
-    auto &FnsInPart = Partitions[PID];
-    FnsInPart.insert(KWD.Fn);
-    FnsInPart.insert(KWD.Dependencies.begin(), KWD.Dependencies.end());
-
-    SML << "assign " << getName(*KWD.Fn) << " to P" << PID << "\n  ->  ";
-    if (!KWD.Dependencies.empty()) {
-      SML << KWD.Dependencies.size() << " dependencies added\n";
-    };
-
-    // Update the balancing queue. we scan backwards because in the common case
-    // the partition is at the end.
-    for (auto &[QueuePID, Cost] : reverse(BalancingQueue)) {
-      if (QueuePID == PID) {
-        CostType NewCost = 0;
-        for (auto *Fn : Partitions[PID])
-          NewCost += FnCosts.at(Fn);
-
-        SML << "[Updating P" << PID << " Cost]:" << Cost << " -> " << NewCost;
-        if (Cost) {
-          SML << " (" << unsigned(((float(NewCost) / Cost) - 1) * 100)
-              << "% increase)";
-        }
-        SML << '\n';
-
-        Cost = NewCost;
-      }
-    }
-
-    sort(BalancingQueue, ComparePartitions);
-  };
-
-  for (auto &CurKernel : WorkList) {
-    // When a kernel has indirect calls, it must stay in the first partition
-    // alongside every reachable non-entry function. This is a nightmare case
-    // for splitting as it severely limits what we can do.
-    if (CurKernel.HasIndirectCall) {
-      SML << "Kernel with indirect call(s): " << getName(*CurKernel.Fn)
-          << " defaulting to P0\n";
-      AssignToPartition(0, CurKernel);
-      continue;
-    }
-
-    // When a kernel has non duplicatable dependencies, we have to keep it in
-    // the first partition as well. This is a conservative approach, a
-    // finer-grained approach could keep track of which dependencies are
-    // non-duplicatable exactly and just make sure they're grouped together.
-    if (CurKernel.HasNonDuplicatableDependecy) {
-      SML << "Kernel with externally visible dependency "
-          << getName(*CurKernel.Fn) << " defaulting to P0\n";
-      AssignToPartition(0, CurKernel);
-      continue;
-    }
-
-    // Be smart with large kernels to avoid duplicating their dependencies.
-    if (CurKernel.isLarge(LargeKernelThreshold)) {
-      assert(LargeKernelOverlapForMerge >= 0.0f &&
-             LargeKernelOverlapForMerge <= 1.0f);
-      SML << "Large Kernel: " << getName(*CurKernel.Fn)
-          << " - looking for partition with at least "
-          << format("%0.2f", LargeKernelOverlapForMerge * 100) << "% overlap\n";
-
-      bool Assigned = false;
-      for (const auto &[PID, Fns] : enumerate(Partitions)) {
-        float Overlap = calculateOverlap(CurKernel.Dependencies, Fns);
-        SML << "  => " << format("%0.2f", Overlap * 100) << "% overlap with P"
-            << PID << '\n';
-        if (Overlap > LargeKernelOverlapForMerge) {
-          SML << "  selecting P" << PID << '\n';
-          AssignToPartition(PID, CurKernel);
-          Assigned = true;
-        }
-      }
-
-      if (Assigned)
-        continue;
-    }
-
-    // Normal "load-balancing", assign to partition with least pressure.
-    auto [PID, CurCost] = BalancingQueue.back();
-    AssignToPartition(PID, CurKernel);
-  }
-
-  // Work is mostly done now, verify the partioning and add all functions we may
-  // have missed (= unreachable, or we don't understand how they're reached) to
-  // P0.
-  DenseSet<const Function *> AllFunctions;
-  for (const auto &[Idx, Part] : enumerate(Partitions)) {
-    CostType Cost = 0;
-    for (auto *Fn : Part) {
-      // external linkage functions should exclusively be in the first partition
-      // at this stage. In theory, we should only ever see external linkage
-      // functions here if they're kernels, or if they've been added due to a
-      // kernel using indirect calls somewhere in its CallGraph.
-      assert(Idx == 0 || (!Fn->hasExternalLinkage() || isEntryPoint(Fn)));
-      Cost += FnCosts.at(Fn);
-    }
-    SML << "P" << Idx << " has a total cost of " << Cost << " ("
-        << format("%0.2f", (float(Cost) / ModuleCost) * 100)
-        << "% of source module)\n";
-    AllFunctions.insert(Part.begin(), Part.end());
-  }
-
-  // Add missed functions to P0. This will take care of adding things like
-  // external functions with no callers in the module to P0. This should be
-  // fairly rare as AMDGPU internalizes everything in most cases, so unused
-  // internal functions would get removed.
-  for (auto &Fn : M) {
-    if (!Fn.isDeclaration() && !AllFunctions.contains(&Fn)) {
-      SML << getName(Fn) << " has no partition assigned, defaulting to P0\n";
-      Partitions[0].insert(&Fn);
-    }
-  }
-
-  SML << "--Partitioning Done--\n\n";
-
-  return Partitions;
-}
-
-static void externalize(GlobalValue &GV) {
-  if (GV.hasLocalLinkage()) {
-    GV.setLinkage(GlobalValue::ExternalLinkage);
-    GV.setVisibility(GlobalValue::HiddenVisibility);
-  }
-
-  // Unnamed entities must be named consistently between modules. setName will
-  // give a distinct name to each such entity.
-  if (!GV.hasName())
-    GV.setName("__llvmsplit_unnamed");
-}
-} // end anonymous namespace
-
-void llvm::splitAMDGPUModule(
-    const AMDGPUTargetMachine &TM, Module &M, unsigned N,
-    function_ref<void(std::unique_ptr<Module> MPart)> ModuleCallback) {
-
-  SplitModuleLogger SML(M);
-
-  CallGraph CG(M);
-
-  // Externalize functions whose address are taken.
-  //
-  // This is needed because partitioning is purely based on calls, but sometimes
-  // a kernel/function may just look at the address of another local function
-  // and not do anything (no calls). After partitioning, that local function may
-  // end up in a 
diff erent module (so it's just a declaration in the module
-  // where its address is taken), which emits a "undefined hidden symbol" linker
-  // error.
-  //
-  // Additionally, it guides partitioning to not duplicate this function if it's
-  // called directly at some point.
-  for (auto &Fn : M) {
-    if (Fn.hasAddressTaken()) {
-      if (Fn.hasLocalLinkage()) {
-        SML << "[externalize] " << Fn.getName()
-            << " because its address is taken\n";
-      }
-      externalize(Fn);
-    }
-  }
-
-  // Externalize local GVs, which avoids duplicating their initializers, which
-  // in turns helps keep code size in check.
-  if (!NoExternalizeGlobals) {
-    for (auto &GV : M.globals()) {
-      if (GV.hasLocalLinkage())
-        SML << "[externalize] GV " << GV.getName() << '\n';
-      externalize(GV);
-    }
-  }
-
-  // Start by calculating the cost of every function in the module, as well as
-  // the module's overall cost.
-  DenseMap<const Function *, CostType> FnCosts;
-  const CostType ModuleCost = calculateFunctionCosts(SML, TM, M, FnCosts);
-
-  // Gather every kernel into a WorkList, then sort it by descending total cost
-  // of the kernel so the biggest kernels are seen first.
-  SmallVector<KernelWithDependencies> WorkList;
-  for (auto &Fn : M) {
-    if (isEntryPoint(&Fn) && !Fn.isDeclaration())
-      WorkList.emplace_back(SML, CG, FnCosts, &Fn);
-  }
-  sort(WorkList, [&](auto &A, auto &B) {
-    // Sort by total cost, and if the total cost is identical, sort
-    // alphabetically.
-    if (A.TotalCost == B.TotalCost)
-      return A.Fn->getName() < B.Fn->getName();
-    return A.TotalCost > B.TotalCost;
-  });
-
-  if (SML) {
-    SML << "Worklist\n";
-    for (const auto &KWD : WorkList) {
-      SML << "[Kernel] " << getName(*KWD.Fn) << " (totalCost:" << KWD.TotalCost
-          << " indirect:" << KWD.HasIndirectCall
-          << " hasNonDuplicatableDep:" << KWD.HasNonDuplicatableDependecy
-          << ")\n";
-      for (const auto *Dep : KWD.Dependencies)
-        SML << "  [Dep] " << getName(*Dep) << '\n';
-    }
-  }
-
-  // This performs all of the partitioning work.
-  auto Partitions = doPartitioning(SML, M, N, ModuleCost, FnCosts, WorkList);
-  assert(Partitions.size() == N);
-
-  // If we didn't externalize GVs, then local GVs need to be conservatively
-  // imported into every module (including their initializers), and then cleaned
-  // up afterwards.
-  const auto NeedsConservativeImport = [&](const GlobalValue *GV) {
-    // We conservatively import private/internal GVs into every module and clean
-    // them up afterwards.
-    const auto *Var = dyn_cast<GlobalVariable>(GV);
-    return Var && Var->hasLocalLinkage();
-  };
-
-  SML << "Creating " << N << " modules...\n";
-  unsigned TotalFnImpls = 0;
-  for (unsigned I = 0; I < N; ++I) {
-    const auto &FnsInPart = Partitions[I];
-
-    ValueToValueMapTy VMap;
-    std::unique_ptr<Module> MPart(
-        CloneModule(M, VMap, [&](const GlobalValue *GV) {
-          // Functions go in their assigned partition.
-          if (const auto *Fn = dyn_cast<Function>(GV)) {
-// Check we don't import an external linkage function in any
-// partition other than P0.
-#ifndef NDEBUG
-            if (Fn->hasExternalLinkage() && !isEntryPoint(Fn)) {
-              assert((I == 0) == FnsInPart.contains(Fn));
-            }
-#endif
-            return FnsInPart.contains(Fn);
-          }
-
-          if (NeedsConservativeImport(GV))
-            return true;
-
-          // Everything else goes in the first partition.
-          return I == 0;
-        }));
-
-    // Clean-up conservatively imported GVs without any users.
-    for (auto &GV : make_early_inc_range(MPart->globals())) {
-      if (NeedsConservativeImport(&GV) && GV.use_empty())
-        GV.eraseFromParent();
-    }
-
-    unsigned NumAllFns = 0, NumKernels = 0;
-    for (auto &Cur : *MPart) {
-      if (!Cur.isDeclaration()) {
-        ++NumAllFns;
-        if (isEntryPoint(&Cur))
-          ++NumKernels;
-      }
-    }
-    TotalFnImpls += NumAllFns;
-    SML << "  - Module " << I << " with " << NumAllFns << " functions ("
-        << NumKernels << " kernels)\n";
-    ModuleCallback(std::move(MPart));
-  }
-
-  SML << TotalFnImpls << " function definitions across all modules ("
-      << format("%0.2f", (float(TotalFnImpls) / FnCosts.size()) * 100)
-      << "% of original module)\n";
-}

diff  --git a/llvm/lib/Target/AMDGPU/AMDGPUSplitModule.h b/llvm/lib/Target/AMDGPU/AMDGPUSplitModule.h
deleted file mode 100644
index 6171643bd4adc..0000000000000
--- a/llvm/lib/Target/AMDGPU/AMDGPUSplitModule.h
+++ /dev/null
@@ -1,30 +0,0 @@
-//===- AMDGPUSplitModule.h -------------------------------------*- C++ -*-===//
-//
-// 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
-//
-//===----------------------------------------------------------------------===//
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_TARGET_AMDGPUSPLITMODULE_H
-#define LLVM_TARGET_AMDGPUSPLITMODULE_H
-
-#include "llvm/ADT/STLFunctionalExtras.h"
-#include <memory>
-
-namespace llvm {
-
-class Module;
-class AMDGPUTargetMachine;
-
-/// Splits the module M into N linkable partitions. The function ModuleCallback
-/// is called N times passing each individual partition as the MPart argument.
-void splitAMDGPUModule(
-    const AMDGPUTargetMachine &TM, Module &M, unsigned N,
-    function_ref<void(std::unique_ptr<Module> MPart)> ModuleCallback);
-
-} // end namespace llvm
-
-#endif // LLVM_TARGET_AMDGPUSPLITMODULE_H

diff  --git a/llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.cpp b/llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.cpp
index dbbfe34a63863..20329dea60275 100644
--- a/llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.cpp
+++ b/llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.cpp
@@ -21,7 +21,6 @@
 #include "AMDGPUIGroupLP.h"
 #include "AMDGPUMacroFusion.h"
 #include "AMDGPURegBankSelect.h"
-#include "AMDGPUSplitModule.h"
 #include "AMDGPUTargetObjectFile.h"
 #include "AMDGPUTargetTransformInfo.h"
 #include "AMDGPUUnifyDivergentExitNodes.h"
@@ -816,13 +815,6 @@ AMDGPUTargetMachine::getAddressSpaceForPseudoSourceKind(unsigned Kind) const {
   return AMDGPUAS::FLAT_ADDRESS;
 }
 
-bool AMDGPUTargetMachine::splitModule(
-    Module &M, unsigned NumParts,
-    function_ref<void(std::unique_ptr<Module> MPart)> ModuleCallback) const {
-  splitAMDGPUModule(*this, M, NumParts, ModuleCallback);
-  return true;
-}
-
 //===----------------------------------------------------------------------===//
 // GCN Target Machine (SI+)
 //===----------------------------------------------------------------------===//

diff  --git a/llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.h b/llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.h
index 2cfd232483a8a..e48cb8fdc6576 100644
--- a/llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.h
+++ b/llvm/lib/Target/AMDGPU/AMDGPUTargetMachine.h
@@ -73,10 +73,6 @@ class AMDGPUTargetMachine : public LLVMTargetMachine {
   getPredicatedAddrSpace(const Value *V) const override;
 
   unsigned getAddressSpaceForPseudoSourceKind(unsigned Kind) const override;
-
-  bool splitModule(Module &M, unsigned NumParts,
-                   function_ref<void(std::unique_ptr<Module> MPart)>
-                       ModuleCallback) const override;
 };
 
 //===----------------------------------------------------------------------===//

diff  --git a/llvm/lib/Target/AMDGPU/CMakeLists.txt b/llvm/lib/Target/AMDGPU/CMakeLists.txt
index c992352cb78da..ead81b402eb76 100644
--- a/llvm/lib/Target/AMDGPU/CMakeLists.txt
+++ b/llvm/lib/Target/AMDGPU/CMakeLists.txt
@@ -98,7 +98,6 @@ add_llvm_target(AMDGPUCodeGen
   AMDGPURewriteOutArguments.cpp
   AMDGPURewriteUndefForPHI.cpp
   AMDGPUSetWavePriority.cpp
-  AMDGPUSplitModule.cpp
   AMDGPUSubtarget.cpp
   AMDGPUTargetMachine.cpp
   AMDGPUTargetObjectFile.cpp

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/address-taken-externalize-with-call.ll b/llvm/test/tools/llvm-split/AMDGPU/address-taken-externalize-with-call.ll
deleted file mode 100644
index 8b76237efa325..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/address-taken-externalize-with-call.ll
+++ /dev/null
@@ -1,46 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa -amdgpu-module-splitting-large-kernel-threshold=0
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; 3 kernels:
-;   - A does a direct call to HelperA
-;   - B is storing @HelperA
-;   - C does a direct call to HelperA
-;
-; The helper functions will get externalized, which will force A and C into P0 as
-; external functions cannot be duplicated.
-
-; CHECK0: define hidden void @HelperA()
-; CHECK0: define amdgpu_kernel void @A()
-; CHECK0: declare amdgpu_kernel void @B(ptr)
-; CHECK0: define amdgpu_kernel void @C()
-
-; CHECK1: declare hidden void @HelperA()
-; CHECK1: declare amdgpu_kernel void @A()
-; CHECK1: declare amdgpu_kernel void @B(ptr)
-; CHECK1: declare amdgpu_kernel void @C()
-
-; CHECK2: declare hidden void @HelperA()
-; CHECK2: declare amdgpu_kernel void @A()
-; CHECK2: define amdgpu_kernel void @B(ptr %dst)
-; CHECK2: declare amdgpu_kernel void @C()
-
-define internal void @HelperA() {
-  ret void
-}
-
-define amdgpu_kernel void @A() {
-  call void @HelperA()
-  ret void
-}
-
-define amdgpu_kernel void @B(ptr %dst) {
-  store ptr @HelperA, ptr %dst
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  call void @HelperA()
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/address-taken-externalize.ll b/llvm/test/tools/llvm-split/AMDGPU/address-taken-externalize.ll
deleted file mode 100644
index 46d7d9783aeae..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/address-taken-externalize.ll
+++ /dev/null
@@ -1,37 +0,0 @@
-; RUN: llvm-split -o %t %s -j 2 -mtriple amdgcn-amd-amdhsa -amdgpu-module-splitting-large-kernel-threshold=0
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-
-; 2 kernels:
-;   - A is isolated
-;   - B is storing @HelperA/B's address
-;
-; The helper functions should get externalized (become hidden w/ external linkage)
-
-; CHECK0: define hidden void @HelperA()
-; CHECK0: define hidden void @HelperB()
-; CHECK0: define amdgpu_kernel void @A()
-; CHECK0: declare amdgpu_kernel void @B(i1, ptr)
-
-; CHECK1: declare hidden void @HelperA()
-; CHECK1: declare hidden void @HelperB()
-; CHECK1: declare amdgpu_kernel void @A()
-; CHECK1: define amdgpu_kernel void @B(i1 %cond, ptr %dst)
-
-define internal void @HelperA() {
-  ret void
-}
-
-define internal void @HelperB() {
-  ret void
-}
-
-define amdgpu_kernel void @A() {
-  ret void
-}
-
-define amdgpu_kernel void @B(i1 %cond, ptr %dst) {
-  %addr = select i1 %cond, ptr @HelperA, ptr @HelperB
-  store ptr %addr, ptr %dst
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/debug-name-hiding.ll b/llvm/test/tools/llvm-split/AMDGPU/debug-name-hiding.ll
deleted file mode 100644
index 6a07ed51ba1be..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/debug-name-hiding.ll
+++ /dev/null
@@ -1,20 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa -debug -amdgpu-module-splitting-log-private 2>&1 | FileCheck %s --implicit-check-not=MyCustomKernel
-; REQUIRES: asserts
-
-; SHA256 of the kernel names.
-
-; CHECK: a097723d21cf9f35d90e6fb7881995ac8c398b3366a6c97efc657404f9fe301c
-; CHECK: 626bc23242de8fcfda7f0e66318d29455c081df6b5380e64d14703c95fcbcd59
-; CHECK: c38d90a7ca71dc5d694bb9e093dadcdedfc4cb4adf7ed7e46d42fe95a0b4ef55
-
-define amdgpu_kernel void @MyCustomKernel0() {
-  ret void
-}
-
-define amdgpu_kernel void @MyCustomKernel1() {
-  ret void
-}
-
-define amdgpu_kernel void @MyCustomKernel2() {
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-alias-dependencies.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-alias-dependencies.ll
deleted file mode 100644
index c2746d1398924..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-alias-dependencies.ll
+++ /dev/null
@@ -1,45 +0,0 @@
-; RUN: llvm-split -o %t %s -j 2 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-
-; 3 kernels:
-;   - A calls nothing
-;   - B calls @PerryThePlatypus
-;   - C calls @Perry, an alias of @PerryThePlatypus
-;
-; We should see through the alias and put B/C in the same
-; partition.
-;
-; Additionally, @PerryThePlatypus gets externalized as
-; the alias counts as taking its address.
-
-; CHECK0-NOT: define
-; CHECK0: @Perry = internal alias ptr (), ptr @PerryThePlatypus
-; CHECK0: define hidden void @PerryThePlatypus()
-; CHECK0: define amdgpu_kernel void @B
-; CHECK0: define amdgpu_kernel void @C
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define amdgpu_kernel void @A
-; CHECK1-NOT: define
-
- at Perry = internal alias ptr(), ptr @PerryThePlatypus
-
-define internal void @PerryThePlatypus() {
-  ret void
-}
-
-define amdgpu_kernel void @A() {
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  call void @PerryThePlatypus()
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  call void @Perry()
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-cost-ranking.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-cost-ranking.ll
deleted file mode 100644
index 4635264aefb39..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-cost-ranking.ll
+++ /dev/null
@@ -1,54 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; 3 kernels with each their own dependencies should go into 3
-; distinct partitions. The most expensive kernel should be
-; seen first and go into the last partition.
-
-; CHECK0-NOT: define
-; CHECK0: define amdgpu_kernel void @C
-; CHECK0: define internal void @HelperC
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define amdgpu_kernel void @A
-; CHECK1: define internal void @HelperA
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define amdgpu_kernel void @B
-; CHECK2: define internal void @HelperB
-; CHECK2-NOT: define
-
-
-define amdgpu_kernel void @A() {
-  call void @HelperA()
-  ret void
-}
-
-define internal void @HelperA() {
-  ret void
-}
-
-define amdgpu_kernel void @B(ptr %x) {
-  store i64 42, ptr %x
-  store i64 43, ptr %x
-  store i64 44, ptr %x
-  call void @HelperB()
-  ret void
-}
-
-define internal void @HelperB() {
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  call void @HelperC()
-  ret void
-}
-
-define internal void @HelperC() {
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependencies.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-dependencies.ll
deleted file mode 100644
index bea527f15bbaa..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependencies.ll
+++ /dev/null
@@ -1,50 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; 3 kernels with each their own dependencies should go into 3
-; distinct partitions.
-
-; CHECK0-NOT: define
-; CHECK0: define amdgpu_kernel void @C
-; CHECK0: define internal void @HelperC
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define amdgpu_kernel void @B
-; CHECK1: define internal void @HelperB
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define amdgpu_kernel void @A
-; CHECK2: define internal void @HelperA
-; CHECK2-NOT: define
-
-
-define amdgpu_kernel void @A() {
-  call void @HelperA()
-  ret void
-}
-
-define internal void @HelperA() {
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  call void @HelperB()
-  ret void
-}
-
-define internal void @HelperB() {
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  call void @HelperC()
-  ret void
-}
-
-define internal void @HelperC() {
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-duplication.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-duplication.ll
deleted file mode 100644
index 64839f8d8456a..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-duplication.ll
+++ /dev/null
@@ -1,41 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; 3 kernels share a common helper, that helper should be
-; cloned in all partitions.
-
-; CHECK0-NOT: define
-; CHECK0: define internal void @Helper
-; CHECK0: define amdgpu_kernel void @C
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define internal void @Helper
-; CHECK1: define amdgpu_kernel void @B
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define internal void @Helper
-; CHECK2: define amdgpu_kernel void @A
-; CHECK2-NOT: define
-
-define internal void @Helper() {
-  ret void
-}
-
-define amdgpu_kernel void @A() {
-  call void @Helper()
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  call void @Helper()
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  call void @Helper()
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-external.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-external.ll
deleted file mode 100644
index 435e97a581340..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-external.ll
+++ /dev/null
@@ -1,64 +0,0 @@
-; RUN: llvm-split -o %t %s -j 4 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-; RUN: llvm-dis -o - %t3 | FileCheck --check-prefix=CHECK3 %s
-
-; Both overridable helper should go in P0.
-
-; CHECK0-NOT: define
-; CHECK0: define available_externally void @OverridableHelper0()
-; CHECK0: define internal void @OverridableHelper1()
-; CHECK0: define amdgpu_kernel void @A
-; CHECK0: define amdgpu_kernel void @B
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define internal void @PrivateHelper1()
-; CHECK2: define amdgpu_kernel void @D
-; CHECK2-NOT: define
-
-; CHECK3-NOT: define
-; CHECK3: define internal void @PrivateHelper0()
-; CHECK3: define amdgpu_kernel void @C
-; CHECK3-NOT: define
-
-define available_externally void @OverridableHelper0() {
-  ret void
-}
-
-define internal void @OverridableHelper1() #0 {
-  ret void
-}
-
-define internal void @PrivateHelper0() {
-  ret void
-}
-
-define internal void @PrivateHelper1() {
-  ret void
-}
-
-define amdgpu_kernel void @A() {
-  call void @OverridableHelper0()
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  call void @OverridableHelper1()
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  call void @PrivateHelper0()
-  ret void
-}
-
-define amdgpu_kernel void @D() {
-  call void @PrivateHelper1()
-  ret void
-}
-
-attributes #0 = { nobuiltin }

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-indirect.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-indirect.ll
deleted file mode 100644
index 9701ac35ce54e..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-indirect.ll
+++ /dev/null
@@ -1,76 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; We have 4 kernels:
-;   - Each kernel has an internal helper
-;   - @A and @B's helpers does an indirect call.
-;
-; We default to putting A/B in P0, alongside a copy
-; of all helpers who have their address taken.
-; The other kernels can still go into separate partitions.
-
-; CHECK0-NOT: define
-; CHECK0: define hidden void @HelperA
-; CHECK0: define hidden void @HelperB
-; CHECK0: define hidden void @CallCandidate
-; CHECK0-NOT: define {{.*}} @HelperC
-; CHECK0-NOT: define {{.*}} @HelperD
-; CHECK0: define amdgpu_kernel void @A
-; CHECK0: define amdgpu_kernel void @B
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define internal void @HelperD
-; CHECK1: define amdgpu_kernel void @D
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define internal void @HelperC
-; CHECK2: define amdgpu_kernel void @C
-; CHECK2-NOT: define
-
- at addrthief = global [3 x ptr] [ptr @HelperA, ptr @HelperB, ptr @CallCandidate]
-
-define internal void @HelperA(ptr %call) {
-  call void %call()
-  ret void
-}
-
-define internal void @HelperB(ptr %call) {
-  call void %call()
-  ret void
-}
-
-define internal void @CallCandidate() {
-  ret void
-}
-
-define internal void @HelperC() {
-  ret void
-}
-
-define internal void @HelperD() {
-  ret void
-}
-
-define amdgpu_kernel void @A(ptr %call) {
-  call void @HelperA(ptr %call)
-  ret void
-}
-
-define amdgpu_kernel void @B(ptr %call) {
-  call void @HelperB(ptr %call)
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  call void @HelperC()
-  ret void
-}
-
-define amdgpu_kernel void @D() {
-  call void @HelperD()
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-overridable.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-overridable.ll
deleted file mode 100644
index dc2c5c3c07bee..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-dependency-overridable.ll
+++ /dev/null
@@ -1,40 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; CHECK0-NOT: define
-; CHECK0: define void @ExternalHelper
-; CHECK0: define amdgpu_kernel void @A
-; CHECK0: define amdgpu_kernel void @B
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define amdgpu_kernel void @D
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define amdgpu_kernel void @C
-; CHECK2-NOT: define
-
-define void @ExternalHelper() {
-  ret void
-}
-
-define amdgpu_kernel void @A() {
-  call void @ExternalHelper()
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  call void @ExternalHelper()
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  ret void
-}
-
-define amdgpu_kernel void @D() {
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-global-variables-noexternal.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-global-variables-noexternal.ll
deleted file mode 100644
index 0fc76934afc54..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-global-variables-noexternal.ll
+++ /dev/null
@@ -1,42 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa -amdgpu-module-splitting-no-externalize-globals
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; 3 kernels use private/internal global variables.
-; The GVs should be copied in each partition as needed.
-
-; CHECK0-NOT: define
-; CHECK0: @bar = internal constant ptr
-; CHECK0: define amdgpu_kernel void @C
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: @foo = private constant ptr
-; CHECK1: define amdgpu_kernel void @A
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: @foo = private constant ptr
-; CHECK2: @bar = internal constant ptr
-; CHECK2: define amdgpu_kernel void @B
-; CHECK2-NOT: define
-
- at foo = private constant ptr poison
- at bar = internal constant ptr poison
-
-define amdgpu_kernel void @A() {
-  store i32 42, ptr @foo
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  store i32 42, ptr @foo
-  store i32 42, ptr @bar
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  store i32 42, ptr @bar
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-global-variables.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-global-variables.ll
deleted file mode 100644
index 7564662e7c7c0..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-global-variables.ll
+++ /dev/null
@@ -1,44 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; 3 kernels use private/internal global variables.
-; The GVs should be copied in each partition as needed.
-
-; CHECK0-NOT: define
-; CHECK0: @foo = hidden constant ptr poison
-; CHECK0: @bar = hidden constant ptr poison
-; CHECK0: define amdgpu_kernel void @C
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: @foo = external hidden constant ptr{{$}}
-; CHECK1: @bar = external hidden constant ptr{{$}}
-; CHECK1: define amdgpu_kernel void @A
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: @foo = external hidden constant ptr{{$}}
-; CHECK2: @bar = external hidden constant ptr{{$}}
-; CHECK2: define amdgpu_kernel void @B
-; CHECK2-NOT: define
-
- at foo = private constant ptr poison
- at bar = internal constant ptr poison
-
-define amdgpu_kernel void @A() {
-  store i32 42, ptr @foo
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  store i32 42, ptr @foo
-  store i32 42, ptr @bar
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  store i32 42, ptr @bar
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-load-balancing.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-load-balancing.ll
deleted file mode 100644
index 5dfb95c5fc660..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-load-balancing.ll
+++ /dev/null
@@ -1,75 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; Test load balancing logic with 6 kernels.
-;
-; Kernels go from most expensive (A == 6) to least expensive (F == 1)
-;
-; Load balancing should work like this (current partition cost is in parens)
-;
-; Initial    -> [P0(0), P1(0), P2(0)]
-;
-; A(6) goes in 2 -> [P2(6), P0(0), P1(0)]
-; B(5) goes in 1 -> [P2(6), P1(5), P0(4)]
-; C(4) goes in 0 -> [P2(6), P1(5), P0(4)]
-
-; D(3) goes in 0 -> [P0(7), P2(6), P1(5)]
-; E(2) goes in 1 -> [P0(7), P1(7), P2(6)]
-; F(1) goes in 2 -> [P0(7), P1(7), P2(7)]
-
-; CHECK0-NOT: define
-; CHECK0: define amdgpu_kernel void @C
-; CHECK0: define amdgpu_kernel void @D
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define amdgpu_kernel void @B
-; CHECK1: define amdgpu_kernel void @E
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define amdgpu_kernel void @A
-; CHECK2: define amdgpu_kernel void @F
-; CHECK2-NOT: define
-
-
-define amdgpu_kernel void @A(ptr %x) {
-  store i64 42, ptr %x
-  store i64 43, ptr %x
-  store i64 44, ptr %x
-  store i64 45, ptr %x
-  store i64 46, ptr %x
-  ret void
-}
-
-define amdgpu_kernel void @B(ptr %x) {
-  store i64 42, ptr %x
-  store i64 43, ptr %x
-  store i64 44, ptr %x
-  store i64 45, ptr %x
-  ret void
-}
-
-define amdgpu_kernel void @C(ptr %x) {
-  store i64 42, ptr %x
-  store i64 43, ptr %x
-  store i64 44, ptr %x
-  ret void
-}
-
-define amdgpu_kernel void @D(ptr %x) {
-  store i64 42, ptr %x
-  store i64 43, ptr %x
-  ret void
-}
-
-define amdgpu_kernel void @E(ptr %x) {
-  store i64 42, ptr %x
-  ret void
-}
-
-define amdgpu_kernel void @F() {
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/kernels-no-dependencies.ll b/llvm/test/tools/llvm-split/AMDGPU/kernels-no-dependencies.ll
deleted file mode 100644
index 8959acfcae542..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/kernels-no-dependencies.ll
+++ /dev/null
@@ -1,39 +0,0 @@
-; RUN: llvm-split -o %t %s -j 4 -mtriple amdgcn-amd-amdhsa
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-; RUN: llvm-dis -o - %t3 | FileCheck --check-prefix=CHECK3 %s
-
-; Check that 4 independent kernels get put into 4 
diff erent partitions.
-
-; CHECK0-NOT: define
-; CHECK0: define amdgpu_kernel void @D
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define amdgpu_kernel void @C
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define amdgpu_kernel void @B
-; CHECK2-NOT: define
-
-; CHECK3-NOT: define
-; CHECK3: define amdgpu_kernel void @A
-; CHECK3-NOT: define
-
-define amdgpu_kernel void @A() {
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  ret void
-}
-
-define amdgpu_kernel void @D() {
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/large-kernels-merging.ll b/llvm/test/tools/llvm-split/AMDGPU/large-kernels-merging.ll
deleted file mode 100644
index 4fdbac7d17897..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/large-kernels-merging.ll
+++ /dev/null
@@ -1,98 +0,0 @@
-; RUN: llvm-split -o %t %s -j 3 -mtriple amdgcn-amd-amdhsa -amdgpu-module-splitting-large-kernel-threshold=1.2 -amdgpu-module-splitting-large-kernel-merge-overlap=0.5
-; RUN: llvm-dis -o - %t0 | FileCheck --check-prefix=CHECK0 %s
-; RUN: llvm-dis -o - %t1 | FileCheck --check-prefix=CHECK1 %s
-; RUN: llvm-dis -o - %t2 | FileCheck --check-prefix=CHECK2 %s
-
-; RUN: llvm-split -o %t.nolarge %s -j 3 -mtriple amdgcn-amd-amdhsa -amdgpu-module-splitting-large-kernel-threshold=0
-; RUN: llvm-dis -o - %t.nolarge0 | FileCheck --check-prefix=NOLARGEKERNELS-CHECK0 %s
-; RUN: llvm-dis -o - %t.nolarge1 | FileCheck --check-prefix=NOLARGEKERNELS-CHECK1 %s
-; RUN: llvm-dis -o - %t.nolarge2 | FileCheck --check-prefix=NOLARGEKERNELS-CHECK2 %s
-
-; 2 kernels (A/B) are large and share all their dependencies.
-; They should go in the same partition, the remaining kernel should
-; go somewhere else, and one partition should be empty.
-;
-; Also check w/o large kernels processing to verify they are indeed handled
-; 
diff erently.
-
-; CHECK0-NOT: define
-
-; CHECK1-NOT: define
-; CHECK1: define internal void @HelperC()
-; CHECK1: define amdgpu_kernel void @C
-; CHECK1-NOT: define
-
-; CHECK2-NOT: define
-; CHECK2: define internal void @large2()
-; CHECK2: define internal void @large1()
-; CHECK2: define internal void @large0()
-; CHECK2: define internal void @HelperA()
-; CHECK2: define internal void @HelperB()
-; CHECK2: define amdgpu_kernel void @A
-; CHECK2: define amdgpu_kernel void @B
-; CHECK2-NOT: define
-
-; NOLARGEKERNELS-CHECK0-NOT: define
-; NOLARGEKERNELS-CHECK0: define internal void @HelperC()
-; NOLARGEKERNELS-CHECK0: define amdgpu_kernel void @C
-; NOLARGEKERNELS-CHECK0-NOT: define
-
-; NOLARGEKERNELS-CHECK1: define internal void @large2()
-; NOLARGEKERNELS-CHECK1: define internal void @large1()
-; NOLARGEKERNELS-CHECK1: define internal void @large0()
-; NOLARGEKERNELS-CHECK1: define internal void @HelperB()
-; NOLARGEKERNELS-CHECK1: define amdgpu_kernel void @B
-
-; NOLARGEKERNELS-CHECK2: define internal void @large2()
-; NOLARGEKERNELS-CHECK2: define internal void @large1()
-; NOLARGEKERNELS-CHECK2: define internal void @large0()
-; NOLARGEKERNELS-CHECK2: define internal void @HelperA()
-; NOLARGEKERNELS-CHECK2: define amdgpu_kernel void @A
-
-define internal void @large2() {
-  store volatile i32 42, ptr null
-  call void @large2()
-  ret void
-}
-
-define internal void @large1() {
-  call void @large1()
-  call void @large2()
-  ret void
-}
-
-define internal void @large0() {
-  call void @large0()
-  call void @large1()
-  call void @large2()
-  ret void
-}
-
-define internal void @HelperA() {
-  call void @large0()
-  ret void
-}
-
-define internal void @HelperB() {
-  call void @large0()
-  ret void
-}
-
-define amdgpu_kernel void @A() {
-  call void @HelperA()
-  ret void
-}
-
-define amdgpu_kernel void @B() {
-  call void @HelperB()
-  ret void
-}
-
-define internal void @HelperC() {
-  ret void
-}
-
-define amdgpu_kernel void @C() {
-  call void @HelperC()
-  ret void
-}

diff  --git a/llvm/test/tools/llvm-split/AMDGPU/lit.local.cfg b/llvm/test/tools/llvm-split/AMDGPU/lit.local.cfg
deleted file mode 100644
index 6154a6c1c9061..0000000000000
--- a/llvm/test/tools/llvm-split/AMDGPU/lit.local.cfg
+++ /dev/null
@@ -1,2 +0,0 @@
-if not "AMDGPU" in config.root.targets:
-  config.unsupported = True


        


More information about the llvm-branch-commits mailing list