https://github.com/AdityaSinha149 updated https://github.com/llvm/llvm-project/pull/217582
>From 5f12b79e8a12302d75bd68d661fb2a94afa2021d Mon Sep 17 00:00:00 2001 From: AdityaSinha149 <[email protected]> Date: Wed, 19 Aug 2026 22:51:56 +0530 Subject: [PATCH 1/4] [clang-repl] Hip environment initialized --- clang/include/clang/Interpreter/Interpreter.h | 21 ++++-- clang/lib/Interpreter/Interpreter.cpp | 52 ++++++++------- .../test/Interpreter/HIP/hip-environment.hip | 8 +++ clang/tools/clang-repl/ClangRepl.cpp | 65 +++++++++++++------ 4 files changed, 97 insertions(+), 49 deletions(-) create mode 100644 clang/test/Interpreter/HIP/hip-environment.hip diff --git a/clang/include/clang/Interpreter/Interpreter.h b/clang/include/clang/Interpreter/Interpreter.h index c2622b23d5d9c..757e74e3bafb8 100644 --- a/clang/include/clang/Interpreter/Interpreter.h +++ b/clang/include/clang/Interpreter/Interpreter.h @@ -65,27 +65,34 @@ class IncrementalCompilerBuilder { // Offload options void SetOffloadArch(llvm::StringRef Arch) { OffloadArch = Arch; }; - // CUDA specific - void SetCudaSDK(llvm::StringRef path) { CudaSDKPath = path; }; + void SetDeviceSDK(llvm::StringRef Path, bool HipEnabled) { + if (HipEnabled) + RocmSDKPath = Path; + else + CudaSDKPath = Path; + } // Hand over the compilation. void SetDriverCompilationCallback(std::function<DriverCompilationFn> C) { CompilationCB = C; } - llvm::Expected<std::unique_ptr<CompilerInstance>> CreateCudaHost(); - llvm::Expected<std::unique_ptr<CompilerInstance>> CreateCudaDevice(); + llvm::Expected<std::unique_ptr<CompilerInstance>> CreateHost(bool HipEnabled); + llvm::Expected<std::unique_ptr<CompilerInstance>> + CreateDevice(bool HipEnabled); private: llvm::Expected<std::unique_ptr<CompilerInstance>> create(std::string TT, std::vector<const char *> &ClangArgv); - llvm::Expected<std::unique_ptr<CompilerInstance>> createCuda(bool device); + llvm::Expected<std::unique_ptr<CompilerInstance>> + createOffload(bool HipEnabled, bool device); std::vector<const char *> UserArgs; std::optional<std::string> TargetTriple; llvm::StringRef OffloadArch; + llvm::StringRef RocmSDKPath; llvm::StringRef CudaSDKPath; std::optional<std::function<DriverCompilationFn>> CompilationCB; @@ -147,8 +154,8 @@ class Interpreter { create(std::unique_ptr<CompilerInstance> CI, std::unique_ptr<IncrementalExecutorBuilder> IEB = nullptr); static llvm::Expected<std::unique_ptr<Interpreter>> - createWithCUDA(std::unique_ptr<CompilerInstance> CI, - std::unique_ptr<CompilerInstance> DCI); + createWithDevice(bool HipEnabled, std::unique_ptr<CompilerInstance> CI, + std::unique_ptr<CompilerInstance> DCI); const ASTContext &getASTContext() const; ASTContext &getASTContext(); diff --git a/clang/lib/Interpreter/Interpreter.cpp b/clang/lib/Interpreter/Interpreter.cpp index ef1ca31538352..a6b7df0220aeb 100644 --- a/clang/lib/Interpreter/Interpreter.cpp +++ b/clang/lib/Interpreter/Interpreter.cpp @@ -302,19 +302,16 @@ IncrementalCompilerBuilder::CreateCpp() { } llvm::Expected<std::unique_ptr<CompilerInstance>> -IncrementalCompilerBuilder::createCuda(bool device) { +IncrementalCompilerBuilder::createOffload(bool HipEnabled, bool device) { std::vector<const char *> Argv; Argv.reserve(5 + 4 + UserArgs.size()); + Argv.push_back(HipEnabled ? "-xhip" : "-xcuda"); + Argv.push_back(device ? "--cuda-device-only" : "--cuda-host-only"); - Argv.push_back("-xcuda"); - if (device) - Argv.push_back("--cuda-device-only"); - else - Argv.push_back("--cuda-host-only"); - - std::string SDKPathArg = "--cuda-path="; - if (!CudaSDKPath.empty()) { - SDKPathArg += CudaSDKPath; + llvm::StringRef SDKPath = HipEnabled ? RocmSDKPath : CudaSDKPath; + std::string SDKPathArg = HipEnabled ? "--rocm-path=" : "--cuda-path="; + if (!SDKPath.empty()) { + SDKPathArg += SDKPath; Argv.push_back(SDKPathArg.c_str()); } @@ -324,6 +321,9 @@ IncrementalCompilerBuilder::createCuda(bool device) { Argv.push_back(ArchArg.c_str()); } + if (device && HipEnabled) + Argv.push_back("-O3"); + llvm::append_range(Argv, UserArgs); std::string TT = TargetTriple ? *TargetTriple : llvm::sys::getProcessTriple(); @@ -331,13 +331,14 @@ IncrementalCompilerBuilder::createCuda(bool device) { } llvm::Expected<std::unique_ptr<CompilerInstance>> -IncrementalCompilerBuilder::CreateCudaDevice() { - return IncrementalCompilerBuilder::createCuda(true); +IncrementalCompilerBuilder::CreateDevice(bool HipEnabled) { + return IncrementalCompilerBuilder::createOffload(HipEnabled, /*device=*/true); } llvm::Expected<std::unique_ptr<CompilerInstance>> -IncrementalCompilerBuilder::CreateCudaHost() { - return IncrementalCompilerBuilder::createCuda(false); +IncrementalCompilerBuilder::CreateHost(bool HipEnabled) { + return IncrementalCompilerBuilder::createOffload(HipEnabled, + /*device=*/false); } Interpreter::Interpreter(std::unique_ptr<CompilerInstance> Instance, @@ -472,8 +473,9 @@ llvm::Expected<std::unique_ptr<Interpreter>> Interpreter::create( } llvm::Expected<std::unique_ptr<Interpreter>> -Interpreter::createWithCUDA(std::unique_ptr<CompilerInstance> CI, - std::unique_ptr<CompilerInstance> DCI) { +Interpreter::createWithDevice(bool HipEnabled, + std::unique_ptr<CompilerInstance> CI, + std::unique_ptr<CompilerInstance> DCI) { // avoid writing fat binary to disk using an in-memory virtual file system llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> IMVFS = std::make_unique<llvm::vfs::InMemoryFileSystem>(); @@ -507,14 +509,20 @@ Interpreter::createWithCUDA(std::unique_ptr<CompilerInstance> CI, Interp->DeviceCI = std::move(DCI); - auto DeviceParser = std::make_unique<IncrementalCUDADeviceParser>( - *Interp->DeviceCI, *Interp->getCompilerInstance(), - Interp->DeviceAct.get(), IMVFS, Err, Interp->PTUs); + if (HipEnabled) { + // FIXME: HIP device parsing is not supported yet; it should use an + // IncrementalHIPDeviceParser once one exists. + } else { + auto DeviceParser = std::make_unique<IncrementalCUDADeviceParser>( + *Interp->DeviceCI, *Interp->getCompilerInstance(), + Interp->DeviceAct.get(), IMVFS, Err, Interp->PTUs); - if (Err) - return std::move(Err); + if (Err) + return std::move(Err); + + Interp->DeviceParser = std::move(DeviceParser); + } - Interp->DeviceParser = std::move(DeviceParser); return std::move(Interp); } diff --git a/clang/test/Interpreter/HIP/hip-environment.hip b/clang/test/Interpreter/HIP/hip-environment.hip new file mode 100644 index 0000000000000..350f118bc46db --- /dev/null +++ b/clang/test/Interpreter/HIP/hip-environment.hip @@ -0,0 +1,8 @@ +// Check that clang-repl initializes the HIP environment. HIP execution is not +// supported yet, so this only verifies that the environment is set up and that +// clang-repl reports it as unsupported. When both -cuda and -hip are passed, +// -hip wins (it appears later), so the HIP path is taken. + +// RUN: not clang-repl -cuda -hip 2>&1 | FileCheck %s + +// CHECK: HIP environment is initialized but not supported as of now. diff --git a/clang/tools/clang-repl/ClangRepl.cpp b/clang/tools/clang-repl/ClangRepl.cpp index c9873540a5d66..7b7fc69330409 100644 --- a/clang/tools/clang-repl/ClangRepl.cpp +++ b/clang/tools/clang-repl/ClangRepl.cpp @@ -52,6 +52,8 @@ LLVM_ATTRIBUTE_USED int __lsan_is_turned_off() { return 1; } #define DEBUG_TYPE "clang-repl" +static llvm::cl::opt<bool> HipEnabled("hip", llvm::cl::Hidden); +static llvm::cl::opt<std::string> RocmPath("rocm-path", llvm::cl::Hidden); static llvm::cl::opt<bool> CudaEnabled("cuda", llvm::cl::Hidden); static llvm::cl::opt<std::string> CudaPath("cuda-path", llvm::cl::Hidden); static llvm::cl::opt<std::string> OffloadArch("offload-arch", llvm::cl::Hidden); @@ -310,24 +312,31 @@ int main(int argc, const char **argv) { IEB->SlabAllocateSize = *SizeOrErr; IEB->UseSharedMemory = UseSharedMemory; - std::unique_ptr<clang::CompilerInstance> DeviceCI; - if (CudaEnabled) { - if (!CudaPath.empty()) - CB.SetCudaSDK(CudaPath); + if (HipEnabled && CudaEnabled) { + if (HipEnabled.getPosition() > CudaEnabled.getPosition()) + CudaEnabled = false; + else + HipEnabled = false; + } - if (OffloadArch.empty()) { - OffloadArch = "sm_35"; - } - CB.SetOffloadArch(OffloadArch); + bool DeviceEnabled = HipEnabled || CudaEnabled; + llvm::StringRef DevicePath = HipEnabled ? RocmPath : CudaPath; + llvm::StringRef DeviceOffloadArch = !OffloadArch.empty() + ? llvm::StringRef(OffloadArch) + : (HipEnabled ? "gfx906" : "sm_35"); + std::unique_ptr<clang::CompilerInstance> DeviceCI; - DeviceCI = ExitOnErr(CB.CreateCudaDevice()); + if (DeviceEnabled) { + CB.SetDeviceSDK(DevicePath, HipEnabled); + CB.SetOffloadArch(DeviceOffloadArch); + DeviceCI = ExitOnErr(CB.CreateDevice(HipEnabled)); } // FIXME: Investigate if we could use runToolOnCodeWithArgs from tooling. It // can replace the boilerplate code for creation of the compiler instance. std::unique_ptr<clang::CompilerInstance> CI; - if (CudaEnabled) { - CI = ExitOnErr(CB.CreateCudaHost()); + if (DeviceEnabled) { + CI = ExitOnErr(CB.CreateHost(HipEnabled)); } else { CI = ExitOnErr(CB.CreateCpp()); } @@ -339,20 +348,36 @@ int main(int argc, const char **argv) { // Load any requested plugins. CI->LoadRequestedPlugins(); - if (CudaEnabled) + if (DeviceEnabled) DeviceCI->LoadRequestedPlugins(); std::unique_ptr<clang::Interpreter> Interp; - if (CudaEnabled) { - Interp = ExitOnErr( - clang::Interpreter::createWithCUDA(std::move(CI), std::move(DeviceCI))); + if (DeviceEnabled) { + Interp = ExitOnErr(clang::Interpreter::createWithDevice( + HipEnabled, std::move(CI), std::move(DeviceCI))); - if (CudaPath.empty()) { - ExitOnErr(Interp->LoadDynamicLibrary("libcudart.so")); - } else { - auto CudaRuntimeLibPath = CudaPath + "/lib/libcudart.so"; - ExitOnErr(Interp->LoadDynamicLibrary(CudaRuntimeLibPath.c_str())); + if (HipEnabled) { + if (RocmPath.empty()) { + ExitOnErr(Interp->LoadDynamicLibrary("libamdhip64.so")); + } else { + auto RocmRuntimeLibPath = RocmPath + "/lib/libamdhip64.so"; + ExitOnErr(Interp->LoadDynamicLibrary(RocmRuntimeLibPath.c_str())); + } + + llvm::errs().changeColor(llvm::raw_ostream::RED, /*Bold=*/true); + llvm::errs() + << "HIP environment is initialized but not supported as of now.\n"; + llvm::errs().resetColor(); + return EXIT_FAILURE; + } + if (CudaEnabled) { + if (CudaPath.empty()) { + ExitOnErr(Interp->LoadDynamicLibrary("libcudart.so")); + } else { + auto CudaRuntimeLibPath = CudaPath + "/lib/libcudart.so"; + ExitOnErr(Interp->LoadDynamicLibrary(CudaRuntimeLibPath.c_str())); + } } } else { Interp = >From 943192cb8e31704ef822f73b6cd7fa38e4264580 Mon Sep 17 00:00:00 2001 From: AdityaSinha149 <[email protected]> Date: Wed, 26 Aug 2026 11:19:02 +0530 Subject: [PATCH 2/4] mend --- clang/lib/Interpreter/Interpreter.cpp | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/clang/lib/Interpreter/Interpreter.cpp b/clang/lib/Interpreter/Interpreter.cpp index a6b7df0220aeb..407cf16ee4300 100644 --- a/clang/lib/Interpreter/Interpreter.cpp +++ b/clang/lib/Interpreter/Interpreter.cpp @@ -337,8 +337,7 @@ IncrementalCompilerBuilder::CreateDevice(bool HipEnabled) { llvm::Expected<std::unique_ptr<CompilerInstance>> IncrementalCompilerBuilder::CreateHost(bool HipEnabled) { - return IncrementalCompilerBuilder::createOffload(HipEnabled, - /*device=*/false); + return IncrementalCompilerBuilder::createOffload(HipEnabled, /*device=*/false); } Interpreter::Interpreter(std::unique_ptr<CompilerInstance> Instance, @@ -718,4 +717,4 @@ llvm::Error Interpreter::LoadDynamicLibrary(const char *name) { return EEOrErr->LoadDynamicLibrary(name); } -} // end namespace clang +} // end namespace clang \ No newline at end of file >From dda895183b199f64b69fe3a5390a7b75af171342 Mon Sep 17 00:00:00 2001 From: AdityaSinha149 <[email protected]> Date: Wed, 26 Aug 2026 11:23:51 +0530 Subject: [PATCH 3/4] mend --- clang/lib/Interpreter/Interpreter.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/clang/lib/Interpreter/Interpreter.cpp b/clang/lib/Interpreter/Interpreter.cpp index 407cf16ee4300..9620876cd21e8 100644 --- a/clang/lib/Interpreter/Interpreter.cpp +++ b/clang/lib/Interpreter/Interpreter.cpp @@ -337,7 +337,8 @@ IncrementalCompilerBuilder::CreateDevice(bool HipEnabled) { llvm::Expected<std::unique_ptr<CompilerInstance>> IncrementalCompilerBuilder::CreateHost(bool HipEnabled) { - return IncrementalCompilerBuilder::createOffload(HipEnabled, /*device=*/false); + return IncrementalCompilerBuilder::createOffload(HipEnabled, + /*device=*/false); } Interpreter::Interpreter(std::unique_ptr<CompilerInstance> Instance, >From 9679c1ff01e479bb4105423aa54d1a5c8c84a996 Mon Sep 17 00:00:00 2001 From: AdityaSinha149 <[email protected]> Date: Wed, 26 Aug 2026 11:53:46 +0530 Subject: [PATCH 4/4] mend Co-authored-by: Cursor <[email protected]> --- clang/include/clang/Interpreter/Interpreter.h | 4 ++-- clang/lib/Interpreter/Interpreter.cpp | 19 ++++++++++--------- 2 files changed, 12 insertions(+), 11 deletions(-) diff --git a/clang/include/clang/Interpreter/Interpreter.h b/clang/include/clang/Interpreter/Interpreter.h index 757e74e3bafb8..dd9fd9249d1ae 100644 --- a/clang/include/clang/Interpreter/Interpreter.h +++ b/clang/include/clang/Interpreter/Interpreter.h @@ -113,9 +113,9 @@ class Interpreter { std::unique_ptr<IncrementalExecutor> IncrExecutor; // An optional parser for CUDA offloading - std::unique_ptr<IncrementalCUDADeviceParser> DeviceParser; + std::unique_ptr<IncrementalCUDADeviceParser> CUDADeviceParser; - // An optional action for CUDA offloading + // An optional action for Device offloading std::unique_ptr<IncrementalAction> DeviceAct; /// List containing information about each incrementally parsed piece of code. diff --git a/clang/lib/Interpreter/Interpreter.cpp b/clang/lib/Interpreter/Interpreter.cpp index 9620876cd21e8..1a2a7bd3093d6 100644 --- a/clang/lib/Interpreter/Interpreter.cpp +++ b/clang/lib/Interpreter/Interpreter.cpp @@ -404,8 +404,8 @@ Interpreter::Interpreter(std::unique_ptr<CompilerInstance> Instance, Interpreter::~Interpreter() { IncrParser.reset(); Act->FinalizeAction(); - if (DeviceParser) - DeviceParser.reset(); + if (CUDADeviceParser) + CUDADeviceParser.reset(); if (DeviceAct) DeviceAct->FinalizeAction(); if (IncrExecutor) { @@ -513,14 +513,14 @@ Interpreter::createWithDevice(bool HipEnabled, // FIXME: HIP device parsing is not supported yet; it should use an // IncrementalHIPDeviceParser once one exists. } else { - auto DeviceParser = std::make_unique<IncrementalCUDADeviceParser>( + auto CUDADeviceParser = std::make_unique<IncrementalCUDADeviceParser>( *Interp->DeviceCI, *Interp->getCompilerInstance(), Interp->DeviceAct.get(), IMVFS, Err, Interp->PTUs); if (Err) return std::move(Err); - Interp->DeviceParser = std::move(DeviceParser); + Interp->CUDADeviceParser = std::move(CUDADeviceParser); } return std::move(Interp); @@ -562,18 +562,19 @@ llvm::Expected<PartialTranslationUnit &> Interpreter::Parse(llvm::StringRef Code) { // If we have a device parser, parse it first. The generated code will be // included in the host compilation - if (DeviceParser) { - llvm::Expected<TranslationUnitDecl *> DeviceTU = DeviceParser->Parse(Code); + if (CUDADeviceParser) { + llvm::Expected<TranslationUnitDecl *> DeviceTU = + CUDADeviceParser->Parse(Code); if (auto E = DeviceTU.takeError()) return std::move(E); - DeviceParser->RegisterPTU(*DeviceTU); + CUDADeviceParser->RegisterPTU(*DeviceTU); - llvm::Expected<llvm::StringRef> PTX = DeviceParser->GeneratePTX(); + llvm::Expected<llvm::StringRef> PTX = CUDADeviceParser->GeneratePTX(); if (!PTX) return PTX.takeError(); - llvm::Error Err = DeviceParser->GenerateFatbinary(); + llvm::Error Err = CUDADeviceParser->GenerateFatbinary(); if (Err) return std::move(Err); } _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
