diff --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td index ec38231f906eb..c77a42ba033a9 100644 --- a/clang/include/clang/Driver/Options.td +++ b/clang/include/clang/Driver/Options.td @@ -1421,6 +1421,16 @@ def fhip_emit_relocatable : Flag<["-"], "fhip-emit-relocatable">, HelpText<"Compile HIP source to relocatable">; def fno_hip_emit_relocatable : Flag<["-"], "fno-hip-emit-relocatable">, HelpText<"Do not override toolchain to compile HIP source to relocatable">; +def use_experimental_spirv_backend + : Flag<["-"], "use-experimental-spirv-backend">, + Group, + Flags<[HelpHidden]>, + HelpText<"Use experimental SPIRV backend for compilation ">; +def no_use_experimental_spirv_backend + : Flag<["-"], "no-use-experimental-spirv-backend">, + Group, + Flags<[HelpHidden]>, + HelpText<"Do not use experimental SPIRV backend for compilation ">; } // Clang specific/exclusive options for OpenACC. diff --git a/clang/lib/Driver/ToolChains/HIPAMD.cpp b/clang/lib/Driver/ToolChains/HIPAMD.cpp index c0c8afec07264..927f3c0abfea3 100644 --- a/clang/lib/Driver/ToolChains/HIPAMD.cpp +++ b/clang/lib/Driver/ToolChains/HIPAMD.cpp @@ -175,15 +175,33 @@ void AMDGCN::Linker::constructLinkAndEmitSpirvCommand( constructLlvmLinkCommand(C, JA, Inputs, LinkedBCFile, Args); - // Emit SPIR-V binary. - llvm::opt::ArgStringList TrArgs{ - "--spirv-max-version=1.6", - "--spirv-ext=+all", - "--spirv-allow-unknown-intrinsics", - "--spirv-lower-const-expr", - "--spirv-preserve-auxdata", - "--spirv-debug-info-version=nonsemantic-shader-200"}; - SPIRV::constructTranslateCommand(C, *this, JA, Output, LinkedBCFile, TrArgs); + bool UseSPIRVBackend = Args.hasFlag( + options::OPT_use_experimental_spirv_backend, + options::OPT_no_use_experimental_spirv_backend, /*Default=*/false); + + // Emit SPIR-V binary either using the SPIRV backend or the translator. + if (UseSPIRVBackend) { + llvm::opt::ArgStringList CmdArgs; + const char *Triple = + C.getArgs().MakeArgString("-triple=spirv64-amd-amdhsa"); + CmdArgs.append({"-cc1", Triple, "-emit-obj", LinkedBCFile.getFilename(), + "-o", Output.getFilename()}); + const char *Exec = getToolChain().getDriver().getClangProgramPath(); + C.addCommand(std::make_unique(JA, *this, + ResponseFileSupport::None(), Exec, + CmdArgs, LinkedBCFile, Output)); + } else { + // Use the SPIRV translator for code gen. + llvm::opt::ArgStringList TrArgs{ + "--spirv-max-version=1.6", + "--spirv-ext=+all", + "--spirv-allow-unknown-intrinsics", + "--spirv-lower-const-expr", + "--spirv-preserve-auxdata", + "--spirv-debug-info-version=nonsemantic-shader-200"}; + SPIRV::constructTranslateCommand(C, *this, JA, Output, LinkedBCFile, + TrArgs); + } } // For amdgcn the inputs of the linker job are device bitcode and output is diff --git a/clang/test/Driver/hip-spirv-backend-opt.c b/clang/test/Driver/hip-spirv-backend-opt.c new file mode 100644 index 0000000000000..57b8d678951f6 --- /dev/null +++ b/clang/test/Driver/hip-spirv-backend-opt.c @@ -0,0 +1,12 @@ +// This test case validates the behavior of -use-experimental-spirv-backend + +// Test that -use-experimental-spirv-backend calls clang -cc1 with the SPIRV triple. +// RUN: %clang -x hip %s --cuda-device-only --offload-arch=amdgcnspirv -use-experimental-spirv-backend -nogpuinc -nogpulib -### 2>&1 | FileCheck %s --check-prefix=CHECK-SPIRV-BACKEND +// CHECK-SPIRV-BACKEND: "{{.*}}clang{{.*}}" "-cc1" "{{.*-triple=spirv64-amd-amdhsa}}" + +// Test that -no-use-experimental-spirv-backend calls the SPIRV translator +// RUN: %clang -x hip %s --cuda-device-only --offload-arch=amdgcnspirv -no-use-experimental-spirv-backend -nogpuinc -nogpulib -### 2>&1 | FileCheck %s --check-prefix=CHECK-SPIRV-TRANSLATOR +// CHECK-SPIRV-TRANSLATOR: "{{.*llvm-spirv.*}}" "{{--spirv-max-version=[0-9]+\.[0-9]}}" + +// Test that by default we use the translator +// RUN: %clang -x hip %s --cuda-device-only --offload-arch=amdgcnspirv -nogpuinc -nogpulib -### 2>&1 | FileCheck %s --check-prefix=CHECK-SPIRV-TRANSLATOR