Skip to content

Commit 5012ee1

Browse files
committed
[GPU] Fix family-conditional PTX compilation.
1 parent 2c9f893 commit 5012ee1

5 files changed

Lines changed: 50 additions & 15 deletions

File tree

xla/service/gpu/llvm_gpu_backend/BUILD

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -87,7 +87,6 @@ cc_library(
8787
"//xla/service/gpu:metrics",
8888
"//xla/service/llvm_ir:llvm_command_line_options",
8989
"//xla/stream_executor:device_description",
90-
"//xla/stream_executor:semantic_version",
9190
"//xla/stream_executor/cuda:cuda_compute_capability",
9291
"//xla/stream_executor/cuda:subprocess_compilation",
9392
"//xla/tsl/platform:env",

xla/service/gpu/llvm_gpu_backend/nvptx_backend.cc

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@ limitations under the License.
2020
#include <functional>
2121
#include <memory>
2222
#include <string>
23-
#include <variant>
2423
#include <vector>
2524

2625
#include "absl/base/call_once.h"
@@ -30,7 +29,6 @@ limitations under the License.
3029
#include "absl/strings/str_cat.h"
3130
#include "absl/strings/str_format.h"
3231
#include "xla/tsl/platform/status_macros.h"
33-
#include "third_party/gpus/cuda/include/cuda.h"
3432
#include "llvm/ADT/FloatingPointMode.h"
3533
#include "llvm/Analysis/CGSCCPassManager.h"
3634
#include "llvm/Analysis/LazyCallGraph.h"
@@ -59,6 +57,7 @@ limitations under the License.
5957
#include "llvm/Transforms/IPO/AlwaysInliner.h"
6058
#include "llvm/Transforms/IPO/Internalize.h"
6159
#include "llvm/Transforms/Scalar.h"
60+
#include "third_party/gpus/cuda/include/cuda.h"
6261
#include "xla/service/gpu/llvm_gpu_backend/gpu_backend_lib.h"
6362
#include "xla/service/gpu/llvm_gpu_backend/load_ir_module.h"
6463
#include "xla/service/gpu/llvm_gpu_backend/nvptx_libdevice_path.h"
@@ -239,7 +238,13 @@ std::vector<std::string> GetNVPTXBackendOptions(
239238
return backend_llvm_opts;
240239
}
241240

242-
std::string GetSmName(se::CudaComputeCapability compute_capability) {
241+
constexpr se::CudaComputeCapability kSupportedVersions[] = {
242+
{12, 1}, {12, 0}, {11, 0}, {10, 3}, {10, 0}, {9, 0}, {8, 9}, {8, 7},
243+
{8, 6}, {8, 0}, {7, 5}, {7, 2}, {7, 0}, {6, 2}, {6, 1}, {6, 0},
244+
{5, 3}, {5, 2}, {5, 0}, {3, 7}, {3, 5}, {3, 2}, {3, 0}};
245+
246+
se::CudaComputeCapability ResolveSupportedComputeCapability(
247+
se::CudaComputeCapability compute_capability) {
243248
using CudaComputeCapabilities =
244249
se::CudaComputeCapability::CudaComputeCapabilities;
245250

@@ -248,10 +253,6 @@ std::string GetSmName(se::CudaComputeCapability compute_capability) {
248253
se::CudaComputeCapability::FeatureExtension::kNone;
249254
// If the current compute capability isn't known, fallback to the
250255
// most recent version before it.
251-
constexpr stream_executor::CudaComputeCapability kSupportedVersions[] = {
252-
{12, 1}, {12, 0}, {11, 0}, {10, 3}, {10, 0}, {9, 0}, {8, 9}, {8, 7},
253-
{8, 6}, {8, 0}, {7, 5}, {7, 2}, {7, 0}, {6, 2}, {6, 1}, {6, 0},
254-
{5, 3}, {5, 2}, {5, 0}, {3, 7}, {3, 5}, {3, 2}, {3, 0}};
255256
// Initialize to the least supported version, which acts as a safe fallback
256257
auto target_compute_capability =
257258
kSupportedVersions[std::size(kSupportedVersions) - 1];
@@ -284,6 +285,13 @@ std::string GetSmName(se::CudaComputeCapability compute_capability) {
284285
se::CudaComputeCapability::FeatureExtension::kFamilyCompatibleFeatures;
285286
}
286287

288+
return target_compute_capability;
289+
}
290+
291+
std::string GetSmName(se::CudaComputeCapability compute_capability) {
292+
se::CudaComputeCapability target_compute_capability =
293+
ResolveSupportedComputeCapability(compute_capability);
294+
287295
// If the current CC isn't supported by LLVM and it is newer then
288296
// the max supported LLVM version, do not warn about it. The end
289297
// user can't do anything about this. E.g., PTX compiled for SM75 will

xla/service/gpu/llvm_gpu_backend/nvptx_backend.h

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,13 +24,20 @@ limitations under the License.
2424
#include "absl/status/statusor.h"
2525
#include "llvm/IR/Module.h"
2626
#include "llvm/Target/TargetMachine.h"
27-
#include "xla/service/gpu/llvm_gpu_backend/ptx_version_util.h"
27+
#include "xla/stream_executor/cuda/cuda_compute_capability.h"
2828
#include "xla/stream_executor/device_description.h"
29-
#include "xla/stream_executor/semantic_version.h"
3029
#include "xla/xla.pb.h"
3130

3231
namespace xla::gpu::nvptx {
3332

33+
// Resolves the compute capability that XLA actually compiles for given the
34+
// compute capability of the target device. If the device's compute capability
35+
// is not directly supported by the bundled LLVM/ptxas, this returns the most
36+
// advanced supported compute capability that the device can run, potentially
37+
// with the family ("f") feature extension enabled.
38+
stream_executor::CudaComputeCapability ResolveSupportedComputeCapability(
39+
stream_executor::CudaComputeCapability compute_capability);
40+
3441
// Gets the GPU name as it's known to LLVM for a given compute
3542
// capability. If we see an unrecognized compute capability, we
3643
// return the highest one that is known and below the selected device.

xla/service/gpu/llvm_gpu_backend/nvptx_backend_test.cc

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,27 @@ TEST(UtilsTest, TestGetSmName) {
6464
ASSERT_EQ(nvptx::GetSmName(se::CudaComputeCapability{13, 0}), "sm_121");
6565
}
6666

67+
TEST(UtilsTest, UnknownCapabilityFallsBackToFamilyCompatible) {
68+
using FeatureExtension = se::CudaComputeCapability::FeatureExtension;
69+
// Directly supported compute capabilities keep their feature extension.
70+
EXPECT_EQ(nvptx::ResolveSupportedComputeCapability(se::CudaComputeCapability{
71+
10, 0, FeatureExtension::kAcceleratedFeatures}),
72+
(se::CudaComputeCapability{
73+
10, 0, FeatureExtension::kAcceleratedFeatures}));
74+
// An unknown compute capability within a known major version falls back to
75+
// the latest supported minor version with the family compatible extension.
76+
// This mirrors a yet-unreleased device (e.g. sm_1099a) where ptxas only knows
77+
// about sm_103f.
78+
EXPECT_EQ(nvptx::ResolveSupportedComputeCapability(se::CudaComputeCapability{
79+
10, 99, FeatureExtension::kAcceleratedFeatures}),
80+
(se::CudaComputeCapability{
81+
10, 3, FeatureExtension::kFamilyCompatibleFeatures}));
82+
// When no family-compatible extension is available, don't use any.
83+
EXPECT_EQ(nvptx::ResolveSupportedComputeCapability(se::CudaComputeCapability{
84+
9, 99, FeatureExtension::kAcceleratedFeatures}),
85+
(se::CudaComputeCapability{9, 0, FeatureExtension::kNone}));
86+
}
87+
6788
using VersionPair = std::pair<se::SemanticVersion, se::SemanticVersion>;
6889
using PtxVersionFromCudaVersionTest = ::testing::TestWithParam<VersionPair>;
6990

xla/service/gpu/nvptx_compiler.cc

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -558,8 +558,8 @@ NVPTXCompiler::CompileTargetBinary(
558558
se::cuda::CompilationOptions compilation_options =
559559
PtxCompileOptionsFromDebugOptions(module_config.debug_options());
560560

561-
se::CudaComputeCapability cc =
562-
*device_description.gpu_compute_capability().cuda_compute_capability();
561+
se::CudaComputeCapability cc = nvptx::ResolveSupportedComputeCapability(
562+
*device_description.gpu_compute_capability().cuda_compute_capability());
563563

564564
// This may print multiple lines per HLO compilation because of the
565565
// parallelized compilation of LLVM modules.
@@ -620,8 +620,8 @@ absl::StatusOr<std::vector<uint8_t>> NVPTXCompiler::LinkModules(
620620
return std::vector<uint8_t>{};
621621
}
622622

623-
auto cc =
624-
device_description.gpu_compute_capability().cuda_compute_capability();
623+
se::CudaComputeCapability cc = nvptx::ResolveSupportedComputeCapability(
624+
*device_description.gpu_compute_capability().cuda_compute_capability());
625625

626626
ASSIGN_OR_RETURN(const se::cuda::CompilationProvider* compilation_provider,
627627
GetCompilationProvider(debug_options, stream_exec));
@@ -640,7 +640,7 @@ absl::StatusOr<std::vector<uint8_t>> NVPTXCompiler::LinkModules(
640640
<< compilation_provider->name();
641641
ASSIGN_OR_RETURN(
642642
se::cuda::Assembly assembly,
643-
compilation_provider->CompileAndLink(*cc, inputs, compilation_options));
643+
compilation_provider->CompileAndLink(cc, inputs, compilation_options));
644644

645645
return std::move(assembly.cubin);
646646
}

0 commit comments

Comments
 (0)