Skip to content

[HLSL] Use hlsl_device address space for getpointer. #127675

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 4 commits into
base: main
Choose a base branch
from

Conversation

s-perron
Copy link
Contributor

We add the hlsl_device address space to represent the device memory
space as defined in section 1.7.1.3 of the HLSL
spec
.

Fixes #127075

@s-perron s-perron force-pushed the getpointer_address_space branch 2 times, most recently from acd00a6 to 7834858 Compare March 20, 2025 13:47
@s-perron s-perron force-pushed the getpointer_address_space branch 2 times, most recently from 7e1a486 to 7693442 Compare April 10, 2025 17:10
@s-perron s-perron marked this pull request as ready for review April 10, 2025 17:10
@llvmbot llvmbot added clang Clang issues not falling into any other category backend:AArch64 backend:AMDGPU backend:SystemZ backend:WebAssembly clang:frontend Language frontend issues, e.g. anything involving "Sema" clang:codegen IR generation bugs: mangling, exceptions, etc. backend:DirectX HLSL HLSL Language Support labels Apr 10, 2025
@s-perron s-perron requested review from Keenuts and hekota April 10, 2025 17:11
@llvmbot
Copy link
Member

llvmbot commented Apr 10, 2025

@llvm/pr-subscribers-backend-directx
@llvm/pr-subscribers-backend-amdgpu
@llvm/pr-subscribers-backend-aarch64
@llvm/pr-subscribers-hlsl

@llvm/pr-subscribers-backend-webassembly

Author: Steven Perron (s-perron)

Changes

We add the hlsl_device address space to represent the device memory
space as defined in section 1.7.1.3 of the HLSL
spec
.

Fixes #127075


Patch is 27.85 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/127675.diff

20 Files Affected:

  • (modified) clang/include/clang/Basic/AddressSpaces.h (+1)
  • (modified) clang/lib/AST/Type.cpp (+5-3)
  • (modified) clang/lib/AST/TypePrinter.cpp (+2)
  • (modified) clang/lib/Basic/Targets/AArch64.h (+1)
  • (modified) clang/lib/Basic/Targets/AMDGPU.cpp (+2)
  • (modified) clang/lib/Basic/Targets/DirectX.h (+1)
  • (modified) clang/lib/Basic/Targets/NVPTX.h (+1)
  • (modified) clang/lib/Basic/Targets/SPIR.h (+2)
  • (modified) clang/lib/Basic/Targets/SystemZ.h (+1)
  • (modified) clang/lib/Basic/Targets/TCE.h (+1)
  • (modified) clang/lib/Basic/Targets/WebAssembly.h (+1)
  • (modified) clang/lib/Basic/Targets/X86.h (+1)
  • (modified) clang/lib/CodeGen/CGHLSLBuiltins.cpp (+1-3)
  • (modified) clang/lib/Sema/HLSLBuiltinTypeDeclBuilder.cpp (+14-7)
  • (modified) clang/lib/Sema/SemaHLSL.cpp (+4-2)
  • (modified) clang/test/AST/HLSL/OutArgExpr.hlsl (+7-7)
  • (modified) clang/test/AST/HLSL/StructuredBuffers-AST.hlsl (+15-15)
  • (modified) clang/test/AST/HLSL/TypedBuffers-AST.hlsl (+11-11)
  • (modified) clang/test/CodeGenHLSL/builtins/RWBuffer-subscript.hlsl (+8-8)
  • (modified) clang/test/CodeGenHLSL/builtins/StructuredBuffers-subscripts.hlsl (+15)
diff --git a/clang/include/clang/Basic/AddressSpaces.h b/clang/include/clang/Basic/AddressSpaces.h
index 5787e6dac0e36..519d959bb636c 100644
--- a/clang/include/clang/Basic/AddressSpaces.h
+++ b/clang/include/clang/Basic/AddressSpaces.h
@@ -60,6 +60,7 @@ enum class LangAS : unsigned {
   hlsl_groupshared,
   hlsl_constant,
   hlsl_private,
+  hlsl_device,
 
   // Wasm specific address spaces.
   wasm_funcref,
diff --git a/clang/lib/AST/Type.cpp b/clang/lib/AST/Type.cpp
index f6dffeb0a1a8f..4d9268c1772a9 100644
--- a/clang/lib/AST/Type.cpp
+++ b/clang/lib/AST/Type.cpp
@@ -94,10 +94,12 @@ bool Qualifiers::isTargetAddressSpaceSupersetOf(LangAS A, LangAS B,
          (A == LangAS::Default &&
           (B == LangAS::cuda_constant || B == LangAS::cuda_device ||
            B == LangAS::cuda_shared)) ||
-         // `this` overloading depending on address space is not ready,
-         // so this is a hack to allow generating addrspacecasts.
-         // IR legalization will be required when this address space is used.
+         // In HLSL, the this pointer for member functions points to the default
+         // address space. This causes a problem if the structure is in
+         // a different address space. We want to allow casting from these
+         // address spaces to default to work around this problem.
          (A == LangAS::Default && B == LangAS::hlsl_private) ||
+         (A == LangAS::Default && B == LangAS::hlsl_device) ||
          // Conversions from target specific address spaces may be legal
          // depending on the target information.
          Ctx.getTargetInfo().isAddressSpaceSupersetOf(A, B);
diff --git a/clang/lib/AST/TypePrinter.cpp b/clang/lib/AST/TypePrinter.cpp
index 4f2b00d19a446..0075a863620e6 100644
--- a/clang/lib/AST/TypePrinter.cpp
+++ b/clang/lib/AST/TypePrinter.cpp
@@ -2583,6 +2583,8 @@ std::string Qualifiers::getAddrSpaceAsString(LangAS AS) {
     return "hlsl_constant";
   case LangAS::hlsl_private:
     return "hlsl_private";
+  case LangAS::hlsl_device:
+    return "hlsl_device";
   case LangAS::wasm_funcref:
     return "__funcref";
   default:
diff --git a/clang/lib/Basic/Targets/AArch64.h b/clang/lib/Basic/Targets/AArch64.h
index 58822e467ce39..2fab88cfca901 100644
--- a/clang/lib/Basic/Targets/AArch64.h
+++ b/clang/lib/Basic/Targets/AArch64.h
@@ -46,6 +46,7 @@ static const unsigned ARM64AddrSpaceMap[] = {
     0, // hlsl_groupshared
     0, // hlsl_constant
     0, // hlsl_private
+    0, // hlsl_device
     // Wasm address space values for this target are dummy values,
     // as it is only enabled for Wasm targets.
     20, // wasm_funcref
diff --git a/clang/lib/Basic/Targets/AMDGPU.cpp b/clang/lib/Basic/Targets/AMDGPU.cpp
index f81cdac3b7422..c368200f3f739 100644
--- a/clang/lib/Basic/Targets/AMDGPU.cpp
+++ b/clang/lib/Basic/Targets/AMDGPU.cpp
@@ -63,6 +63,7 @@ const LangASMap AMDGPUTargetInfo::AMDGPUDefIsGenMap = {
     // FIXME(pr/122103): hlsl_private -> PRIVATE is wrong, but at least this
     // will break loudly.
     llvm::AMDGPUAS::PRIVATE_ADDRESS, // hlsl_private
+    llvm::AMDGPUAS::GLOBAL_ADDRESS,  // hlsl_device
 };
 
 const LangASMap AMDGPUTargetInfo::AMDGPUDefIsPrivMap = {
@@ -89,6 +90,7 @@ const LangASMap AMDGPUTargetInfo::AMDGPUDefIsPrivMap = {
     llvm::AMDGPUAS::FLAT_ADDRESS,     // hlsl_groupshared
     llvm::AMDGPUAS::CONSTANT_ADDRESS, // hlsl_constant
     llvm::AMDGPUAS::PRIVATE_ADDRESS,  // hlsl_private
+    llvm::AMDGPUAS::GLOBAL_ADDRESS,   // hlsl_device
 };
 } // namespace targets
 } // namespace clang
diff --git a/clang/lib/Basic/Targets/DirectX.h b/clang/lib/Basic/Targets/DirectX.h
index 4ff66cdd9f8fa..566acd6bb3cf3 100644
--- a/clang/lib/Basic/Targets/DirectX.h
+++ b/clang/lib/Basic/Targets/DirectX.h
@@ -44,6 +44,7 @@ static const unsigned DirectXAddrSpaceMap[] = {
     3, // hlsl_groupshared
     2, // hlsl_constant
     0, // hlsl_private
+    0, // hlsl_device
     // Wasm address space values for this target are dummy values,
     // as it is only enabled for Wasm targets.
     20, // wasm_funcref
diff --git a/clang/lib/Basic/Targets/NVPTX.h b/clang/lib/Basic/Targets/NVPTX.h
index 041596929ff5b..dc1ecc30980b7 100644
--- a/clang/lib/Basic/Targets/NVPTX.h
+++ b/clang/lib/Basic/Targets/NVPTX.h
@@ -48,6 +48,7 @@ static const unsigned NVPTXAddrSpaceMap[] = {
     0, // hlsl_groupshared
     0, // hlsl_constant
     0, // hlsl_private
+    0, // hlsl_device
     // Wasm address space values for this target are dummy values,
     // as it is only enabled for Wasm targets.
     20, // wasm_funcref
diff --git a/clang/lib/Basic/Targets/SPIR.h b/clang/lib/Basic/Targets/SPIR.h
index 5ea727364d24b..4509748589b76 100644
--- a/clang/lib/Basic/Targets/SPIR.h
+++ b/clang/lib/Basic/Targets/SPIR.h
@@ -49,6 +49,7 @@ static const unsigned SPIRDefIsPrivMap[] = {
     0,  // hlsl_groupshared
     2,  // hlsl_constant
     10, // hlsl_private
+    11, // hlsl_device
     // Wasm address space values for this target are dummy values,
     // as it is only enabled for Wasm targets.
     20, // wasm_funcref
@@ -84,6 +85,7 @@ static const unsigned SPIRDefIsGenMap[] = {
     0,  // hlsl_groupshared
     0,  // hlsl_constant
     10, // hlsl_private
+    11, // hlsl_device
     // Wasm address space values for this target are dummy values,
     // as it is only enabled for Wasm targets.
     20, // wasm_funcref
diff --git a/clang/lib/Basic/Targets/SystemZ.h b/clang/lib/Basic/Targets/SystemZ.h
index 4d1509b84e82b..dc4534642b9b7 100644
--- a/clang/lib/Basic/Targets/SystemZ.h
+++ b/clang/lib/Basic/Targets/SystemZ.h
@@ -44,6 +44,7 @@ static const unsigned ZOSAddressMap[] = {
     0, // hlsl_groupshared
     0, // hlsl_constant
     0, // hlsl_private
+    0, // hlsl_device
     0  // wasm_funcref
 };
 
diff --git a/clang/lib/Basic/Targets/TCE.h b/clang/lib/Basic/Targets/TCE.h
index 44de8aae52a16..f6e582120447f 100644
--- a/clang/lib/Basic/Targets/TCE.h
+++ b/clang/lib/Basic/Targets/TCE.h
@@ -53,6 +53,7 @@ static const unsigned TCEOpenCLAddrSpaceMap[] = {
     0, // hlsl_groupshared
     0, // hlsl_constant
     0, // hlsl_private
+    0, // hlsl_device
     // Wasm address space values for this target are dummy values,
     // as it is only enabled for Wasm targets.
     20, // wasm_funcref
diff --git a/clang/lib/Basic/Targets/WebAssembly.h b/clang/lib/Basic/Targets/WebAssembly.h
index e786f9a3db68e..04f0cb5df4601 100644
--- a/clang/lib/Basic/Targets/WebAssembly.h
+++ b/clang/lib/Basic/Targets/WebAssembly.h
@@ -44,6 +44,7 @@ static const unsigned WebAssemblyAddrSpaceMap[] = {
     0,  // hlsl_groupshared
     0,  // hlsl_constant
     0,  // hlsl_private
+    0,  // hlsl_device
     20, // wasm_funcref
 };
 
diff --git a/clang/lib/Basic/Targets/X86.h b/clang/lib/Basic/Targets/X86.h
index d44561dd42997..bc8d60f592548 100644
--- a/clang/lib/Basic/Targets/X86.h
+++ b/clang/lib/Basic/Targets/X86.h
@@ -48,6 +48,7 @@ static const unsigned X86AddrSpaceMap[] = {
     0,   // hlsl_groupshared
     0,   // hlsl_constant
     0,   // hlsl_private
+    0,   // hlsl_device
     // Wasm address space values for this target are dummy values,
     // as it is only enabled for Wasm targets.
     20, // wasm_funcref
diff --git a/clang/lib/CodeGen/CGHLSLBuiltins.cpp b/clang/lib/CodeGen/CGHLSLBuiltins.cpp
index 99c62808c323d..044d427688267 100644
--- a/clang/lib/CodeGen/CGHLSLBuiltins.cpp
+++ b/clang/lib/CodeGen/CGHLSLBuiltins.cpp
@@ -280,9 +280,7 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID,
     Value *HandleOp = EmitScalarExpr(E->getArg(0));
     Value *IndexOp = EmitScalarExpr(E->getArg(1));
 
-    // TODO: Map to an hlsl_device address space.
-    llvm::Type *RetTy = llvm::PointerType::getUnqual(getLLVMContext());
-
+    llvm::Type *RetTy = ConvertType(E->getType());
     return Builder.CreateIntrinsic(
         RetTy, CGM.getHLSLRuntime().getCreateResourceGetPointerIntrinsic(),
         ArrayRef<Value *>{HandleOp, IndexOp});
diff --git a/clang/lib/Sema/HLSLBuiltinTypeDeclBuilder.cpp b/clang/lib/Sema/HLSLBuiltinTypeDeclBuilder.cpp
index 2d3e1088557ab..1e022c82b959f 100644
--- a/clang/lib/Sema/HLSLBuiltinTypeDeclBuilder.cpp
+++ b/clang/lib/Sema/HLSLBuiltinTypeDeclBuilder.cpp
@@ -751,13 +751,14 @@ BuiltinTypeDeclBuilder::addHandleAccessFunction(DeclarationName &Name,
   using PH = BuiltinTypeMethodBuilder::PlaceHolder;
 
   QualType ElemTy = getHandleElementType();
-  // TODO: Map to an hlsl_device address space.
-  QualType ElemPtrTy = AST.getPointerType(ElemTy);
-  QualType ReturnTy = ElemTy;
+  QualType AddrSpaceElemTy =
+      AST.getAddrSpaceQualType(ElemTy, LangAS::hlsl_device);
+  QualType ElemPtrTy = AST.getPointerType(AddrSpaceElemTy);
+  // QualType ReturnTy = (IsRef ? AST.getLValueReferenceType(ElemTy) : ElemTy);
+  QualType ReturnTy =
+      (IsRef ? AST.getLValueReferenceType(AddrSpaceElemTy) : ElemTy);
   if (IsConst)
     ReturnTy.addConst();
-  if (IsRef)
-    ReturnTy = AST.getLValueReferenceType(ReturnTy);
 
   return BuiltinTypeMethodBuilder(*this, Name, ReturnTy, IsConst)
       .addParam("Index", AST.UnsignedIntTy)
@@ -771,12 +772,15 @@ BuiltinTypeDeclBuilder &BuiltinTypeDeclBuilder::addAppendMethod() {
   using PH = BuiltinTypeMethodBuilder::PlaceHolder;
   ASTContext &AST = SemaRef.getASTContext();
   QualType ElemTy = getHandleElementType();
+  QualType AddrSpaceElemTy =
+      AST.getAddrSpaceQualType(ElemTy, LangAS::hlsl_device);
   return BuiltinTypeMethodBuilder(*this, "Append", AST.VoidTy)
       .addParam("value", ElemTy)
       .callBuiltin("__builtin_hlsl_buffer_update_counter", AST.UnsignedIntTy,
                    PH::Handle, getConstantIntExpr(1))
       .callBuiltin("__builtin_hlsl_resource_getpointer",
-                   AST.getPointerType(ElemTy), PH::Handle, PH::LastStmt)
+                   AST.getPointerType(AddrSpaceElemTy), PH::Handle,
+                   PH::LastStmt)
       .dereference(PH::LastStmt)
       .assign(PH::LastStmt, PH::_0)
       .finalize();
@@ -786,11 +790,14 @@ BuiltinTypeDeclBuilder &BuiltinTypeDeclBuilder::addConsumeMethod() {
   using PH = BuiltinTypeMethodBuilder::PlaceHolder;
   ASTContext &AST = SemaRef.getASTContext();
   QualType ElemTy = getHandleElementType();
+  QualType AddrSpaceElemTy =
+      AST.getAddrSpaceQualType(ElemTy, LangAS::hlsl_device);
   return BuiltinTypeMethodBuilder(*this, "Consume", ElemTy)
       .callBuiltin("__builtin_hlsl_buffer_update_counter", AST.UnsignedIntTy,
                    PH::Handle, getConstantIntExpr(-1))
       .callBuiltin("__builtin_hlsl_resource_getpointer",
-                   AST.getPointerType(ElemTy), PH::Handle, PH::LastStmt)
+                   AST.getPointerType(AddrSpaceElemTy), PH::Handle,
+                   PH::LastStmt)
       .dereference(PH::LastStmt)
       .finalize();
 }
diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp
index 0b442b75d174d..1f763dfc44650 100644
--- a/clang/lib/Sema/SemaHLSL.cpp
+++ b/clang/lib/Sema/SemaHLSL.cpp
@@ -2379,8 +2379,10 @@ bool SemaHLSL::CheckBuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) {
     auto *ResourceTy =
         TheCall->getArg(0)->getType()->castAs<HLSLAttributedResourceType>();
     QualType ContainedTy = ResourceTy->getContainedType();
-    // TODO: Map to an hlsl_device address space.
-    TheCall->setType(getASTContext().getPointerType(ContainedTy));
+    auto returnType =
+        SemaRef.Context.getAddrSpaceQualType(ContainedTy, LangAS::hlsl_device);
+    returnType = SemaRef.Context.getPointerType(returnType);
+    TheCall->setType(returnType);
     TheCall->setValueKind(VK_LValue);
 
     break;
diff --git a/clang/test/AST/HLSL/OutArgExpr.hlsl b/clang/test/AST/HLSL/OutArgExpr.hlsl
index b07c2efadbf4a..04ce635e721bf 100644
--- a/clang/test/AST/HLSL/OutArgExpr.hlsl
+++ b/clang/test/AST/HLSL/OutArgExpr.hlsl
@@ -30,10 +30,10 @@ void zero(out int Z) { Z = 0; }
 // AST-NEXT: ImplicitCastExpr {{.*}} 'void (*)(inout int)' <FunctionToPointerDecay>
 // AST-NEXT: DeclRefExpr {{.*}} 'void (inout int)' lvalue Function
 // AST-NEXT: HLSLOutArgExpr {{.*}} 'int' lvalue inout
-// AST-NEXT: OpaqueValueExpr [[LVOpV:0x[0-9a-fA-F]+]] {{.*}} 'float' lvalue
-// AST-NEXT: CXXOperatorCallExpr {{.*}} 'float' lvalue '[]'
-// AST-NEXT: ImplicitCastExpr {{.*}} 'float &(*)(unsigned int)' <FunctionToPointerDecay>
-// AST-NEXT: DeclRefExpr {{.*}} 'float &(unsigned int)' lvalue CXXMethod {{.*}} 'operator[]' 'float &(unsigned int)'
+// AST-NEXT: OpaqueValueExpr [[LVOpV:0x[0-9a-fA-F]+]] {{.*}} 'hlsl_device float' lvalue
+// AST-NEXT: CXXOperatorCallExpr {{.*}} 'hlsl_device float' lvalue '[]'
+// AST-NEXT: ImplicitCastExpr {{.*}} 'hlsl_device float &(*)(unsigned int)' <FunctionToPointerDecay>
+// AST-NEXT: DeclRefExpr {{.*}} 'hlsl_device float &(unsigned int)' lvalue CXXMethod {{.*}} 'operator[]' 'hlsl_device float &(unsigned int)'
 // AST-NEXT: DeclRefExpr {{.*}} 'RWBuffer<float>':'hlsl::RWBuffer<float>' lvalue Var {{.*}} 'Buf' 'RWBuffer<float>':'hlsl::RWBuffer<float>'
 // AST-NEXT: ImplicitCastExpr {{.*}} 'uint':'unsigned int' <LValueToRValue>
 // AST-NEXT: DeclRefExpr {{.*}} 'uint':'unsigned int' lvalue ParmVar {{.*}} 'GI' 'uint':'unsigned int'
@@ -41,10 +41,10 @@ void zero(out int Z) { Z = 0; }
 // AST-NEXT: OpaqueValueExpr [[TmpOpV:0x[0-9a-fA-F]+]] {{.*}} 'int' lvalue
 // AST-NEXT: ImplicitCastExpr {{.*}} 'int' <FloatingToIntegral>
 // AST-NEXT: ImplicitCastExpr {{.*}} 'float' <LValueToRValue>
-// AST-NEXT: OpaqueValueExpr [[LVOpV]] <col:15, col:21> 'float' lvalue
+// AST-NEXT: OpaqueValueExpr [[LVOpV]] <col:15, col:21> 'hlsl_device float' lvalue
 
-// AST: BinaryOperator {{.*}} 'float' lvalue '='
-// AST-NEXT: OpaqueValueExpr [[LVOpV]] {{.*}} 'float' lvalue
+// AST: BinaryOperator {{.*}} 'hlsl_device float' lvalue '='
+// AST-NEXT: OpaqueValueExpr [[LVOpV]] {{.*}} 'hlsl_device float' lvalue
 // AST: ImplicitCastExpr {{.*}} 'float' <IntegralToFloating>
 // AST-NEXT: ImplicitCastExpr {{.*}} 'int' <LValueToRValue>
 // AST-NEXT: OpaqueValueExpr [[TmpOpV]] {{.*}} 'int' lvalue
diff --git a/clang/test/AST/HLSL/StructuredBuffers-AST.hlsl b/clang/test/AST/HLSL/StructuredBuffers-AST.hlsl
index dcead068f481e..75dd4fe23121b 100644
--- a/clang/test/AST/HLSL/StructuredBuffers-AST.hlsl
+++ b/clang/test/AST/HLSL/StructuredBuffers-AST.hlsl
@@ -89,12 +89,12 @@ RESOURCE<float> Buffer;
 // CHECK-SAME{LITERAL}: [[hlsl::raw_buffer]]
 // CHECK-SAME{LITERAL}: [[hlsl::contained_type(element_type)]]
 
-// CHECK-SUBSCRIPT: CXXMethodDecl {{.*}} operator[] 'const element_type &(unsigned int) const'
+// CHECK-SUBSCRIPT: CXXMethodDecl {{.*}} operator[] 'hlsl_device element_type &const (unsigned int) const'
 // CHECK-SUBSCRIPT-NEXT: ParmVarDecl {{.*}} Index 'unsigned int'
 // CHECK-SUBSCRIPT-NEXT: CompoundStmt
 // CHECK-SUBSCRIPT-NEXT: ReturnStmt
-// CHECK-SUBSCRIPT-NEXT: UnaryOperator {{.*}} 'element_type' prefix '*' cannot overflow
-// CHECK-SUBSCRIPT-NEXT: CallExpr {{.*}} 'element_type *'
+// CHECK-SUBSCRIPT-NEXT: UnaryOperator {{.*}} 'hlsl_device element_type' prefix '*' cannot overflow
+// CHECK-SUBSCRIPT-NEXT: CallExpr {{.*}} 'hlsl_device element_type *'
 // CHECK-SUBSCRIPT-NEXT: DeclRefExpr {{.*}} '<builtin fn type>' Function {{.*}} '__builtin_hlsl_resource_getpointer' 'void (...) noexcept'
 // CHECK-SUBSCRIPT-NEXT: MemberExpr {{.*}} '__hlsl_resource_t
 // CHECK-SUBSCRIPT-SAME{LITERAL}: [[hlsl::resource_class(
@@ -105,12 +105,12 @@ RESOURCE<float> Buffer;
 // CHECK-SUBSCRIPT-NEXT: DeclRefExpr {{.*}} 'unsigned int' ParmVar {{.*}} 'Index' 'unsigned int'
 // CHECK-SUBSCRIPT-NEXT: AlwaysInlineAttr {{.*}} Implicit always_inline
 
-// CHECK-SUBSCRIPT-NEXT: CXXMethodDecl {{.*}} operator[] 'element_type &(unsigned int)'
+// CHECK-SUBSCRIPT-NEXT: CXXMethodDecl {{.*}} operator[] 'hlsl_device element_type &(unsigned int)'
 // CHECK-SUBSCRIPT-NEXT: ParmVarDecl {{.*}} Index 'unsigned int'
 // CHECK-SUBSCRIPT-NEXT: CompoundStmt
 // CHECK-SUBSCRIPT-NEXT: ReturnStmt
-// CHECK-SUBSCRIPT-NEXT: UnaryOperator {{.*}} 'element_type' prefix '*' cannot overflow
-// CHECK-SUBSCRIPT-NEXT: CallExpr {{.*}} 'element_type *'
+// CHECK-SUBSCRIPT-NEXT: UnaryOperator {{.*}} 'hlsl_device element_type' prefix '*' cannot overflow
+// CHECK-SUBSCRIPT-NEXT: CallExpr {{.*}} 'hlsl_device element_type *'
 // CHECK-SUBSCRIPT-NEXT: DeclRefExpr {{.*}} '<builtin fn type>' Function {{.*}} '__builtin_hlsl_resource_getpointer' 'void (...) noexcept'
 // CHECK-SUBSCRIPT-NEXT: MemberExpr {{.*}} '__hlsl_resource_t
 // CHECK-SUBSCRIPT-SAME{LITERAL}: [[hlsl::resource_class(
@@ -121,15 +121,15 @@ RESOURCE<float> Buffer;
 // CHECK-SUBSCRIPT-NEXT: DeclRefExpr {{.*}} 'unsigned int' ParmVar {{.*}} 'Index' 'unsigned int'
 // CHECK-SUBSCRIPT-NEXT: AlwaysInlineAttr {{.*}} Implicit always_inline
 
-// CHECK-NOSUBSCRIPT-NOT: CXXMethodDecl {{.*}} operator[] 'const element_type &(unsigned int) const'
-// CHECK-NOSUBSCRIPT-NOT: CXXMethodDecl {{.*}} operator[] 'element_type &(unsigned int)'
+// CHECK-NOSUBSCRIPT-NOT: CXXMethodDecl {{.*}} operator[] 'hlsl_device element_type &const (unsigned int) const'
+// CHECK-NOSUBSCRIPT-NOT: CXXMethodDecl {{.*}} operator[] 'hlsl_device element_type &(unsigned int)'
 
 // CHECK-LOAD: CXXMethodDecl {{.*}} Load 'element_type (unsigned int)'
 // CHECK-LOAD-NEXT: ParmVarDecl {{.*}} Index 'unsigned int'
 // CHECK-LOAD-NEXT: CompoundStmt
 // CHECK-LOAD-NEXT: ReturnStmt
-// CHECK-LOAD-NEXT: UnaryOperator {{.*}} 'element_type' prefix '*' cannot overflow
-// CHECK-LOAD-NEXT: CallExpr {{.*}} 'element_type *'
+// CHECK-LOAD-NEXT: UnaryOperator {{.*}} 'hlsl_device element_type' prefix '*' cannot overflow
+// CHECK-LOAD-NEXT: CallExpr {{.*}} 'hlsl_device element_type *'
 // CHECK-LOAD-NEXT: DeclRefExpr {{.*}} '<builtin fn type>' Function {{.*}} '__builtin_hlsl_resource_getpointer' 'void (...) noexcept'
 // CHECK-LOAD-NEXT: MemberExpr {{.*}} '__hlsl_resource_t
 // CHECK-LOAD-SAME{LITERAL}: [[hlsl::resource_class(
@@ -168,9 +168,9 @@ RESOURCE<float> Buffer;
 // CHECK-APPEND: CXXMethodDecl {{.*}} Append 'void (element_type)'
 // CHECK-APPEND-NEXT: ParmVarDecl {{.*}} value 'element_type'
 // CHECK-APPEND-NEXT: CompoundStmt
-// CHECK-APPEND-NEXT: BinaryOperator {{.*}} 'element_type' '='
-// CHECK-APPEND-NEXT: UnaryOperator {{.*}} 'element_type' prefix '*' cannot overflow
-// CHECK-APPEND-NEXT: CallExpr {{.*}} 'element_type *'
+// CHECK-APPEND-NEXT: BinaryOperator {{.*}} 'hlsl_device element_type' '='
+// CHECK-APPEND-NEXT: UnaryOperator {{.*}} 'hlsl_device element_type' prefix '*' cannot overflow
+// CHECK-APPEND-NEXT: CallExpr {{.*}} 'hlsl_device element_type *'
 // CHECK-APPEND-NEXT: DeclRefExpr {{.*}} '<builtin fn type>' Function {{.*}} '__builtin_hlsl_resource_getpointer' 'void (...) noexcept'
 // CHECK-APPEND-NEXT: MemberExpr {{.*}} '__hlsl_resource_t
 // CHECK-APPEND-SAME{LITERAL}: [[hlsl::resource_class(UAV)]]
@@ -190,8 +190,8 @@ RESOURCE<float> Buffer;
 // CHECK-CONSUME: CXXMethodDecl {{.*}} Consume 'element_type ()'
 // CHECK-CONSUME-NEXT: CompoundStmt
 // CHECK-CONSUME-NEXT: ReturnStmt
-// CHECK-CONSUME-NEXT: UnaryOperator {{.*}} 'element_type' prefix '*' cannot overflow
-// CHECK-CONSUME-NEXT: CallExpr {{.*}} 'element_type *'
+// CHECK-CONSUME-NEXT: UnaryOperator {{.*}} 'hlsl_device element_type' prefix '*' cannot overflow
+// CHECK-CONSUME-NEXT: CallExpr {{.*}} 'hlsl_device element_type *'
 // CHECK-CONSUME-NEXT: DeclRefExpr {{.*}} '<builtin fn type>' Function {{.*}} '__builtin_hlsl_resource_getpointer' 'void (...) noexcept'
 // CHECK-CONSUME-NEXT: MemberExpr {{.*}} '__hlsl_resource_t
 // CHECK-CONSUME-SAME{LITERAL}: [[hlsl::resource_class(UAV)]]
diff --git a/clang/test/AST/HLSL/TypedBuffers-AST.hlsl b/clang/test/AST/HLSL/TypedBuffers-AST.hlsl
index f665b06d691e8..1da474469c0c0 100644
--- a/clang/test/AST/HLSL/TypedBuffers-AST.hlsl
+++ b/clang/test/AST/HLSL/TypedBuffers-AST.hlsl
@@ -56,32 +56,32 @@ RESOURCE<float> Buffer;
 // CHECK-UAV-SAME{LITERAL}: [[hlsl::resource_class(UAV)]]
 // CHECK-SAME{LITERAL}: [[hlsl::contained_type(element_type)]]
 
-// CHECK: CXXMethodDecl {{.*}} operator[] 'const element_type &(unsigned int) const'
+// CHECK: CXXMethodDecl {{.*}} operator[] 'hlsl_device element_type &const (unsigned int) const'
 // CHECK-NEXT: ParmVarDecl {{.*}} Index 'unsigned int'
 // CHECK-NEXT: CompoundStmt
 // CHECK-NEXT: ReturnStmt
-// CHECK-NEXT: UnaryOperator {{.*}} 'element_type' prefix '*' cannot overflow
-// CHECK-NEXT: CallExpr {{.*}} 'element_type *'
+// CHECK-NEXT: UnaryOperator {{.*}} 'hlsl_device element_type' prefix '*' cannot overflow
+// CHECK-NEXT: CallExpr {{.*}} 'hlsl_device element_type *'
 // C...
[truncated]

We add the hlsl_device address space to represent the device memory
space as defined in section 1.7.1.3 of the [HLSL
spec](https://microsoft.github.io/hlsl-specs/specs/hlsl.pdf).

Fixes llvm#127075
@s-perron s-perron force-pushed the getpointer_address_space branch from 7693442 to 81c31fc Compare April 10, 2025 17:22
Copy link
Member

@hekota hekota left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks mostly good, but I think there is an issue with the const-ness of the subscript operator return value.

@s-perron s-perron requested a review from hekota April 14, 2025 13:46
@s-perron
Copy link
Contributor Author

@hekota Do you have any more things that need to be fixed?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
backend:AArch64 backend:AMDGPU backend:DirectX backend:SystemZ backend:WebAssembly clang:codegen IR generation bugs: mangling, exceptions, etc. clang:frontend Language frontend issues, e.g. anything involving "Sema" clang Clang issues not falling into any other category HLSL HLSL Language Support
Projects
Status: No status
Development

Successfully merging this pull request may close these issues.

[HLSL] Add hlsl_device address space
6 participants