[clang] c5a85b9 - [CIR] Fix address space issues related to SPIR/SPIR-V targets (#220982)

via cfe-commits cfe-commits at lists.llvm.org
Mon Sep 7 01:43:06 PDT 2026


Author: Mariya Podchishchaeva
Date: 2026-09-07T10:42:59+02:00
New Revision: c5a85b9c6996b2459c169ef6a410c501980c9ea0

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

LOG: [CIR] Fix address space issues related to SPIR/SPIR-V targets (#220982)

This adds support for address space lowering for spir/spir64 (not v)
which are still widely used in OpenCL testing despite spirv32/spirv64
targets existence. This also corrects alloca address space for all
mentioned targets from default to private which is semantically correct
for them and avoids emission of spurious address space casts.

Assisted-by: claude in test cases updating

Added: 
    

Modified: 
    clang/lib/CIR/CodeGen/CIRGenModule.cpp
    clang/lib/CIR/CodeGen/TargetInfo.h
    clang/lib/CIR/CodeGen/Targets/SPIRV.cpp
    clang/lib/CIR/Dialect/Transforms/TargetLowering/LowerModule.cpp
    clang/test/CIR/CodeGenOpenCL/address-space-local-var.clcpp
    clang/test/CIR/CodeGenOpenCL/address-spaces.cl

Removed: 
    


################################################################################
diff  --git a/clang/lib/CIR/CodeGen/CIRGenModule.cpp b/clang/lib/CIR/CodeGen/CIRGenModule.cpp
index cb3f109da2bdf..0dcd35269dbdc 100644
--- a/clang/lib/CIR/CodeGen/CIRGenModule.cpp
+++ b/clang/lib/CIR/CodeGen/CIRGenModule.cpp
@@ -338,7 +338,7 @@ const TargetCIRGenInfo &CIRGenModule::getTargetCIRGenInfo() {
   case llvm::Triple::spirv:
   case llvm::Triple::spirv32:
   case llvm::Triple::spirv64:
-    theTargetCIRGenInfo = createSPIRVTargetCIRGenInfo(genTypes);
+    theTargetCIRGenInfo = createCommonSPIRTargetCIRGenInfo(genTypes);
     return *theTargetCIRGenInfo;
   }
 }

diff  --git a/clang/lib/CIR/CodeGen/TargetInfo.h b/clang/lib/CIR/CodeGen/TargetInfo.h
index b0f036a10ab09..5f380026e025d 100644
--- a/clang/lib/CIR/CodeGen/TargetInfo.h
+++ b/clang/lib/CIR/CodeGen/TargetInfo.h
@@ -200,7 +200,8 @@ createAArch64TargetCIRGenInfo(CIRGenTypes &cgt);
 
 std::unique_ptr<TargetCIRGenInfo> createNVPTXTargetCIRGenInfo(CIRGenTypes &cgt);
 
-std::unique_ptr<TargetCIRGenInfo> createSPIRVTargetCIRGenInfo(CIRGenTypes &cgt);
+std::unique_ptr<TargetCIRGenInfo>
+createCommonSPIRTargetCIRGenInfo(CIRGenTypes &cgt);
 
 } // namespace clang::CIRGen
 

diff  --git a/clang/lib/CIR/CodeGen/Targets/SPIRV.cpp b/clang/lib/CIR/CodeGen/Targets/SPIRV.cpp
index 598cd693d6d26..7b66c51af640c 100644
--- a/clang/lib/CIR/CodeGen/Targets/SPIRV.cpp
+++ b/clang/lib/CIR/CodeGen/Targets/SPIRV.cpp
@@ -6,7 +6,7 @@
 //
 //===----------------------------------------------------------------------===//
 //
-// This provides SPIR-V-specific CIR CodeGen logic for function attributes.
+// This provides SPIR/SPIRV-specific CIR CodeGen logic for function attributes.
 //
 //===----------------------------------------------------------------------===//
 
@@ -22,15 +22,22 @@ using namespace clang::CIRGen;
 
 namespace {
 
-class SPIRVABIInfo : public ABIInfo {
+class CommonSPIRABIInfo : public ABIInfo {
 public:
-  SPIRVABIInfo(CIRGenTypes &cgt) : ABIInfo(cgt) {}
+  CommonSPIRABIInfo(CIRGenTypes &cgt) : ABIInfo(cgt) {}
 };
 
-class SPIRVTargetCIRGenInfo : public TargetCIRGenInfo {
+class CommonSPIRTargetCIRGenInfo : public TargetCIRGenInfo {
 public:
-  SPIRVTargetCIRGenInfo(CIRGenTypes &cgt)
-      : TargetCIRGenInfo(std::make_unique<SPIRVABIInfo>(cgt)) {}
+  CommonSPIRTargetCIRGenInfo(CIRGenTypes &cgt)
+      : TargetCIRGenInfo(std::make_unique<CommonSPIRABIInfo>(cgt)) {}
+
+  mlir::ptr::MemorySpaceAttrInterface
+  getCIRAllocaAddressSpace() const override {
+    return cir::LangAddressSpaceAttr::get(
+        &getABIInfo().cgt.getMLIRContext(),
+        cir::LangAddressSpace::OffloadPrivate);
+  }
 
   cir::CallingConv getDeviceKernelCallingConv() const override {
     return cir::CallingConv::SpirKernel;
@@ -47,6 +54,6 @@ class SPIRVTargetCIRGenInfo : public TargetCIRGenInfo {
 } // namespace
 
 std::unique_ptr<TargetCIRGenInfo>
-clang::CIRGen::createSPIRVTargetCIRGenInfo(CIRGenTypes &cgt) {
-  return std::make_unique<SPIRVTargetCIRGenInfo>(cgt);
+clang::CIRGen::createCommonSPIRTargetCIRGenInfo(CIRGenTypes &cgt) {
+  return std::make_unique<CommonSPIRTargetCIRGenInfo>(cgt);
 }

diff  --git a/clang/lib/CIR/Dialect/Transforms/TargetLowering/LowerModule.cpp b/clang/lib/CIR/Dialect/Transforms/TargetLowering/LowerModule.cpp
index 4061d3b2e58c7..5fd5c8c429f48 100644
--- a/clang/lib/CIR/Dialect/Transforms/TargetLowering/LowerModule.cpp
+++ b/clang/lib/CIR/Dialect/Transforms/TargetLowering/LowerModule.cpp
@@ -53,6 +53,8 @@ createTargetLoweringInfo(LowerModule &lm) {
   case llvm::Triple::nvptx:
   case llvm::Triple::nvptx64:
     return createNVPTXTargetLoweringInfo();
+  case llvm::Triple::spir:
+  case llvm::Triple::spir64:
   case llvm::Triple::spirv:
   case llvm::Triple::spirv32:
   case llvm::Triple::spirv64:

diff  --git a/clang/test/CIR/CodeGenOpenCL/address-space-local-var.clcpp b/clang/test/CIR/CodeGenOpenCL/address-space-local-var.clcpp
index 84dea3b6daead..dcf93a01af038 100644
--- a/clang/test/CIR/CodeGenOpenCL/address-space-local-var.clcpp
+++ b/clang/test/CIR/CodeGenOpenCL/address-space-local-var.clcpp
@@ -8,28 +8,26 @@
 // Test that local variable allocation works correctly in OpenCL C++,
 // where auto variables have the opencl_private address space.
 
-// CIR: cir.func {{.*}} @k(%arg0: !cir.ptr<!s32i>
-// CIR:   %[[GP:.*]] = cir.alloca "gp" {{.*}} init : !cir.ptr<!cir.ptr<!s32i>>
-// CIR:   %[[GR_ALLOCA:.*]] = cir.alloca "gr" {{.*}} init const : !cir.ptr<!cir.ptr<!s32i>>
-// CIR:   %[[R_ALLOCA:.*]] = cir.alloca "r" {{.*}} init const : !cir.ptr<!cir.ptr<!s32i>>
-// CIR:   %[[R:.*]] = cir.cast address_space %[[R_ALLOCA]] : !cir.ptr<!cir.ptr<!s32i>> -> !cir.ptr<!cir.ptr<!s32i>>
-// CIR:   %[[GR:.*]] = cir.cast address_space %[[GR_ALLOCA]] : !cir.ptr<!cir.ptr<!s32i>> -> !cir.ptr<!cir.ptr<!s32i>>
-// CIR:   cir.store %arg0, %[[GP]] : !cir.ptr<!s32i>, !cir.ptr<!cir.ptr<!s32i>>
-// CIR:   %[[DEREF:.*]] = cir.load deref {{.*}} %[[GP]] : !cir.ptr<!cir.ptr<!s32i>>, !cir.ptr<!s32i>
-// CIR:   cir.store {{.*}} %[[DEREF]], %[[GR]] : !cir.ptr<!s32i>, !cir.ptr<!cir.ptr<!s32i>>
-// CIR:   %[[GR_VAL:.*]] = cir.load %[[GR]] : !cir.ptr<!cir.ptr<!s32i>>, !cir.ptr<!s32i>
-// CIR:   %[[CAST:.*]] = cir.cast address_space %[[GR_VAL]] : !cir.ptr<!s32i> -> !cir.ptr<!s32i>
-// CIR:   cir.store {{.*}} %[[CAST]], %[[R]] : !cir.ptr<!s32i>, !cir.ptr<!cir.ptr<!s32i>>
+// CIR: cir.func {{.*}} @k(%arg0: !cir.ptr<!s32i, target_address_space(1)>
+// CIR:   %[[GP:.*]] = cir.alloca "gp" {{.*}} init : !cir.ptr<!cir.ptr<!s32i, target_address_space(1)>>
+// CIR:   %[[GR:.*]] = cir.alloca "gr" {{.*}} init const : !cir.ptr<!cir.ptr<!s32i, target_address_space(1)>>
+// CIR:   %[[R:.*]] = cir.alloca "r" {{.*}} init const : !cir.ptr<!cir.ptr<!s32i, target_address_space(4)>>
+// CIR:   cir.store %arg0, %[[GP]] : !cir.ptr<!s32i, target_address_space(1)>, !cir.ptr<!cir.ptr<!s32i, target_address_space(1)>>
+// CIR:   %[[DEREF:.*]] = cir.load deref {{.*}} %[[GP]] : !cir.ptr<!cir.ptr<!s32i, target_address_space(1)>>, !cir.ptr<!s32i, target_address_space(1)>
+// CIR:   cir.store {{.*}} %[[DEREF]], %[[GR]] : !cir.ptr<!s32i, target_address_space(1)>, !cir.ptr<!cir.ptr<!s32i, target_address_space(1)>>
+// CIR:   %[[CAST:.*]] = cir.cast address_space %[[DEREF]] : !cir.ptr<!s32i, target_address_space(1)> -> !cir.ptr<!s32i, target_address_space(4)>
+// CIR:   cir.store {{.*}} %[[CAST]], %[[R]] : !cir.ptr<!s32i, target_address_space(4)>, !cir.ptr<!cir.ptr<!s32i, target_address_space(4)>>
 
-// LLVM: define dso_local spir_kernel void @k(ptr noundef %[[ARG:.*]])
-// LLVM:   %[[GP_ADDR:.*]] = alloca ptr
-// LLVM:   %[[GR_ADDR:.*]] = alloca ptr
-// LLVM:   %[[R_ADDR:.*]] = alloca ptr
-// LLVM:   store ptr %[[ARG]], ptr %[[GP_ADDR]]
-// LLVM:   %[[V1:.*]] = load ptr, ptr %[[GP_ADDR]]
-// LLVM:   store ptr %[[V1]], ptr %[[GR_ADDR]]
-// LLVM:   %[[V2:.*]] = load ptr, ptr %[[GR_ADDR]]
-// LLVM:   store ptr %[[V2]], ptr %[[R_ADDR]]
+// LLVM: define dso_local spir_kernel void @k(ptr addrspace(1) noundef %[[ARG:.*]])
+// LLVM:   %[[GP_ADDR:.*]] = alloca ptr addrspace(1)
+// LLVM:   %[[GR_ADDR:.*]] = alloca ptr addrspace(1)
+// LLVM:   %[[R_ADDR:.*]] = alloca ptr addrspace(4)
+// LLVM:   store ptr addrspace(1) %[[ARG]], ptr %[[GP_ADDR]]
+// LLVM:   %[[V1:.*]] = load ptr addrspace(1), ptr %[[GP_ADDR]]
+// LLVM:   store ptr addrspace(1) %[[V1]], ptr %[[GR_ADDR]]
+// LLVM:   %[[V2:.*]] = load ptr addrspace(1), ptr %[[GR_ADDR]]
+// LLVM:   %[[V3:.*]] = addrspacecast ptr addrspace(1) %[[V2]] to ptr addrspace(4)
+// LLVM:   store ptr addrspace(4) %[[V3]], ptr %[[R_ADDR]]
 
 // OGCG: define dso_local spir_func void @__clang_ocl_kern_imp_k(ptr addrspace(1) noundef align 4 %gp)
 // OGCG:   %gp.addr = alloca ptr addrspace(1)

diff  --git a/clang/test/CIR/CodeGenOpenCL/address-spaces.cl b/clang/test/CIR/CodeGenOpenCL/address-spaces.cl
index 16c6243ef18ad..42941fad9ea42 100644
--- a/clang/test/CIR/CodeGenOpenCL/address-spaces.cl
+++ b/clang/test/CIR/CodeGenOpenCL/address-spaces.cl
@@ -49,11 +49,8 @@ void local_pointer_value(global int *ptr) {
 
 // CIR-LABEL: cir.func dso_local @local_pointer_value
 // CIR: %[[SAVED:.*]] = cir.alloca "saved"
-// CIR-SAME: !cir.ptr<!cir.ptr<!s32i, lang_address_space(offload_global)>>
-// CIR: %[[SAVED_ADDR:.*]] = cir.cast address_space %[[SAVED]]
-// CIR-SAME: !cir.ptr<!cir.ptr<!s32i, lang_address_space(offload_global)>>
 // CIR-SAME: !cir.ptr<!cir.ptr<!s32i, lang_address_space(offload_global)>, lang_address_space(offload_private)>
-// CIR: cir.store {{.*}}, %[[SAVED_ADDR]]
+// CIR: cir.store {{.*}}, %[[SAVED]]
 // CIR-SAME: !cir.ptr<!s32i, lang_address_space(offload_global)>
 // CIR-SAME: !cir.ptr<!cir.ptr<!s32i, lang_address_space(offload_global)>, lang_address_space(offload_private)>
 


        


More information about the cfe-commits mailing list