From d24050e85e974112f1fae2cb0e376ecbe693b3e5 Mon Sep 17 00:00:00 2001 From: AdUhTkJm <2292398666@qq.com> Date: Thu, 20 Feb 2025 16:03:51 +0000 Subject: [PATCH] [CIR][CUDA] Add attribute for CUDA fat binary name --- .../clang/CIR/Dialect/IR/CIRCUDAAttrs.td | 19 ++++++++++++++++++- .../clang/CIR/Dialect/IR/CIRDialect.td | 1 + clang/lib/CIR/CodeGen/CIRGenCUDARuntime.cpp | 2 -- clang/lib/CIR/CodeGen/CIRGenModule.cpp | 11 +++++++++++ clang/test/CIR/CodeGen/CUDA/registration.cu | 9 +++++++++ clang/test/CIR/CodeGen/CUDA/simple.cu | 2 +- clang/test/CIR/CodeGen/HIP/simple.cpp | 2 +- 7 files changed, 41 insertions(+), 5 deletions(-) create mode 100644 clang/test/CIR/CodeGen/CUDA/registration.cu diff --git a/clang/include/clang/CIR/Dialect/IR/CIRCUDAAttrs.td b/clang/include/clang/CIR/Dialect/IR/CIRCUDAAttrs.td index fd74fe2d349e..e658bb49e815 100644 --- a/clang/include/clang/CIR/Dialect/IR/CIRCUDAAttrs.td +++ b/clang/include/clang/CIR/Dialect/IR/CIRCUDAAttrs.td @@ -18,7 +18,7 @@ //===----------------------------------------------------------------------===// def CUDAKernelNameAttr : CIR_Attr<"CUDAKernelName", - "cuda_kernel_name"> { + "cu.kernel_name"> { let summary = "Device-side function name for this stub."; let description = [{ @@ -35,4 +35,21 @@ def CUDAKernelNameAttr : CIR_Attr<"CUDAKernelName", let assemblyFormat = "`<` $kernel_name `>`"; } +def CUDABinaryHandleAttr : CIR_Attr<"CUDABinaryHandle", + "cu.binary_handle"> { + let summary = "Fat binary handle for device code."; + let description = + [{ + This attribute is attached to the ModuleOp and records the binary file + name passed to host. + + CUDA first compiles device-side code into a fat binary file. The file + name is then passed into host-side code, which is used to create a handle + and then generate various registration functions. + }]; + + let parameters = (ins "std::string":$name); + let assemblyFormat = "`<` $name `>`"; +} + #endif // MLIR_CIR_DIALECT_CIR_CUDA_ATTRS diff --git a/clang/include/clang/CIR/Dialect/IR/CIRDialect.td b/clang/include/clang/CIR/Dialect/IR/CIRDialect.td index 46d2f1a13273..c1ea26919c8e 100644 --- a/clang/include/clang/CIR/Dialect/IR/CIRDialect.td +++ b/clang/include/clang/CIR/Dialect/IR/CIRDialect.td @@ -45,6 +45,7 @@ def CIR_Dialect : Dialect { static llvm::StringRef getGlobalAnnotationsAttrName() { return "cir.global_annotations"; } static llvm::StringRef getOpenCLVersionAttrName() { return "cir.cl.version"; } + static llvm::StringRef getCUDABinaryHandleAttrName() { return "cir.cu.binary_handle"; } void registerAttributes(); void registerTypes(); diff --git a/clang/lib/CIR/CodeGen/CIRGenCUDARuntime.cpp b/clang/lib/CIR/CodeGen/CIRGenCUDARuntime.cpp index 30697d50bf2b..c47663772aa1 100644 --- a/clang/lib/CIR/CodeGen/CIRGenCUDARuntime.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenCUDARuntime.cpp @@ -19,7 +19,6 @@ #include "clang/CIR/Dialect/IR/CIRTypes.h" #include "llvm/Support/Casting.h" #include "llvm/Support/raw_ostream.h" -#include using namespace clang; using namespace clang::CIRGen; @@ -91,7 +90,6 @@ void CIRGenCUDARuntime::emitDeviceStubBodyNew(CIRGenFunction &cgf, llvm_unreachable("NYI"); std::string launchAPI = addPrefixToName("LaunchKernel"); - std::cout << "LaunchAPI is " << launchAPI << "\n"; const IdentifierInfo &launchII = cgm.getASTContext().Idents.get(launchAPI); FunctionDecl *launchFD = nullptr; for (auto *result : dc->lookup(&launchII)) { diff --git a/clang/lib/CIR/CodeGen/CIRGenModule.cpp b/clang/lib/CIR/CodeGen/CIRGenModule.cpp index 79a9d7875423..3c14885dc1c3 100644 --- a/clang/lib/CIR/CodeGen/CIRGenModule.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenModule.cpp @@ -215,6 +215,17 @@ CIRGenModule::CIRGenModule(mlir::MLIRContext &mlirContext, /*line=*/0, /*col=*/0)); } + + // Set CUDA GPU binary handle. + if (langOpts.CUDA) { + std::string cudaBinaryName = codeGenOpts.CudaGpuBinaryFileName; + if (!cudaBinaryName.empty()) { + theModule->setAttr( + cir::CIRDialect::getCUDABinaryHandleAttrName(), + cir::CUDABinaryHandleAttr::get(&mlirContext, cudaBinaryName)); + } + } + if (langOpts.Sanitize.has(SanitizerKind::Thread) || (!codeGenOpts.RelaxedAliasing && codeGenOpts.OptimizationLevel > 0)) { tbaa.reset(new CIRGenTBAA(&mlirContext, astContext, genTypes, theModule, diff --git a/clang/test/CIR/CodeGen/CUDA/registration.cu b/clang/test/CIR/CodeGen/CUDA/registration.cu new file mode 100644 index 000000000000..2c04731bea62 --- /dev/null +++ b/clang/test/CIR/CodeGen/CUDA/registration.cu @@ -0,0 +1,9 @@ +#include "../Inputs/cuda.h" + +// RUN: %clang_cc1 -triple x86_64-unknown-linux-gnu -fclangir \ +// RUN: -x cuda -emit-cir -target-sdk-version=12.3 \ +// RUN: -fcuda-include-gpubinary fatbin.o\ +// RUN: %s -o %t.cir +// RUN: FileCheck --check-prefix=CIR-HOST --input-file=%t.cir %s + +// CIR-HOST: module @"{{.*}}" attributes{{.*}}cir.cu.binary_handle = #cir.cu.binary_handle{{.*}} diff --git a/clang/test/CIR/CodeGen/CUDA/simple.cu b/clang/test/CIR/CodeGen/CUDA/simple.cu index 51a1d3bb2f4b..db5e7628439f 100644 --- a/clang/test/CIR/CodeGen/CUDA/simple.cu +++ b/clang/test/CIR/CodeGen/CUDA/simple.cu @@ -11,7 +11,7 @@ // RUN: FileCheck --check-prefix=CIR-DEVICE --input-file=%t.cir %s // Attribute for global_fn -// CIR-HOST: [[Kernel:#[a-zA-Z_0-9]+]] = {{.*}}#cir.cuda_kernel_name<_Z9global_fni>{{.*}} +// CIR-HOST: [[Kernel:#[a-zA-Z_0-9]+]] = {{.*}}#cir.cu.kernel_name<_Z9global_fni>{{.*}} __host__ void host_fn(int *a, int *b, int *c) {} // CIR-HOST: cir.func @_Z7host_fnPiS_S_ diff --git a/clang/test/CIR/CodeGen/HIP/simple.cpp b/clang/test/CIR/CodeGen/HIP/simple.cpp index f04dd27e0411..d4db01aa23b8 100644 --- a/clang/test/CIR/CodeGen/HIP/simple.cpp +++ b/clang/test/CIR/CodeGen/HIP/simple.cpp @@ -11,7 +11,7 @@ // RUN: FileCheck --check-prefix=CIR-DEVICE --input-file=%t.cir %s // Attribute for global_fn -// CIR-HOST: [[Kernel:#[a-zA-Z_0-9]+]] = {{.*}}#cir.cuda_kernel_name<_Z9global_fni>{{.*}} +// CIR-HOST: [[Kernel:#[a-zA-Z_0-9]+]] = {{.*}}#cir.cu.kernel_name<_Z9global_fni>{{.*}} __host__ void host_fn(int *a, int *b, int *c) {}