[llvm-branch-commits] [llvm] [CodeGen][NPM] Clear MachineFunctions without using PA (PR #139517)

2025-07-04 Thread Akshat Oke via llvm-branch-commits

https://github.com/optimisan edited 
https://github.com/llvm/llvm-project/pull/139517
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147094)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic created 
https://github.com/llvm/llvm-project/pull/147094

At the moment, when we report diagnostics from `SemaHLSL` we only provide the 
source location of the root signature attr. This allows for significantly less 
helpful diagnostics (for eg. reporting resource range overlaps).

This pr implements a way to retain the source location of a root element when 
it is parsed, so that we can output the `SourceLocation` of each root element 
that causes the overlap in the diagnostics during semantic analysis.

This pr defines a wrapper struct `clang::hlsl::RootSignatureElement` in 
`SemaHLSL` that will contain the underlying `RootElement` and can hold any 
additional diagnostic information. This struct will be what is used in 
`HLSLRootSignatureParser` and in `SemaHLSL`. Then the diagnostic information 
will be stripped and the underlying element will be stored in the 
`RootSignatureDecl`.

For the reporting of diagnostics, we can now use the retained `SourceLocation` 
of each `RootElement` when reporting the range overlap, and we can add a `note` 
diagnostic to highlight the other root element as well.

- Defines `RootSignatureElement` in the `hlsl` namespace in `SemaHLSL` (defined 
in `SemaHLSL` because `Parse` has a dependency on `Sema`)
- Updates parsing logic to construct `RootSignatureElement`s and retain the 
source loction in `ParseHLSLRootSignature`
- Updates `SemaHLSL` when it constructs the `RootSignatureDecl` to take the new 
`RootSignatureElement` and store the underlying `RootElement`
- Updates the current tests to ensure the new `note` diagnostic is produced and 
that the `SourceLocation` is seen
- Adds a test to demonstrate the `SourceLocation` of both elements being 
correctly pointed out

Resolves: https://github.com/llvm/llvm-project/issues/145819

>From 4a5cde3f77dc0c371d1f33b10be9507d3aeff3e3 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 27 Jun 2025 18:36:38 +
Subject: [PATCH 1/8] nfc: introduce wrapper `RootSignatureElement` around
 `RootElement` to retain clang diag info

---
 .../clang/Parse/ParseHLSLRootSignature.h  |  17 ++-
 clang/include/clang/Sema/SemaHLSL.h   |  10 +-
 clang/lib/Parse/ParseDeclCXX.cpp  |   2 +-
 clang/lib/Parse/ParseHLSLRootSignature.cpp|  21 ++--
 clang/lib/Sema/SemaHLSL.cpp   |   6 +-
 .../Parse/ParseHLSLRootSignatureTest.cpp  | 115 +-
 6 files changed, 99 insertions(+), 72 deletions(-)

diff --git a/clang/include/clang/Parse/ParseHLSLRootSignature.h 
b/clang/include/clang/Parse/ParseHLSLRootSignature.h
index b0ef617a13c28..53001d2ba461f 100644
--- a/clang/include/clang/Parse/ParseHLSLRootSignature.h
+++ b/clang/include/clang/Parse/ParseHLSLRootSignature.h
@@ -26,10 +26,22 @@
 namespace clang {
 namespace hlsl {
 
+// Introduce a wrapper struct around the underlying RootElement. This structure
+// will retain extra clang diagnostic information that is not available in 
llvm.
+struct RootSignatureElement {
+  RootSignatureElement(llvm::hlsl::rootsig::RootElement Element)
+  : Element(Element) {}
+
+  const llvm::hlsl::rootsig::RootElement &getElement() const { return Element; 
}
+
+private:
+  llvm::hlsl::rootsig::RootElement Element;
+};
+
 class RootSignatureParser {
 public:
   RootSignatureParser(llvm::dxbc::RootSignatureVersion Version,
-  SmallVector &Elements,
+  SmallVector &Elements,
   StringLiteral *Signature, Preprocessor &PP);
 
   /// Consumes tokens from the Lexer and constructs the in-memory
@@ -196,7 +208,8 @@ class RootSignatureParser {
 
 private:
   llvm::dxbc::RootSignatureVersion Version;
-  SmallVector &Elements;
+  SmallVector &Elements;
+
   clang::StringLiteral *Signature;
   RootSignatureLexer Lexer;
   clang::Preprocessor &PP;
diff --git a/clang/include/clang/Sema/SemaHLSL.h 
b/clang/include/clang/Sema/SemaHLSL.h
index 7d7eae4db532c..1af706da702c2 100644
--- a/clang/include/clang/Sema/SemaHLSL.h
+++ b/clang/include/clang/Sema/SemaHLSL.h
@@ -32,6 +32,10 @@ class ParsedAttr;
 class Scope;
 class VarDecl;
 
+namespace hlsl {
+struct RootSignatureElement;
+}
+
 using llvm::dxil::ResourceClass;
 
 // FIXME: This can be hidden (as static function in SemaHLSL.cpp) once we no
@@ -130,9 +134,9 @@ class SemaHLSL : public SemaBase {
 
   /// Creates the Root Signature decl of the parsed Root Signature elements
   /// onto the AST and push it onto current Scope
-  void ActOnFinishRootSignatureDecl(
-  SourceLocation Loc, IdentifierInfo *DeclIdent,
-  SmallVector &Elements);
+  void
+  ActOnFinishRootSignatureDecl(SourceLocation Loc, IdentifierInfo *DeclIdent,
+   ArrayRef Elements);
 
   // Returns true when D is invalid and a diagnostic was produced
   bool handleRootSignatureDecl(HLSLRootSignatureDecl *D, SourceLocation Loc);
diff --git a/clang/lib/Parse/ParseDeclCXX.cpp b/clang/lib/Parse/ParseDeclCXX.cpp
index d3bc6f1e89832..d06bb6a25efa5 100

[llvm-branch-commits] [llvm] [DirectX] Add missing verifications during `validate` of `DXILRootSignature` (PR #147111)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic edited 
https://github.com/llvm/llvm-project/pull/147111
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir] NFC - refactor id builder and avoid leaking impl details (PR #146922)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits

https://github.com/ftynse approved this pull request.


https://github.com/llvm/llvm-project/pull/146922
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] WIP: retain source location for sema validation diagnostics and move validations out to library (PR #146150)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic closed 
https://github.com/llvm/llvm-project/pull/146150
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [DirectX][Draft] validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

https://github.com/joaosaffran updated 
https://github.com/llvm/llvm-project/pull/146785

>From 76d633d2b2b70ae6eaa1e7c40ef09e5f6ef9ae74 Mon Sep 17 00:00:00 2001
From: joaosaffran 
Date: Thu, 26 Jun 2025 19:28:01 +
Subject: [PATCH 1/6] refactoring

---
 .../lib/Target/DirectX/DXContainerGlobals.cpp |  9 ++--
 llvm/lib/Target/DirectX/DXILRootSignature.cpp | 12 ++---
 llvm/lib/Target/DirectX/DXILRootSignature.h   | 45 ++-
 3 files changed, 44 insertions(+), 22 deletions(-)

diff --git a/llvm/lib/Target/DirectX/DXContainerGlobals.cpp 
b/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
index 9c38901f6821f..fa27c4665cfbe 100644
--- a/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
+++ b/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
@@ -160,18 +160,17 @@ void DXContainerGlobals::addRootSignature(Module &M,
 
   assert(MMI.EntryPropertyVec.size() == 1);
 
-  auto &RSA = getAnalysis();
+  auto &RSA = getAnalysis().getRSInfo();
   const Function *EntryFunction = MMI.EntryPropertyVec[0].Entry;
-  const auto &FuncRs = RSA.find(EntryFunction);
+  const auto &RS = RSA.getDescForFunction(EntryFunction);
 
-  if (FuncRs == RSA.end())
+  if (!RS )
 return;
 
-  const RootSignatureDesc &RS = FuncRs->second;
   SmallString<256> Data;
   raw_svector_ostream OS(Data);
 
-  RS.write(OS);
+  RS->write(OS);
 
   Constant *Constant =
   ConstantDataArray::getString(M.getContext(), Data, /*AddNull*/ false);
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.cpp 
b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
index 29e78fcce5262..4094df160ef6f 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.cpp
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
@@ -554,9 +554,9 @@ analyzeModule(Module &M) {
 
 AnalysisKey RootSignatureAnalysis::Key;
 
-SmallDenseMap
-RootSignatureAnalysis::run(Module &M, ModuleAnalysisManager &AM) {
-  return analyzeModule(M);
+RootSignatureBindingInfo RootSignatureAnalysis::run(Module &M,
+ModuleAnalysisManager &AM) 
{
+  return RootSignatureBindingInfo(analyzeModule(M));
 }
 
 
//===--===//
@@ -564,8 +564,7 @@ RootSignatureAnalysis::run(Module &M, ModuleAnalysisManager 
&AM) {
 PreservedAnalyses RootSignatureAnalysisPrinter::run(Module &M,
 ModuleAnalysisManager &AM) 
{
 
-  SmallDenseMap &RSDMap =
-  AM.getResult(M);
+  RootSignatureBindingInfo &RSDMap = AM.getResult(M);
 
   OS << "Root Signature Definitions"
  << "\n";
@@ -636,7 +635,8 @@ PreservedAnalyses RootSignatureAnalysisPrinter::run(Module 
&M,
 
 
//===--===//
 bool RootSignatureAnalysisWrapper::runOnModule(Module &M) {
-  FuncToRsMap = analyzeModule(M);
+  FuncToRsMap = std::make_unique(
+  RootSignatureBindingInfo(analyzeModule(M)));
   return false;
 }
 
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.h 
b/llvm/lib/Target/DirectX/DXILRootSignature.h
index b45cebc15fd39..fef933811f840 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.h
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.h
@@ -33,16 +33,43 @@ enum class RootSignatureElementKind {
   CBV = 5,
   DescriptorTable = 6,
 };
+
+class RootSignatureBindingInfo {
+  private:
+SmallDenseMap FuncToRsMap;
+
+  public:
+  using iterator =
+SmallDenseMap::iterator;
+
+  RootSignatureBindingInfo () = default;
+  RootSignatureBindingInfo(SmallDenseMap Map) : FuncToRsMap(Map) {};
+
+  iterator find(const Function *F) { return FuncToRsMap.find(F); }
+
+  iterator end() { return FuncToRsMap.end(); }
+
+  std::optional getDescForFunction(const Function* 
F) {
+const auto FuncRs = find(F);
+if (FuncRs == end())
+  return std::nullopt;
+
+return FuncRs->second;
+  }
+  
+};
+
 class RootSignatureAnalysis : public AnalysisInfoMixin {
   friend AnalysisInfoMixin;
   static AnalysisKey Key;
 
 public:
-  RootSignatureAnalysis() = default;
 
-  using Result = SmallDenseMap;
+RootSignatureAnalysis() = default;
 
-  SmallDenseMap
+  using Result = RootSignatureBindingInfo;
+  
+  RootSignatureBindingInfo
   run(Module &M, ModuleAnalysisManager &AM);
 };
 
@@ -52,20 +79,16 @@ class RootSignatureAnalysis : public 
AnalysisInfoMixin {
 /// passes which run through the legacy pass manager.
 class RootSignatureAnalysisWrapper : public ModulePass {
 private:
-  SmallDenseMap FuncToRsMap;
+  std::unique_ptr FuncToRsMap;
 
 public:
   static char ID;
+  using Result = RootSignatureBindingInfo;
 
   RootSignatureAnalysisWrapper() : ModulePass(ID) {}
 
-  using iterator =
-  SmallDenseMap::iterator;
-
-  iterator find(const Function *F) { return FuncToRsMap.find(F); }
-
-  iterator end() { return FuncToRsMap.end(); }
-
+  RootSignatureBindingInfo& getRSInfo() {return *FuncToRsMap;}
+  
   bool runOnModule(Module &M) override;
 
   void getAnalysisUsage(AnalysisUsage &AU) const override;

>From 75

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

https://github.com/joaosaffran edited 
https://github.com/llvm/llvm-project/pull/146785
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] release/20.x: [X86] Ignore NSW when DstSVT is i32 (#131755) (PR #147034)

2025-07-04 Thread Nikita Popov via llvm-branch-commits

https://github.com/nikic updated 
https://github.com/llvm/llvm-project/pull/147034

>From c50b409b6b523fa4b8164b80515a93b12e1b5cd4 Mon Sep 17 00:00:00 2001
From: Phoebe Wang 
Date: Tue, 18 Mar 2025 13:04:23 +0100
Subject: [PATCH] [X86] Ignore NSW when DstSVT is i32 (#131755)

We don't have PACKSS for i64->i32.

Fixes: https://godbolt.org/z/qb8nxnPbK, which was introduced by ddd2f57b
(cherry picked from commit 3d631914677b58a5479b310f480ac76e27d41e7e)
---
 llvm/lib/Target/X86/X86ISelLowering.cpp  |  3 +-
 llvm/test/CodeGen/X86/vector-trunc-nowrap.ll | 88 
 2 files changed, 90 insertions(+), 1 deletion(-)

diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp 
b/llvm/lib/Target/X86/X86ISelLowering.cpp
index 4413fbb77f415..12c40b501f627 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.cpp
+++ b/llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -20889,7 +20889,8 @@ static SDValue matchTruncateWithPACK(unsigned 
&PackOpcode, EVT DstVT,
 return SDValue();
 
   unsigned MinSignBits = NumSrcEltBits - NumPackedSignBits;
-  if (Flags.hasNoSignedWrap() || MinSignBits < NumSignBits) {
+  if ((Flags.hasNoSignedWrap() && DstSVT != MVT::i32) ||
+  MinSignBits < NumSignBits) {
 PackOpcode = X86ISD::PACKSS;
 return In;
   }
diff --git a/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll 
b/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
index 2b8eedfbbdc9c..863f30e03d2d6 100644
--- a/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
+++ b/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
@@ -1592,3 +1592,91 @@ entry:
   %1 = bitcast <8 x i8> %0 to i64
   ret i64 %1
 }
+
+define void @foo(<4 x i64> %a, <4 x i64> %b, ptr %p) 
"min-legal-vector-width"="256" "prefer-vector-width"="256" {
+; SSE-LABEL: foo:
+; SSE:   # %bb.0: # %entry
+; SSE-NEXT:shufps {{.*#+}} xmm0 = xmm0[0,2],xmm1[0,2]
+; SSE-NEXT:shufps {{.*#+}} xmm2 = xmm2[0,2],xmm3[0,2]
+; SSE-NEXT:movaps %xmm2, 16(%rdi)
+; SSE-NEXT:movaps %xmm0, (%rdi)
+; SSE-NEXT:retq
+;
+; AVX1-LABEL: foo:
+; AVX1:   # %bb.0: # %entry
+; AVX1-NEXT:vextractf128 $1, %ymm0, %xmm2
+; AVX1-NEXT:vshufps {{.*#+}} xmm0 = xmm0[0,2],xmm2[0,2]
+; AVX1-NEXT:vextractf128 $1, %ymm1, %xmm2
+; AVX1-NEXT:vshufps {{.*#+}} xmm1 = xmm1[0,2],xmm2[0,2]
+; AVX1-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX1-NEXT:vmovaps %xmm0, (%rdi)
+; AVX1-NEXT:vzeroupper
+; AVX1-NEXT:retq
+;
+; AVX2-SLOW-LABEL: foo:
+; AVX2-SLOW:   # %bb.0: # %entry
+; AVX2-SLOW-NEXT:vextractf128 $1, %ymm0, %xmm2
+; AVX2-SLOW-NEXT:vshufps {{.*#+}} xmm0 = xmm0[0,2],xmm2[0,2]
+; AVX2-SLOW-NEXT:vextractf128 $1, %ymm1, %xmm2
+; AVX2-SLOW-NEXT:vshufps {{.*#+}} xmm1 = xmm1[0,2],xmm2[0,2]
+; AVX2-SLOW-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-SLOW-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-SLOW-NEXT:vzeroupper
+; AVX2-SLOW-NEXT:retq
+;
+; AVX2-FAST-ALL-LABEL: foo:
+; AVX2-FAST-ALL:   # %bb.0: # %entry
+; AVX2-FAST-ALL-NEXT:vmovaps {{.*#+}} ymm2 = [0,2,4,6,4,6,6,7]
+; AVX2-FAST-ALL-NEXT:vpermps %ymm0, %ymm2, %ymm0
+; AVX2-FAST-ALL-NEXT:vpermps %ymm1, %ymm2, %ymm1
+; AVX2-FAST-ALL-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-FAST-ALL-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-FAST-ALL-NEXT:vzeroupper
+; AVX2-FAST-ALL-NEXT:retq
+;
+; AVX2-FAST-PERLANE-LABEL: foo:
+; AVX2-FAST-PERLANE:   # %bb.0: # %entry
+; AVX2-FAST-PERLANE-NEXT:vextractf128 $1, %ymm0, %xmm2
+; AVX2-FAST-PERLANE-NEXT:vshufps {{.*#+}} xmm0 = xmm0[0,2],xmm2[0,2]
+; AVX2-FAST-PERLANE-NEXT:vextractf128 $1, %ymm1, %xmm2
+; AVX2-FAST-PERLANE-NEXT:vshufps {{.*#+}} xmm1 = xmm1[0,2],xmm2[0,2]
+; AVX2-FAST-PERLANE-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-FAST-PERLANE-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-FAST-PERLANE-NEXT:vzeroupper
+; AVX2-FAST-PERLANE-NEXT:retq
+;
+; AVX512F-LABEL: foo:
+; AVX512F:   # %bb.0: # %entry
+; AVX512F-NEXT:# kill: def $ymm0 killed $ymm0 def $zmm0
+; AVX512F-NEXT:vinserti64x4 $1, %ymm1, %zmm0, %zmm0
+; AVX512F-NEXT:vpmovqd %zmm0, (%rdi)
+; AVX512F-NEXT:vzeroupper
+; AVX512F-NEXT:retq
+;
+; AVX512VL-LABEL: foo:
+; AVX512VL:   # %bb.0: # %entry
+; AVX512VL-NEXT:vpmovqd %ymm1, 16(%rdi)
+; AVX512VL-NEXT:vpmovqd %ymm0, (%rdi)
+; AVX512VL-NEXT:vzeroupper
+; AVX512VL-NEXT:retq
+;
+; AVX512BW-LABEL: foo:
+; AVX512BW:   # %bb.0: # %entry
+; AVX512BW-NEXT:# kill: def $ymm0 killed $ymm0 def $zmm0
+; AVX512BW-NEXT:vinserti64x4 $1, %ymm1, %zmm0, %zmm0
+; AVX512BW-NEXT:vpmovqd %zmm0, (%rdi)
+; AVX512BW-NEXT:vzeroupper
+; AVX512BW-NEXT:retq
+;
+; AVX512BWVL-LABEL: foo:
+; AVX512BWVL:   # %bb.0: # %entry
+; AVX512BWVL-NEXT:vpmovqd %ymm1, 16(%rdi)
+; AVX512BWVL-NEXT:vpmovqd %ymm0, (%rdi)
+; AVX512BWVL-NEXT:vzeroupper
+; AVX512BWVL-NEXT:retq
+entry:
+  %0 = shufflevector <4 x i64> %a, <4 x i64> %b, <8 x i32> 
+  %1 = trunc nsw <8 x i64> %0 to <8 x i32>
+  store <8 x i32> %1, ptr %p, align 16
+  ret void
+}

___
llvm-bran

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

https://github.com/joaosaffran edited 
https://github.com/llvm/llvm-project/pull/146785
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [AArch64][PAC] Introduce AArch64::PAC pseudo instruction (PR #146488)

2025-07-04 Thread Anatoly Trosinenko via llvm-branch-commits

https://github.com/atrosinenko updated 
https://github.com/llvm/llvm-project/pull/146488

>From ba9d8965de86e63cce18fc9c2d0fe9484f172e1f Mon Sep 17 00:00:00 2001
From: Anatoly Trosinenko 
Date: Sat, 28 Jun 2025 10:50:46 +0300
Subject: [PATCH 1/2] [AArch64][PAC] Introduce AArch64::PAC pseudo instruction

Introduce a pseudo instruction to be selected instead of a pair of
`MOVKXi` and `PAC[DI][AB]` carrying address and immediate modifiers
as separate operands. The new pseudo instruction is expanded in
AsmPrinter, so that MOVKXi is emitted immediately before `PAC[DI][AB]`.
This way, an attacker cannot control the immediate modifier used to sign
the value, even if address modifier can be substituted.

To simplify the instruction selection, select AArch64::PAC pseudo using
TableGen pattern and post-process its $AddrDisc operand by custom
inserter hook - this eliminates duplication of the logic for DAGISel
and GlobalISel. Furthermore, this improves cross-BB analysis in case of
DAGISel.
---
 llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp |  32 +++
 .../Target/AArch64/AArch64ISelLowering.cpp|  74 +++
 llvm/lib/Target/AArch64/AArch64ISelLowering.h |   7 +
 llvm/lib/Target/AArch64/AArch64InstrInfo.td   |  21 +-
 llvm/test/CodeGen/AArch64/ptrauth-isel.ll | 205 ++
 5 files changed, 338 insertions(+), 1 deletion(-)
 create mode 100644 llvm/test/CodeGen/AArch64/ptrauth-isel.ll

diff --git a/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp 
b/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
index dd10050592190..f34217a3a8133 100644
--- a/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
+++ b/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
@@ -171,6 +171,9 @@ class AArch64AsmPrinter : public AsmPrinter {
   // Emit the sequence for AUT or AUTPAC.
   void emitPtrauthAuthResign(const MachineInstr *MI);
 
+  // Emit the sequence for PAC.
+  void emitPtrauthSign(const MachineInstr *MI);
+
   // Emit the sequence to compute the discriminator.
   //
   // ScratchReg should be x16/x17.
@@ -2173,6 +2176,31 @@ void AArch64AsmPrinter::emitPtrauthAuthResign(const 
MachineInstr *MI) {
 OutStreamer->emitLabel(EndSym);
 }
 
+void AArch64AsmPrinter::emitPtrauthSign(const MachineInstr *MI) {
+  Register Val = MI->getOperand(1).getReg();
+  auto Key = (AArch64PACKey::ID)MI->getOperand(2).getImm();
+  uint64_t Disc = MI->getOperand(3).getImm();
+  Register AddrDisc = MI->getOperand(4).getReg();
+  bool AddrDiscKilled = MI->getOperand(4).isKill();
+
+  // Compute aut discriminator into x17
+  assert(isUInt<16>(Disc));
+  Register DiscReg = emitPtrauthDiscriminator(
+  Disc, AddrDisc, AArch64::X17, /*MayUseAddrAsScratch=*/AddrDiscKilled);
+  bool IsZeroDisc = DiscReg == AArch64::XZR;
+  unsigned Opc = getPACOpcodeForKey(Key, IsZeroDisc);
+
+  //  paciza x16  ; if  IsZeroDisc
+  //  pacia x16, x17  ; if !IsZeroDisc
+  MCInst PACInst;
+  PACInst.setOpcode(Opc);
+  PACInst.addOperand(MCOperand::createReg(Val));
+  PACInst.addOperand(MCOperand::createReg(Val));
+  if (!IsZeroDisc)
+PACInst.addOperand(MCOperand::createReg(DiscReg));
+  EmitToStreamer(*OutStreamer, PACInst);
+}
+
 void AArch64AsmPrinter::emitPtrauthBranch(const MachineInstr *MI) {
   bool IsCall = MI->getOpcode() == AArch64::BLRA;
   unsigned BrTarget = MI->getOperand(0).getReg();
@@ -2867,6 +2895,10 @@ void AArch64AsmPrinter::emitInstruction(const 
MachineInstr *MI) {
 emitPtrauthAuthResign(MI);
 return;
 
+  case AArch64::PAC:
+emitPtrauthSign(MI);
+return;
+
   case AArch64::LOADauthptrstatic:
 LowerLOADauthptrstatic(*MI);
 return;
diff --git a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp 
b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
index fb8bd81c033af..c8eb9f3dd01ad 100644
--- a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
+++ b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
@@ -3073,6 +3073,75 @@ AArch64TargetLowering::EmitGetSMESaveSize(MachineInstr 
&MI,
   return BB;
 }
 
+// Helper function to find the instruction that defined a virtual register.
+// If unable to find such instruction, returns nullptr.
+static MachineInstr *stripVRegCopies(const MachineRegisterInfo &MRI,
+ Register Reg) {
+  while (Reg.isVirtual()) {
+MachineInstr *DefMI = MRI.getVRegDef(Reg);
+assert(DefMI && "Virtual register definition not found");
+unsigned Opcode = DefMI->getOpcode();
+
+if (Opcode == AArch64::COPY) {
+  Reg = DefMI->getOperand(1).getReg();
+  // Vreg is defined by copying from physreg.
+  if (Reg.isPhysical())
+return DefMI;
+  continue;
+}
+if (Opcode == AArch64::SUBREG_TO_REG) {
+  Reg = DefMI->getOperand(2).getReg();
+  continue;
+}
+
+return DefMI;
+  }
+  return nullptr;
+}
+
+void AArch64TargetLowering::fixupBlendComponents(
+MachineInstr &MI, MachineBasicBlock *BB, MachineOperand &IntDiscOp,
+MachineOperand &AddrDiscOp, const TargetRegisterClass *AddrDiscRC) const {
+  const TargetInstrInfo *TII = Subt

[llvm-branch-commits] [llvm] [AArch64][PAC] Rework discriminator analysis in AUT and AUTPAC (PR #146489)

2025-07-04 Thread Anatoly Trosinenko via llvm-branch-commits

https://github.com/atrosinenko updated 
https://github.com/llvm/llvm-project/pull/146489

>From 13b218dc895bcfb176bfe5616c6479c3982cfde7 Mon Sep 17 00:00:00 2001
From: Anatoly Trosinenko 
Date: Sat, 28 Jun 2025 11:09:01 +0300
Subject: [PATCH] [AArch64][PAC] Rework discriminator analysis in AUT and
 AUTPAC

Make use of post-processing the discriminator components by custom
inserter hook to eliminate duplication for DAGISel and GlobalISel and
improve cross-BB analysis for DAGISel.
---
 .../Target/AArch64/AArch64ISelDAGToDAG.cpp|  51 +---
 .../Target/AArch64/AArch64ISelLowering.cpp|  10 +
 llvm/lib/Target/AArch64/AArch64InstrInfo.td   |   2 +
 .../GISel/AArch64InstructionSelector.cpp  |  27 +-
 llvm/test/CodeGen/AArch64/ptrauth-isel.ll | 235 +-
 5 files changed, 256 insertions(+), 69 deletions(-)

diff --git a/llvm/lib/Target/AArch64/AArch64ISelDAGToDAG.cpp 
b/llvm/lib/Target/AArch64/AArch64ISelDAGToDAG.cpp
index da617b7e19266..5d3fd48f448b5 100644
--- a/llvm/lib/Target/AArch64/AArch64ISelDAGToDAG.cpp
+++ b/llvm/lib/Target/AArch64/AArch64ISelDAGToDAG.cpp
@@ -1487,39 +1487,6 @@ void AArch64DAGToDAGISel::SelectTable(SDNode *N, 
unsigned NumVecs, unsigned Opc,
   ReplaceNode(N, CurDAG->getMachineNode(Opc, dl, VT, Ops));
 }
 
-static std::tuple
-extractPtrauthBlendDiscriminators(SDValue Disc, SelectionDAG *DAG) {
-  SDLoc DL(Disc);
-  SDValue AddrDisc;
-  SDValue ConstDisc;
-
-  // If this is a blend, remember the constant and address discriminators.
-  // Otherwise, it's either a constant discriminator, or a non-blended
-  // address discriminator.
-  if (Disc->getOpcode() == ISD::INTRINSIC_WO_CHAIN &&
-  Disc->getConstantOperandVal(0) == Intrinsic::ptrauth_blend) {
-AddrDisc = Disc->getOperand(1);
-ConstDisc = Disc->getOperand(2);
-  } else {
-ConstDisc = Disc;
-  }
-
-  // If the constant discriminator (either the blend RHS, or the entire
-  // discriminator value) isn't a 16-bit constant, bail out, and let the
-  // discriminator be computed separately.
-  auto *ConstDiscN = dyn_cast(ConstDisc);
-  if (!ConstDiscN || !isUInt<16>(ConstDiscN->getZExtValue()))
-return std::make_tuple(DAG->getTargetConstant(0, DL, MVT::i64), Disc);
-
-  // If there's no address discriminator, use XZR directly.
-  if (!AddrDisc)
-AddrDisc = DAG->getRegister(AArch64::XZR, MVT::i64);
-
-  return std::make_tuple(
-  DAG->getTargetConstant(ConstDiscN->getZExtValue(), DL, MVT::i64),
-  AddrDisc);
-}
-
 void AArch64DAGToDAGISel::SelectPtrauthAuth(SDNode *N) {
   SDLoc DL(N);
   // IntrinsicID is operand #0
@@ -1530,13 +1497,11 @@ void AArch64DAGToDAGISel::SelectPtrauthAuth(SDNode *N) {
   unsigned AUTKeyC = cast(AUTKey)->getZExtValue();
   AUTKey = CurDAG->getTargetConstant(AUTKeyC, DL, MVT::i64);
 
-  SDValue AUTAddrDisc, AUTConstDisc;
-  std::tie(AUTConstDisc, AUTAddrDisc) =
-  extractPtrauthBlendDiscriminators(AUTDisc, CurDAG);
+  SDValue Zero = CurDAG->getTargetConstant(0, DL, MVT::i64);
 
   SDValue X16Copy = CurDAG->getCopyToReg(CurDAG->getEntryNode(), DL,
  AArch64::X16, Val, SDValue());
-  SDValue Ops[] = {AUTKey, AUTConstDisc, AUTAddrDisc, X16Copy.getValue(1)};
+  SDValue Ops[] = {AUTKey, Zero, AUTDisc, X16Copy.getValue(1)};
 
   SDNode *AUT = CurDAG->getMachineNode(AArch64::AUT, DL, MVT::i64, Ops);
   ReplaceNode(N, AUT);
@@ -1557,19 +1522,13 @@ void AArch64DAGToDAGISel::SelectPtrauthResign(SDNode 
*N) {
   AUTKey = CurDAG->getTargetConstant(AUTKeyC, DL, MVT::i64);
   PACKey = CurDAG->getTargetConstant(PACKeyC, DL, MVT::i64);
 
-  SDValue AUTAddrDisc, AUTConstDisc;
-  std::tie(AUTConstDisc, AUTAddrDisc) =
-  extractPtrauthBlendDiscriminators(AUTDisc, CurDAG);
-
-  SDValue PACAddrDisc, PACConstDisc;
-  std::tie(PACConstDisc, PACAddrDisc) =
-  extractPtrauthBlendDiscriminators(PACDisc, CurDAG);
+  SDValue Zero = CurDAG->getTargetConstant(0, DL, MVT::i64);
 
   SDValue X16Copy = CurDAG->getCopyToReg(CurDAG->getEntryNode(), DL,
  AArch64::X16, Val, SDValue());
 
-  SDValue Ops[] = {AUTKey,   AUTConstDisc, AUTAddrDisc,PACKey,
-   PACConstDisc, PACAddrDisc,  X16Copy.getValue(1)};
+  SDValue Ops[] = {
+  AUTKey, Zero, AUTDisc, PACKey, Zero, PACDisc, X16Copy.getValue(1)};
 
   SDNode *AUTPAC = CurDAG->getMachineNode(AArch64::AUTPAC, DL, MVT::i64, Ops);
   ReplaceNode(N, AUTPAC);
diff --git a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp 
b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
index 17f9f36474d9f..f6d763b3aef1a 100644
--- a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
+++ b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
@@ -3242,10 +3242,20 @@ MachineBasicBlock 
*AArch64TargetLowering::EmitInstrWithCustomInserter(
   case AArch64::MOVT_TIZ_PSEUDO:
 return EmitZTInstr(MI, BB, AArch64::MOVT_TIZ, /*Op0IsDef=*/true);
 
+  case AArch64::AUT:
+fixupBlendComponents(MI, BB, MI.getOperand(1), MI.getOperand(2),
+   

[llvm-branch-commits] [llvm] [AArch64][PAC] Rework discriminator analysis in AUT and AUTPAC (PR #146489)

2025-07-04 Thread Anatoly Trosinenko via llvm-branch-commits

https://github.com/atrosinenko updated 
https://github.com/llvm/llvm-project/pull/146489

>From 13b218dc895bcfb176bfe5616c6479c3982cfde7 Mon Sep 17 00:00:00 2001
From: Anatoly Trosinenko 
Date: Sat, 28 Jun 2025 11:09:01 +0300
Subject: [PATCH] [AArch64][PAC] Rework discriminator analysis in AUT and
 AUTPAC

Make use of post-processing the discriminator components by custom
inserter hook to eliminate duplication for DAGISel and GlobalISel and
improve cross-BB analysis for DAGISel.
---
 .../Target/AArch64/AArch64ISelDAGToDAG.cpp|  51 +---
 .../Target/AArch64/AArch64ISelLowering.cpp|  10 +
 llvm/lib/Target/AArch64/AArch64InstrInfo.td   |   2 +
 .../GISel/AArch64InstructionSelector.cpp  |  27 +-
 llvm/test/CodeGen/AArch64/ptrauth-isel.ll | 235 +-
 5 files changed, 256 insertions(+), 69 deletions(-)

diff --git a/llvm/lib/Target/AArch64/AArch64ISelDAGToDAG.cpp 
b/llvm/lib/Target/AArch64/AArch64ISelDAGToDAG.cpp
index da617b7e19266..5d3fd48f448b5 100644
--- a/llvm/lib/Target/AArch64/AArch64ISelDAGToDAG.cpp
+++ b/llvm/lib/Target/AArch64/AArch64ISelDAGToDAG.cpp
@@ -1487,39 +1487,6 @@ void AArch64DAGToDAGISel::SelectTable(SDNode *N, 
unsigned NumVecs, unsigned Opc,
   ReplaceNode(N, CurDAG->getMachineNode(Opc, dl, VT, Ops));
 }
 
-static std::tuple
-extractPtrauthBlendDiscriminators(SDValue Disc, SelectionDAG *DAG) {
-  SDLoc DL(Disc);
-  SDValue AddrDisc;
-  SDValue ConstDisc;
-
-  // If this is a blend, remember the constant and address discriminators.
-  // Otherwise, it's either a constant discriminator, or a non-blended
-  // address discriminator.
-  if (Disc->getOpcode() == ISD::INTRINSIC_WO_CHAIN &&
-  Disc->getConstantOperandVal(0) == Intrinsic::ptrauth_blend) {
-AddrDisc = Disc->getOperand(1);
-ConstDisc = Disc->getOperand(2);
-  } else {
-ConstDisc = Disc;
-  }
-
-  // If the constant discriminator (either the blend RHS, or the entire
-  // discriminator value) isn't a 16-bit constant, bail out, and let the
-  // discriminator be computed separately.
-  auto *ConstDiscN = dyn_cast(ConstDisc);
-  if (!ConstDiscN || !isUInt<16>(ConstDiscN->getZExtValue()))
-return std::make_tuple(DAG->getTargetConstant(0, DL, MVT::i64), Disc);
-
-  // If there's no address discriminator, use XZR directly.
-  if (!AddrDisc)
-AddrDisc = DAG->getRegister(AArch64::XZR, MVT::i64);
-
-  return std::make_tuple(
-  DAG->getTargetConstant(ConstDiscN->getZExtValue(), DL, MVT::i64),
-  AddrDisc);
-}
-
 void AArch64DAGToDAGISel::SelectPtrauthAuth(SDNode *N) {
   SDLoc DL(N);
   // IntrinsicID is operand #0
@@ -1530,13 +1497,11 @@ void AArch64DAGToDAGISel::SelectPtrauthAuth(SDNode *N) {
   unsigned AUTKeyC = cast(AUTKey)->getZExtValue();
   AUTKey = CurDAG->getTargetConstant(AUTKeyC, DL, MVT::i64);
 
-  SDValue AUTAddrDisc, AUTConstDisc;
-  std::tie(AUTConstDisc, AUTAddrDisc) =
-  extractPtrauthBlendDiscriminators(AUTDisc, CurDAG);
+  SDValue Zero = CurDAG->getTargetConstant(0, DL, MVT::i64);
 
   SDValue X16Copy = CurDAG->getCopyToReg(CurDAG->getEntryNode(), DL,
  AArch64::X16, Val, SDValue());
-  SDValue Ops[] = {AUTKey, AUTConstDisc, AUTAddrDisc, X16Copy.getValue(1)};
+  SDValue Ops[] = {AUTKey, Zero, AUTDisc, X16Copy.getValue(1)};
 
   SDNode *AUT = CurDAG->getMachineNode(AArch64::AUT, DL, MVT::i64, Ops);
   ReplaceNode(N, AUT);
@@ -1557,19 +1522,13 @@ void AArch64DAGToDAGISel::SelectPtrauthResign(SDNode 
*N) {
   AUTKey = CurDAG->getTargetConstant(AUTKeyC, DL, MVT::i64);
   PACKey = CurDAG->getTargetConstant(PACKeyC, DL, MVT::i64);
 
-  SDValue AUTAddrDisc, AUTConstDisc;
-  std::tie(AUTConstDisc, AUTAddrDisc) =
-  extractPtrauthBlendDiscriminators(AUTDisc, CurDAG);
-
-  SDValue PACAddrDisc, PACConstDisc;
-  std::tie(PACConstDisc, PACAddrDisc) =
-  extractPtrauthBlendDiscriminators(PACDisc, CurDAG);
+  SDValue Zero = CurDAG->getTargetConstant(0, DL, MVT::i64);
 
   SDValue X16Copy = CurDAG->getCopyToReg(CurDAG->getEntryNode(), DL,
  AArch64::X16, Val, SDValue());
 
-  SDValue Ops[] = {AUTKey,   AUTConstDisc, AUTAddrDisc,PACKey,
-   PACConstDisc, PACAddrDisc,  X16Copy.getValue(1)};
+  SDValue Ops[] = {
+  AUTKey, Zero, AUTDisc, PACKey, Zero, PACDisc, X16Copy.getValue(1)};
 
   SDNode *AUTPAC = CurDAG->getMachineNode(AArch64::AUTPAC, DL, MVT::i64, Ops);
   ReplaceNode(N, AUTPAC);
diff --git a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp 
b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
index 17f9f36474d9f..f6d763b3aef1a 100644
--- a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
+++ b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
@@ -3242,10 +3242,20 @@ MachineBasicBlock 
*AArch64TargetLowering::EmitInstrWithCustomInserter(
   case AArch64::MOVT_TIZ_PSEUDO:
 return EmitZTInstr(MI, BB, AArch64::MOVT_TIZ, /*Op0IsDef=*/true);
 
+  case AArch64::AUT:
+fixupBlendComponents(MI, BB, MI.getOperand(1), MI.getOperand(2),
+   

[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147115)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic created 
https://github.com/llvm/llvm-project/pull/147115

At the moment, when we report diagnostics from `SemaHLSL` we only provide the 
source location of the root signature attr. This allows for significantly less 
helpful diagnostics (for eg. reporting resource range overlaps).

This pr implements a way to retain the source location of a root element when 
it is parsed, so that we can output the `SourceLocation` of each root element 
that causes the overlap in the diagnostics during semantic analysis.

This pr defines a wrapper struct `clang::hlsl::RootSignatureElement` in 
`SemaHLSL` that will contain the underlying `RootElement` and can hold any 
additional diagnostic information. This struct will be what is used in 
`HLSLRootSignatureParser` and in `SemaHLSL`. Then the diagnostic information 
will be stripped and the underlying element will be stored in the 
`RootSignatureDecl`.

For the reporting of diagnostics, we can now use the retained `SourceLocation` 
of each `RootElement` when reporting the range overlap, and we can add a `note` 
diagnostic to highlight the other root element as well.

- Defines `RootSignatureElement` in the `hlsl` namespace in `SemaHLSL` (defined 
in `SemaHLSL` because `Parse` has a dependency on `Sema`)
- Updates parsing logic to construct `RootSignatureElement`s and retain the 
source loction in `ParseHLSLRootSignature`
- Updates `SemaHLSL` when it constructs the `RootSignatureDecl` to take the new 
`RootSignatureElement` and store the underlying `RootElement`
- Updates the current tests to ensure the new `note` diagnostic is produced and 
that the `SourceLocation` is seen
- Adds a test to demonstrate the `SourceLocation` of both elements being 
correctly pointed out

Resolves: https://github.com/llvm/llvm-project/issues/145819

>From 4a5cde3f77dc0c371d1f33b10be9507d3aeff3e3 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 27 Jun 2025 18:36:38 +
Subject: [PATCH 1/8] nfc: introduce wrapper `RootSignatureElement` around
 `RootElement` to retain clang diag info

---
 .../clang/Parse/ParseHLSLRootSignature.h  |  17 ++-
 clang/include/clang/Sema/SemaHLSL.h   |  10 +-
 clang/lib/Parse/ParseDeclCXX.cpp  |   2 +-
 clang/lib/Parse/ParseHLSLRootSignature.cpp|  21 ++--
 clang/lib/Sema/SemaHLSL.cpp   |   6 +-
 .../Parse/ParseHLSLRootSignatureTest.cpp  | 115 +-
 6 files changed, 99 insertions(+), 72 deletions(-)

diff --git a/clang/include/clang/Parse/ParseHLSLRootSignature.h 
b/clang/include/clang/Parse/ParseHLSLRootSignature.h
index b0ef617a13c28..53001d2ba461f 100644
--- a/clang/include/clang/Parse/ParseHLSLRootSignature.h
+++ b/clang/include/clang/Parse/ParseHLSLRootSignature.h
@@ -26,10 +26,22 @@
 namespace clang {
 namespace hlsl {
 
+// Introduce a wrapper struct around the underlying RootElement. This structure
+// will retain extra clang diagnostic information that is not available in 
llvm.
+struct RootSignatureElement {
+  RootSignatureElement(llvm::hlsl::rootsig::RootElement Element)
+  : Element(Element) {}
+
+  const llvm::hlsl::rootsig::RootElement &getElement() const { return Element; 
}
+
+private:
+  llvm::hlsl::rootsig::RootElement Element;
+};
+
 class RootSignatureParser {
 public:
   RootSignatureParser(llvm::dxbc::RootSignatureVersion Version,
-  SmallVector &Elements,
+  SmallVector &Elements,
   StringLiteral *Signature, Preprocessor &PP);
 
   /// Consumes tokens from the Lexer and constructs the in-memory
@@ -196,7 +208,8 @@ class RootSignatureParser {
 
 private:
   llvm::dxbc::RootSignatureVersion Version;
-  SmallVector &Elements;
+  SmallVector &Elements;
+
   clang::StringLiteral *Signature;
   RootSignatureLexer Lexer;
   clang::Preprocessor &PP;
diff --git a/clang/include/clang/Sema/SemaHLSL.h 
b/clang/include/clang/Sema/SemaHLSL.h
index 7d7eae4db532c..1af706da702c2 100644
--- a/clang/include/clang/Sema/SemaHLSL.h
+++ b/clang/include/clang/Sema/SemaHLSL.h
@@ -32,6 +32,10 @@ class ParsedAttr;
 class Scope;
 class VarDecl;
 
+namespace hlsl {
+struct RootSignatureElement;
+}
+
 using llvm::dxil::ResourceClass;
 
 // FIXME: This can be hidden (as static function in SemaHLSL.cpp) once we no
@@ -130,9 +134,9 @@ class SemaHLSL : public SemaBase {
 
   /// Creates the Root Signature decl of the parsed Root Signature elements
   /// onto the AST and push it onto current Scope
-  void ActOnFinishRootSignatureDecl(
-  SourceLocation Loc, IdentifierInfo *DeclIdent,
-  SmallVector &Elements);
+  void
+  ActOnFinishRootSignatureDecl(SourceLocation Loc, IdentifierInfo *DeclIdent,
+   ArrayRef Elements);
 
   // Returns true when D is invalid and a diagnostic was produced
   bool handleRootSignatureDecl(HLSLRootSignatureDecl *D, SourceLocation Loc);
diff --git a/clang/lib/Parse/ParseDeclCXX.cpp b/clang/lib/Parse/ParseDeclCXX.cpp
index d3bc6f1e89832..d06bb6a25efa5 100

[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147115)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-clang

Author: Finn Plummer (inbelic)


Changes

At the moment, when we report diagnostics from `SemaHLSL` we only provide the 
source location of the root signature attr. This allows for significantly less 
helpful diagnostics (for eg. reporting resource range overlaps).

This pr implements a way to retain the source location of a root element when 
it is parsed, so that we can output the `SourceLocation` of each root element 
that causes the overlap in the diagnostics during semantic analysis.

This pr defines a wrapper struct `clang::hlsl::RootSignatureElement` in 
`SemaHLSL` that will contain the underlying `RootElement` and can hold any 
additional diagnostic information. This struct will be what is used in 
`HLSLRootSignatureParser` and in `SemaHLSL`. Then the diagnostic information 
will be stripped and the underlying element will be stored in the 
`RootSignatureDecl`.

For the reporting of diagnostics, we can now use the retained `SourceLocation` 
of each `RootElement` when reporting the range overlap, and we can add a `note` 
diagnostic to highlight the other root element as well.

- Defines `RootSignatureElement` in the `hlsl` namespace in `SemaHLSL` (defined 
in `SemaHLSL` because `Parse` has a dependency on `Sema`)
- Updates parsing logic to construct `RootSignatureElement`s and retain the 
source loction in `ParseHLSLRootSignature`
- Updates `SemaHLSL` when it constructs the `RootSignatureDecl` to take the new 
`RootSignatureElement` and store the underlying `RootElement`
- Updates the current tests to ensure the new `note` diagnostic is produced and 
that the `SourceLocation` is seen
- Adds a test to demonstrate the `SourceLocation` of both elements being 
correctly pointed out

Resolves: https://github.com/llvm/llvm-project/issues/145819

---

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


9 Files Affected:

- (modified) clang/include/clang/Basic/DiagnosticSemaKinds.td (+1) 
- (modified) clang/include/clang/Parse/ParseHLSLRootSignature.h (+4-2) 
- (modified) clang/include/clang/Sema/SemaHLSL.h (+25-4) 
- (modified) clang/lib/Parse/ParseDeclCXX.cpp (+1-1) 
- (modified) clang/lib/Parse/ParseHLSLRootSignature.cpp (+19-8) 
- (modified) clang/lib/Sema/SemaHLSL.cpp (+38-10) 
- (modified) clang/test/SemaHLSL/RootSignature-resource-ranges-err.hlsl (+41) 
- (modified) clang/unittests/Parse/ParseHLSLRootSignatureTest.cpp (+74-73) 
- (modified) llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h (+3) 


``diff
diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td 
b/clang/include/clang/Basic/DiagnosticSemaKinds.td
index 968edd967e0c5..4fe0abb972a61 100644
--- a/clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -13079,6 +13079,7 @@ def err_hlsl_resource_range_overlap: Error<
   "resource ranges %sub{subst_hlsl_format_ranges}0,1,2,3 and 
%sub{subst_hlsl_format_ranges}4,5,6,7 "
   "overlap within space = %8 and visibility = "
   "%select{All|Vertex|Hull|Domain|Geometry|Pixel|Amplification|Mesh}9">;
+def note_hlsl_resource_range_here: Note<"overlapping resource range here">;
 
 // Layout randomization diagnostics.
 def err_non_designated_init_used : Error<
diff --git a/clang/include/clang/Parse/ParseHLSLRootSignature.h 
b/clang/include/clang/Parse/ParseHLSLRootSignature.h
index b0ef617a13c28..9ef5b64d7b4a5 100644
--- a/clang/include/clang/Parse/ParseHLSLRootSignature.h
+++ b/clang/include/clang/Parse/ParseHLSLRootSignature.h
@@ -17,6 +17,7 @@
 #include "clang/Basic/DiagnosticParse.h"
 #include "clang/Lex/LexHLSLRootSignature.h"
 #include "clang/Lex/Preprocessor.h"
+#include "clang/Sema/SemaHLSL.h"
 
 #include "llvm/ADT/SmallVector.h"
 #include "llvm/ADT/StringRef.h"
@@ -29,7 +30,7 @@ namespace hlsl {
 class RootSignatureParser {
 public:
   RootSignatureParser(llvm::dxbc::RootSignatureVersion Version,
-  SmallVector &Elements,
+  SmallVector &Elements,
   StringLiteral *Signature, Preprocessor &PP);
 
   /// Consumes tokens from the Lexer and constructs the in-memory
@@ -196,7 +197,8 @@ class RootSignatureParser {
 
 private:
   llvm::dxbc::RootSignatureVersion Version;
-  SmallVector &Elements;
+  SmallVector &Elements;
+
   clang::StringLiteral *Signature;
   RootSignatureLexer Lexer;
   clang::Preprocessor &PP;
diff --git a/clang/include/clang/Sema/SemaHLSL.h 
b/clang/include/clang/Sema/SemaHLSL.h
index 7d7eae4db532c..910e0e640796b 100644
--- a/clang/include/clang/Sema/SemaHLSL.h
+++ b/clang/include/clang/Sema/SemaHLSL.h
@@ -32,6 +32,25 @@ class ParsedAttr;
 class Scope;
 class VarDecl;
 
+namespace hlsl {
+
+// Introduce a wrapper struct around the underlying RootElement. This structure
+// will retain extra clang diagnostic information that is not available in 
llvm.
+struct RootSignatureElement {
+  RootSignatureElement(SourceLocation Loc,
+ 

[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147094)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

inbelic wrote:

Whoops, accidently pushed to the wrong upstream branch. Looks like I can't 
unmerge it to the stacked branch...

https://github.com/llvm/llvm-project/pull/147094
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147094)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic closed 
https://github.com/llvm/llvm-project/pull/147094
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147115)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic updated 
https://github.com/llvm/llvm-project/pull/147115

>From 4a5cde3f77dc0c371d1f33b10be9507d3aeff3e3 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 27 Jun 2025 18:36:38 +
Subject: [PATCH 1/9] nfc: introduce wrapper `RootSignatureElement` around
 `RootElement` to retain clang diag info

---
 .../clang/Parse/ParseHLSLRootSignature.h  |  17 ++-
 clang/include/clang/Sema/SemaHLSL.h   |  10 +-
 clang/lib/Parse/ParseDeclCXX.cpp  |   2 +-
 clang/lib/Parse/ParseHLSLRootSignature.cpp|  21 ++--
 clang/lib/Sema/SemaHLSL.cpp   |   6 +-
 .../Parse/ParseHLSLRootSignatureTest.cpp  | 115 +-
 6 files changed, 99 insertions(+), 72 deletions(-)

diff --git a/clang/include/clang/Parse/ParseHLSLRootSignature.h 
b/clang/include/clang/Parse/ParseHLSLRootSignature.h
index b0ef617a13c28..53001d2ba461f 100644
--- a/clang/include/clang/Parse/ParseHLSLRootSignature.h
+++ b/clang/include/clang/Parse/ParseHLSLRootSignature.h
@@ -26,10 +26,22 @@
 namespace clang {
 namespace hlsl {
 
+// Introduce a wrapper struct around the underlying RootElement. This structure
+// will retain extra clang diagnostic information that is not available in 
llvm.
+struct RootSignatureElement {
+  RootSignatureElement(llvm::hlsl::rootsig::RootElement Element)
+  : Element(Element) {}
+
+  const llvm::hlsl::rootsig::RootElement &getElement() const { return Element; 
}
+
+private:
+  llvm::hlsl::rootsig::RootElement Element;
+};
+
 class RootSignatureParser {
 public:
   RootSignatureParser(llvm::dxbc::RootSignatureVersion Version,
-  SmallVector &Elements,
+  SmallVector &Elements,
   StringLiteral *Signature, Preprocessor &PP);
 
   /// Consumes tokens from the Lexer and constructs the in-memory
@@ -196,7 +208,8 @@ class RootSignatureParser {
 
 private:
   llvm::dxbc::RootSignatureVersion Version;
-  SmallVector &Elements;
+  SmallVector &Elements;
+
   clang::StringLiteral *Signature;
   RootSignatureLexer Lexer;
   clang::Preprocessor &PP;
diff --git a/clang/include/clang/Sema/SemaHLSL.h 
b/clang/include/clang/Sema/SemaHLSL.h
index 7d7eae4db532c..1af706da702c2 100644
--- a/clang/include/clang/Sema/SemaHLSL.h
+++ b/clang/include/clang/Sema/SemaHLSL.h
@@ -32,6 +32,10 @@ class ParsedAttr;
 class Scope;
 class VarDecl;
 
+namespace hlsl {
+struct RootSignatureElement;
+}
+
 using llvm::dxil::ResourceClass;
 
 // FIXME: This can be hidden (as static function in SemaHLSL.cpp) once we no
@@ -130,9 +134,9 @@ class SemaHLSL : public SemaBase {
 
   /// Creates the Root Signature decl of the parsed Root Signature elements
   /// onto the AST and push it onto current Scope
-  void ActOnFinishRootSignatureDecl(
-  SourceLocation Loc, IdentifierInfo *DeclIdent,
-  SmallVector &Elements);
+  void
+  ActOnFinishRootSignatureDecl(SourceLocation Loc, IdentifierInfo *DeclIdent,
+   ArrayRef Elements);
 
   // Returns true when D is invalid and a diagnostic was produced
   bool handleRootSignatureDecl(HLSLRootSignatureDecl *D, SourceLocation Loc);
diff --git a/clang/lib/Parse/ParseDeclCXX.cpp b/clang/lib/Parse/ParseDeclCXX.cpp
index d3bc6f1e89832..d06bb6a25efa5 100644
--- a/clang/lib/Parse/ParseDeclCXX.cpp
+++ b/clang/lib/Parse/ParseDeclCXX.cpp
@@ -4951,7 +4951,7 @@ void 
Parser::ParseHLSLRootSignatureAttributeArgs(ParsedAttributes &Attrs) {
   // signature string and construct the in-memory elements
   if (!Found) {
 // Invoke the root signature parser to construct the in-memory constructs
-SmallVector RootElements;
+SmallVector RootElements;
 hlsl::RootSignatureParser Parser(getLangOpts().HLSLRootSigVer, 
RootElements,
  Signature, PP);
 if (Parser.parse()) {
diff --git a/clang/lib/Parse/ParseHLSLRootSignature.cpp 
b/clang/lib/Parse/ParseHLSLRootSignature.cpp
index ebaf7ba60fa17..76e50fb85c8d7 100644
--- a/clang/lib/Parse/ParseHLSLRootSignature.cpp
+++ b/clang/lib/Parse/ParseHLSLRootSignature.cpp
@@ -19,33 +19,34 @@ using TokenKind = RootSignatureToken::Kind;
 
 RootSignatureParser::RootSignatureParser(
 llvm::dxbc::RootSignatureVersion Version,
-SmallVector &Elements, StringLiteral *Signature,
+SmallVector &Elements, StringLiteral *Signature,
 Preprocessor &PP)
 : Version(Version), Elements(Elements), Signature(Signature),
   Lexer(Signature->getString()), PP(PP), CurToken(0) {}
 
 bool RootSignatureParser::parse() {
-  // Iterate as many RootElements as possible
+  // Iterate as many RootSignatureElements as possible
   do {
+std::optional Element = std::nullopt;
 if (tryConsumeExpectedToken(TokenKind::kw_RootFlags)) {
   auto Flags = parseRootFlags();
   if (!Flags.has_value())
 return true;
-  Elements.push_back(*Flags);
+  Element = RootSignatureElement(*Flags);
 }
 
 if (tryConsumeExpectedToken(TokenKind::kw_RootConstants)) {
   auto Co

[llvm-branch-commits] [clang] [llvm] [NFC][HLSL] Move resource range logic from `SemaHLSL` to `RootSignatureValidations` (PR #147117)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic created 
https://github.com/llvm/llvm-project/pull/147117

This pr abstracts out the logic of detecting resource range overlap from 
`SemaHLSL` into the `RootSignatureValidations` library.

For more context see linked issue.

- Moves the validation logic from `SemaHLSL` to `RootSignatureValidations`
- Updates `SemaHLSL` to use the new interface for the validations

Resolves: https://github.com/llvm/llvm-project/issues/146393

>From 969f316004ae500d707be081e6f2f4abc669fff3 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 27 Jun 2025 19:58:15 +
Subject: [PATCH] nfc: move collection of overlaps to
 `RootSignatureValidations`

---
 clang/lib/Sema/SemaHLSL.cpp   | 101 ++
 .../Frontend/HLSL/RootSignatureValidations.h  |  32 ++
 .../HLSL/RootSignatureValidations.cpp |  73 +
 3 files changed, 115 insertions(+), 91 deletions(-)

diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp
index 3feb27ac44bd6..18b84c33b39c8 100644
--- a/clang/lib/Sema/SemaHLSL.cpp
+++ b/clang/lib/Sema/SemaHLSL.cpp
@@ -1083,29 +1083,8 @@ void SemaHLSL::ActOnFinishRootSignatureDecl(
 
 bool SemaHLSL::handleRootSignatureElements(
 ArrayRef Elements) {
-  // The following conducts analysis on resource ranges to detect and report
-  // any overlaps in resource ranges.
-  //
-  // A resource range overlaps with another resource range if they have:
-  // - equivalent ResourceClass (SRV, UAV, CBuffer, Sampler)
-  // - equivalent resource space
-  // - overlapping visbility
-  //
-  // The following algorithm is implemented in the following steps:
-  //
-  // 1. Collect RangeInfo from relevant RootElements:
-  //   - RangeInfo will retain the interval, ResourceClass, Space and 
Visibility
-  // 2. Sort the RangeInfo's such that they are grouped together by
-  //  ResourceClass and Space (GroupT defined below)
-  // 3. Iterate through the collected RangeInfos by their groups
-  //   - For each group we will have a ResourceRange for each visibility
-  //   - As we iterate through we will:
-  //  A: Insert the current RangeInfo into the corresponding Visibility
-  //   ResourceRange
-  //  B: Check for overlap with any overlapping Visibility ResourceRange
   using RangeInfo = llvm::hlsl::rootsig::RangeInfo;
-  using ResourceRange = llvm::hlsl::rootsig::ResourceRange;
-  using GroupT = std::pair;
+  using OverlappingRanges = llvm::hlsl::rootsig::OverlappingRanges;
 
   // Introduce a mapping from the collected RangeInfos back to the
   // RootSignatureElement that will retain its diagnostics info
@@ -1188,40 +1167,10 @@ bool SemaHLSL::handleRootSignatureElements(
 }
   }
 
-  // 2. Sort the RangeInfo's by their GroupT to form groupings
-  std::sort(Infos.begin(), Infos.end(), [](RangeInfo A, RangeInfo B) {
-return std::tie(A.Class, A.Space) < std::tie(B.Class, B.Space);
-  });
-
-  // 3. First we will init our state to track:
-  if (Infos.size() == 0)
-return false; // No ranges to overlap
-  GroupT CurGroup = {Infos[0].Class, Infos[0].Space};
-  bool HadOverlap = false;
-
-  // Create a ResourceRange for each Visibility
-  ResourceRange::MapT::Allocator Allocator;
-  std::array Ranges = {
-  ResourceRange(Allocator), // All
-  ResourceRange(Allocator), // Vertex
-  ResourceRange(Allocator), // Hull
-  ResourceRange(Allocator), // Domain
-  ResourceRange(Allocator), // Geometry
-  ResourceRange(Allocator), // Pixel
-  ResourceRange(Allocator), // Amplification
-  ResourceRange(Allocator), // Mesh
-  };
-
-  // Reset the ResourceRanges for when we iterate through a new group
-  auto ClearRanges = [&Ranges]() {
-for (ResourceRange &Range : Ranges)
-  Range.clear();
-  };
-
   // Helper to report diagnostics
-  auto ReportOverlap = [this, InfoIndexMap, &HadOverlap](
-   const RangeInfo *Info, const RangeInfo *OInfo) {
-HadOverlap = true;
+  auto ReportOverlap = [this, InfoIndexMap](OverlappingRanges Overlap) {
+const RangeInfo *Info = Overlap.A;
+const RangeInfo *OInfo = Overlap.B;
 auto CommonVis = Info->Visibility == llvm::dxbc::ShaderVisibility::All
  ? OInfo->Visibility
  : Info->Visibility;
@@ -1240,42 +1189,12 @@ bool SemaHLSL::handleRootSignatureElements(
 this->Diag(OInfoLoc, diag::note_hlsl_resource_range_here);
   };
 
-  // 3: Iterate through collected RangeInfos
-  for (const RangeInfo &Info : Infos) {
-GroupT InfoGroup = {Info.Class, Info.Space};
-// Reset our ResourceRanges when we enter a new group
-if (CurGroup != InfoGroup) {
-  ClearRanges();
-  CurGroup = InfoGroup;
-}
-
-// 3A: Insert range info into corresponding Visibility ResourceRange
-ResourceRange &VisRange = Ranges[llvm::to_underlying(Info.Visibility)];
-if (std::optional Overlapping = VisRange.insert(Info))
-  ReportOverlap(&Info, Overlapping.value());
-
-// 3B: Check for

[llvm-branch-commits] [clang] [llvm] [NFC][HLSL] Move resource range logic from `SemaHLSL` to `RootSignatureValidations` (PR #147117)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-clang

Author: Finn Plummer (inbelic)


Changes

This pr abstracts out the logic of detecting resource range overlap from 
`SemaHLSL` into the `RootSignatureValidations` library.

For more context see linked issue.

- Moves the validation logic from `SemaHLSL` to `RootSignatureValidations`
- Updates `SemaHLSL` to use the new interface for the validations

Resolves: https://github.com/llvm/llvm-project/issues/146393

---
Full diff: https://github.com/llvm/llvm-project/pull/147117.diff


3 Files Affected:

- (modified) clang/lib/Sema/SemaHLSL.cpp (+10-91) 
- (modified) llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h (+32) 
- (modified) llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp (+73) 


``diff
diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp
index 3feb27ac44bd6..18b84c33b39c8 100644
--- a/clang/lib/Sema/SemaHLSL.cpp
+++ b/clang/lib/Sema/SemaHLSL.cpp
@@ -1083,29 +1083,8 @@ void SemaHLSL::ActOnFinishRootSignatureDecl(
 
 bool SemaHLSL::handleRootSignatureElements(
 ArrayRef Elements) {
-  // The following conducts analysis on resource ranges to detect and report
-  // any overlaps in resource ranges.
-  //
-  // A resource range overlaps with another resource range if they have:
-  // - equivalent ResourceClass (SRV, UAV, CBuffer, Sampler)
-  // - equivalent resource space
-  // - overlapping visbility
-  //
-  // The following algorithm is implemented in the following steps:
-  //
-  // 1. Collect RangeInfo from relevant RootElements:
-  //   - RangeInfo will retain the interval, ResourceClass, Space and 
Visibility
-  // 2. Sort the RangeInfo's such that they are grouped together by
-  //  ResourceClass and Space (GroupT defined below)
-  // 3. Iterate through the collected RangeInfos by their groups
-  //   - For each group we will have a ResourceRange for each visibility
-  //   - As we iterate through we will:
-  //  A: Insert the current RangeInfo into the corresponding Visibility
-  //   ResourceRange
-  //  B: Check for overlap with any overlapping Visibility ResourceRange
   using RangeInfo = llvm::hlsl::rootsig::RangeInfo;
-  using ResourceRange = llvm::hlsl::rootsig::ResourceRange;
-  using GroupT = std::pair;
+  using OverlappingRanges = llvm::hlsl::rootsig::OverlappingRanges;
 
   // Introduce a mapping from the collected RangeInfos back to the
   // RootSignatureElement that will retain its diagnostics info
@@ -1188,40 +1167,10 @@ bool SemaHLSL::handleRootSignatureElements(
 }
   }
 
-  // 2. Sort the RangeInfo's by their GroupT to form groupings
-  std::sort(Infos.begin(), Infos.end(), [](RangeInfo A, RangeInfo B) {
-return std::tie(A.Class, A.Space) < std::tie(B.Class, B.Space);
-  });
-
-  // 3. First we will init our state to track:
-  if (Infos.size() == 0)
-return false; // No ranges to overlap
-  GroupT CurGroup = {Infos[0].Class, Infos[0].Space};
-  bool HadOverlap = false;
-
-  // Create a ResourceRange for each Visibility
-  ResourceRange::MapT::Allocator Allocator;
-  std::array Ranges = {
-  ResourceRange(Allocator), // All
-  ResourceRange(Allocator), // Vertex
-  ResourceRange(Allocator), // Hull
-  ResourceRange(Allocator), // Domain
-  ResourceRange(Allocator), // Geometry
-  ResourceRange(Allocator), // Pixel
-  ResourceRange(Allocator), // Amplification
-  ResourceRange(Allocator), // Mesh
-  };
-
-  // Reset the ResourceRanges for when we iterate through a new group
-  auto ClearRanges = [&Ranges]() {
-for (ResourceRange &Range : Ranges)
-  Range.clear();
-  };
-
   // Helper to report diagnostics
-  auto ReportOverlap = [this, InfoIndexMap, &HadOverlap](
-   const RangeInfo *Info, const RangeInfo *OInfo) {
-HadOverlap = true;
+  auto ReportOverlap = [this, InfoIndexMap](OverlappingRanges Overlap) {
+const RangeInfo *Info = Overlap.A;
+const RangeInfo *OInfo = Overlap.B;
 auto CommonVis = Info->Visibility == llvm::dxbc::ShaderVisibility::All
  ? OInfo->Visibility
  : Info->Visibility;
@@ -1240,42 +1189,12 @@ bool SemaHLSL::handleRootSignatureElements(
 this->Diag(OInfoLoc, diag::note_hlsl_resource_range_here);
   };
 
-  // 3: Iterate through collected RangeInfos
-  for (const RangeInfo &Info : Infos) {
-GroupT InfoGroup = {Info.Class, Info.Space};
-// Reset our ResourceRanges when we enter a new group
-if (CurGroup != InfoGroup) {
-  ClearRanges();
-  CurGroup = InfoGroup;
-}
-
-// 3A: Insert range info into corresponding Visibility ResourceRange
-ResourceRange &VisRange = Ranges[llvm::to_underlying(Info.Visibility)];
-if (std::optional Overlapping = VisRange.insert(Info))
-  ReportOverlap(&Info, Overlapping.value());
-
-// 3B: Check for overlap in all overlapping Visibility ResourceRanges
-//
-// If the range that we are inserting has ShaderVisiblity::All it needs to
-// check f

[llvm-branch-commits] [clang] [llvm] [NFC][HLSL] Move resource range logic from `SemaHLSL` to `RootSignatureValidations` (PR #147117)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-hlsl

Author: Finn Plummer (inbelic)


Changes

This pr abstracts out the logic of detecting resource range overlap from 
`SemaHLSL` into the `RootSignatureValidations` library.

For more context see linked issue.

- Moves the validation logic from `SemaHLSL` to `RootSignatureValidations`
- Updates `SemaHLSL` to use the new interface for the validations

Resolves: https://github.com/llvm/llvm-project/issues/146393

---
Full diff: https://github.com/llvm/llvm-project/pull/147117.diff


3 Files Affected:

- (modified) clang/lib/Sema/SemaHLSL.cpp (+10-91) 
- (modified) llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h (+32) 
- (modified) llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp (+73) 


``diff
diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp
index 3feb27ac44bd6..18b84c33b39c8 100644
--- a/clang/lib/Sema/SemaHLSL.cpp
+++ b/clang/lib/Sema/SemaHLSL.cpp
@@ -1083,29 +1083,8 @@ void SemaHLSL::ActOnFinishRootSignatureDecl(
 
 bool SemaHLSL::handleRootSignatureElements(
 ArrayRef Elements) {
-  // The following conducts analysis on resource ranges to detect and report
-  // any overlaps in resource ranges.
-  //
-  // A resource range overlaps with another resource range if they have:
-  // - equivalent ResourceClass (SRV, UAV, CBuffer, Sampler)
-  // - equivalent resource space
-  // - overlapping visbility
-  //
-  // The following algorithm is implemented in the following steps:
-  //
-  // 1. Collect RangeInfo from relevant RootElements:
-  //   - RangeInfo will retain the interval, ResourceClass, Space and 
Visibility
-  // 2. Sort the RangeInfo's such that they are grouped together by
-  //  ResourceClass and Space (GroupT defined below)
-  // 3. Iterate through the collected RangeInfos by their groups
-  //   - For each group we will have a ResourceRange for each visibility
-  //   - As we iterate through we will:
-  //  A: Insert the current RangeInfo into the corresponding Visibility
-  //   ResourceRange
-  //  B: Check for overlap with any overlapping Visibility ResourceRange
   using RangeInfo = llvm::hlsl::rootsig::RangeInfo;
-  using ResourceRange = llvm::hlsl::rootsig::ResourceRange;
-  using GroupT = std::pair;
+  using OverlappingRanges = llvm::hlsl::rootsig::OverlappingRanges;
 
   // Introduce a mapping from the collected RangeInfos back to the
   // RootSignatureElement that will retain its diagnostics info
@@ -1188,40 +1167,10 @@ bool SemaHLSL::handleRootSignatureElements(
 }
   }
 
-  // 2. Sort the RangeInfo's by their GroupT to form groupings
-  std::sort(Infos.begin(), Infos.end(), [](RangeInfo A, RangeInfo B) {
-return std::tie(A.Class, A.Space) < std::tie(B.Class, B.Space);
-  });
-
-  // 3. First we will init our state to track:
-  if (Infos.size() == 0)
-return false; // No ranges to overlap
-  GroupT CurGroup = {Infos[0].Class, Infos[0].Space};
-  bool HadOverlap = false;
-
-  // Create a ResourceRange for each Visibility
-  ResourceRange::MapT::Allocator Allocator;
-  std::array Ranges = {
-  ResourceRange(Allocator), // All
-  ResourceRange(Allocator), // Vertex
-  ResourceRange(Allocator), // Hull
-  ResourceRange(Allocator), // Domain
-  ResourceRange(Allocator), // Geometry
-  ResourceRange(Allocator), // Pixel
-  ResourceRange(Allocator), // Amplification
-  ResourceRange(Allocator), // Mesh
-  };
-
-  // Reset the ResourceRanges for when we iterate through a new group
-  auto ClearRanges = [&Ranges]() {
-for (ResourceRange &Range : Ranges)
-  Range.clear();
-  };
-
   // Helper to report diagnostics
-  auto ReportOverlap = [this, InfoIndexMap, &HadOverlap](
-   const RangeInfo *Info, const RangeInfo *OInfo) {
-HadOverlap = true;
+  auto ReportOverlap = [this, InfoIndexMap](OverlappingRanges Overlap) {
+const RangeInfo *Info = Overlap.A;
+const RangeInfo *OInfo = Overlap.B;
 auto CommonVis = Info->Visibility == llvm::dxbc::ShaderVisibility::All
  ? OInfo->Visibility
  : Info->Visibility;
@@ -1240,42 +1189,12 @@ bool SemaHLSL::handleRootSignatureElements(
 this->Diag(OInfoLoc, diag::note_hlsl_resource_range_here);
   };
 
-  // 3: Iterate through collected RangeInfos
-  for (const RangeInfo &Info : Infos) {
-GroupT InfoGroup = {Info.Class, Info.Space};
-// Reset our ResourceRanges when we enter a new group
-if (CurGroup != InfoGroup) {
-  ClearRanges();
-  CurGroup = InfoGroup;
-}
-
-// 3A: Insert range info into corresponding Visibility ResourceRange
-ResourceRange &VisRange = Ranges[llvm::to_underlying(Info.Visibility)];
-if (std::optional Overlapping = VisRange.insert(Info))
-  ReportOverlap(&Info, Overlapping.value());
-
-// 3B: Check for overlap in all overlapping Visibility ResourceRanges
-//
-// If the range that we are inserting has ShaderVisiblity::All it needs to
-// check fo

[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147115)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic updated 
https://github.com/llvm/llvm-project/pull/147115

>From 4a5cde3f77dc0c371d1f33b10be9507d3aeff3e3 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 27 Jun 2025 18:36:38 +
Subject: [PATCH 1/9] nfc: introduce wrapper `RootSignatureElement` around
 `RootElement` to retain clang diag info

---
 .../clang/Parse/ParseHLSLRootSignature.h  |  17 ++-
 clang/include/clang/Sema/SemaHLSL.h   |  10 +-
 clang/lib/Parse/ParseDeclCXX.cpp  |   2 +-
 clang/lib/Parse/ParseHLSLRootSignature.cpp|  21 ++--
 clang/lib/Sema/SemaHLSL.cpp   |   6 +-
 .../Parse/ParseHLSLRootSignatureTest.cpp  | 115 +-
 6 files changed, 99 insertions(+), 72 deletions(-)

diff --git a/clang/include/clang/Parse/ParseHLSLRootSignature.h 
b/clang/include/clang/Parse/ParseHLSLRootSignature.h
index b0ef617a13c28..53001d2ba461f 100644
--- a/clang/include/clang/Parse/ParseHLSLRootSignature.h
+++ b/clang/include/clang/Parse/ParseHLSLRootSignature.h
@@ -26,10 +26,22 @@
 namespace clang {
 namespace hlsl {
 
+// Introduce a wrapper struct around the underlying RootElement. This structure
+// will retain extra clang diagnostic information that is not available in 
llvm.
+struct RootSignatureElement {
+  RootSignatureElement(llvm::hlsl::rootsig::RootElement Element)
+  : Element(Element) {}
+
+  const llvm::hlsl::rootsig::RootElement &getElement() const { return Element; 
}
+
+private:
+  llvm::hlsl::rootsig::RootElement Element;
+};
+
 class RootSignatureParser {
 public:
   RootSignatureParser(llvm::dxbc::RootSignatureVersion Version,
-  SmallVector &Elements,
+  SmallVector &Elements,
   StringLiteral *Signature, Preprocessor &PP);
 
   /// Consumes tokens from the Lexer and constructs the in-memory
@@ -196,7 +208,8 @@ class RootSignatureParser {
 
 private:
   llvm::dxbc::RootSignatureVersion Version;
-  SmallVector &Elements;
+  SmallVector &Elements;
+
   clang::StringLiteral *Signature;
   RootSignatureLexer Lexer;
   clang::Preprocessor &PP;
diff --git a/clang/include/clang/Sema/SemaHLSL.h 
b/clang/include/clang/Sema/SemaHLSL.h
index 7d7eae4db532c..1af706da702c2 100644
--- a/clang/include/clang/Sema/SemaHLSL.h
+++ b/clang/include/clang/Sema/SemaHLSL.h
@@ -32,6 +32,10 @@ class ParsedAttr;
 class Scope;
 class VarDecl;
 
+namespace hlsl {
+struct RootSignatureElement;
+}
+
 using llvm::dxil::ResourceClass;
 
 // FIXME: This can be hidden (as static function in SemaHLSL.cpp) once we no
@@ -130,9 +134,9 @@ class SemaHLSL : public SemaBase {
 
   /// Creates the Root Signature decl of the parsed Root Signature elements
   /// onto the AST and push it onto current Scope
-  void ActOnFinishRootSignatureDecl(
-  SourceLocation Loc, IdentifierInfo *DeclIdent,
-  SmallVector &Elements);
+  void
+  ActOnFinishRootSignatureDecl(SourceLocation Loc, IdentifierInfo *DeclIdent,
+   ArrayRef Elements);
 
   // Returns true when D is invalid and a diagnostic was produced
   bool handleRootSignatureDecl(HLSLRootSignatureDecl *D, SourceLocation Loc);
diff --git a/clang/lib/Parse/ParseDeclCXX.cpp b/clang/lib/Parse/ParseDeclCXX.cpp
index d3bc6f1e89832..d06bb6a25efa5 100644
--- a/clang/lib/Parse/ParseDeclCXX.cpp
+++ b/clang/lib/Parse/ParseDeclCXX.cpp
@@ -4951,7 +4951,7 @@ void 
Parser::ParseHLSLRootSignatureAttributeArgs(ParsedAttributes &Attrs) {
   // signature string and construct the in-memory elements
   if (!Found) {
 // Invoke the root signature parser to construct the in-memory constructs
-SmallVector RootElements;
+SmallVector RootElements;
 hlsl::RootSignatureParser Parser(getLangOpts().HLSLRootSigVer, 
RootElements,
  Signature, PP);
 if (Parser.parse()) {
diff --git a/clang/lib/Parse/ParseHLSLRootSignature.cpp 
b/clang/lib/Parse/ParseHLSLRootSignature.cpp
index ebaf7ba60fa17..76e50fb85c8d7 100644
--- a/clang/lib/Parse/ParseHLSLRootSignature.cpp
+++ b/clang/lib/Parse/ParseHLSLRootSignature.cpp
@@ -19,33 +19,34 @@ using TokenKind = RootSignatureToken::Kind;
 
 RootSignatureParser::RootSignatureParser(
 llvm::dxbc::RootSignatureVersion Version,
-SmallVector &Elements, StringLiteral *Signature,
+SmallVector &Elements, StringLiteral *Signature,
 Preprocessor &PP)
 : Version(Version), Elements(Elements), Signature(Signature),
   Lexer(Signature->getString()), PP(PP), CurToken(0) {}
 
 bool RootSignatureParser::parse() {
-  // Iterate as many RootElements as possible
+  // Iterate as many RootSignatureElements as possible
   do {
+std::optional Element = std::nullopt;
 if (tryConsumeExpectedToken(TokenKind::kw_RootFlags)) {
   auto Flags = parseRootFlags();
   if (!Flags.has_value())
 return true;
-  Elements.push_back(*Flags);
+  Element = RootSignatureElement(*Flags);
 }
 
 if (tryConsumeExpectedToken(TokenKind::kw_RootConstants)) {
   auto Co

[llvm-branch-commits] [clang] [llvm] [NFC][HLSL] Move resource range logic from `SemaHLSL` to `RootSignatureValidations` (PR #147117)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic updated 
https://github.com/llvm/llvm-project/pull/147117

>From d66a67d9660ab1114d55f75ef2ad5a9cfd35f8f6 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 4 Jul 2025 22:17:37 +
Subject: [PATCH 1/2] self-review: remove unused Loc

---
 clang/include/clang/Sema/SemaHLSL.h | 3 +--
 clang/lib/Sema/SemaHLSL.cpp | 2 +-
 2 files changed, 2 insertions(+), 3 deletions(-)

diff --git a/clang/include/clang/Sema/SemaHLSL.h 
b/clang/include/clang/Sema/SemaHLSL.h
index 910e0e640796b..42abd29b01ea7 100644
--- a/clang/include/clang/Sema/SemaHLSL.h
+++ b/clang/include/clang/Sema/SemaHLSL.h
@@ -155,8 +155,7 @@ class SemaHLSL : public SemaBase {
 
   // Returns true when D is invalid and a diagnostic was produced
   bool
-  handleRootSignatureElements(ArrayRef Elements,
-  SourceLocation Loc);
+  handleRootSignatureElements(ArrayRef Elements);
   void handleRootSignatureAttr(Decl *D, const ParsedAttr &AL);
   void handleNumThreadsAttr(Decl *D, const ParsedAttr &AL);
   void handleWaveSizeAttr(Decl *D, const ParsedAttr &AL);
diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp
index f490f957f9667..3feb27ac44bd6 100644
--- a/clang/lib/Sema/SemaHLSL.cpp
+++ b/clang/lib/Sema/SemaHLSL.cpp
@@ -1082,7 +1082,7 @@ void SemaHLSL::ActOnFinishRootSignatureDecl(
 }
 
 bool SemaHLSL::handleRootSignatureElements(
-ArrayRef Elements, SourceLocation Loc) {
+ArrayRef Elements) {
   // The following conducts analysis on resource ranges to detect and report
   // any overlaps in resource ranges.
   //

>From 969f316004ae500d707be081e6f2f4abc669fff3 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 27 Jun 2025 19:58:15 +
Subject: [PATCH 2/2] nfc: move collection of overlaps to
 `RootSignatureValidations`

---
 clang/lib/Sema/SemaHLSL.cpp   | 101 ++
 .../Frontend/HLSL/RootSignatureValidations.h  |  32 ++
 .../HLSL/RootSignatureValidations.cpp |  73 +
 3 files changed, 115 insertions(+), 91 deletions(-)

diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp
index 3feb27ac44bd6..18b84c33b39c8 100644
--- a/clang/lib/Sema/SemaHLSL.cpp
+++ b/clang/lib/Sema/SemaHLSL.cpp
@@ -1083,29 +1083,8 @@ void SemaHLSL::ActOnFinishRootSignatureDecl(
 
 bool SemaHLSL::handleRootSignatureElements(
 ArrayRef Elements) {
-  // The following conducts analysis on resource ranges to detect and report
-  // any overlaps in resource ranges.
-  //
-  // A resource range overlaps with another resource range if they have:
-  // - equivalent ResourceClass (SRV, UAV, CBuffer, Sampler)
-  // - equivalent resource space
-  // - overlapping visbility
-  //
-  // The following algorithm is implemented in the following steps:
-  //
-  // 1. Collect RangeInfo from relevant RootElements:
-  //   - RangeInfo will retain the interval, ResourceClass, Space and 
Visibility
-  // 2. Sort the RangeInfo's such that they are grouped together by
-  //  ResourceClass and Space (GroupT defined below)
-  // 3. Iterate through the collected RangeInfos by their groups
-  //   - For each group we will have a ResourceRange for each visibility
-  //   - As we iterate through we will:
-  //  A: Insert the current RangeInfo into the corresponding Visibility
-  //   ResourceRange
-  //  B: Check for overlap with any overlapping Visibility ResourceRange
   using RangeInfo = llvm::hlsl::rootsig::RangeInfo;
-  using ResourceRange = llvm::hlsl::rootsig::ResourceRange;
-  using GroupT = std::pair;
+  using OverlappingRanges = llvm::hlsl::rootsig::OverlappingRanges;
 
   // Introduce a mapping from the collected RangeInfos back to the
   // RootSignatureElement that will retain its diagnostics info
@@ -1188,40 +1167,10 @@ bool SemaHLSL::handleRootSignatureElements(
 }
   }
 
-  // 2. Sort the RangeInfo's by their GroupT to form groupings
-  std::sort(Infos.begin(), Infos.end(), [](RangeInfo A, RangeInfo B) {
-return std::tie(A.Class, A.Space) < std::tie(B.Class, B.Space);
-  });
-
-  // 3. First we will init our state to track:
-  if (Infos.size() == 0)
-return false; // No ranges to overlap
-  GroupT CurGroup = {Infos[0].Class, Infos[0].Space};
-  bool HadOverlap = false;
-
-  // Create a ResourceRange for each Visibility
-  ResourceRange::MapT::Allocator Allocator;
-  std::array Ranges = {
-  ResourceRange(Allocator), // All
-  ResourceRange(Allocator), // Vertex
-  ResourceRange(Allocator), // Hull
-  ResourceRange(Allocator), // Domain
-  ResourceRange(Allocator), // Geometry
-  ResourceRange(Allocator), // Pixel
-  ResourceRange(Allocator), // Amplification
-  ResourceRange(Allocator), // Mesh
-  };
-
-  // Reset the ResourceRanges for when we iterate through a new group
-  auto ClearRanges = [&Ranges]() {
-for (ResourceRange &Range : Ranges)
-  Range.clear();
-  };
-
   // Helper to report diagnostics
-  auto ReportOverlap = [this, InfoIndexMap, &HadOverlap](
- 

[llvm-branch-commits] [llvm] [SelectionDAG] Deal with POISON for INSERT_VECTOR_ELT/INSERT_SUBVECTOR (part 2) (PR #143103)

2025-07-04 Thread Björn Pettersson via llvm-branch-commits

https://github.com/bjope updated 
https://github.com/llvm/llvm-project/pull/143103

From fe73a97a1ef8c1c2df5999e0b6abecde0e89733b Mon Sep 17 00:00:00 2001
From: Bjorn Pettersson 
Date: Tue, 3 Jun 2025 10:01:01 +0200
Subject: [PATCH] [SelectionDAG] Deal with POISON for
 INSERT_VECTOR_ELT/INSERT_SUBVECTOR (part 2)

Add support in isGuaranteedNotToBeUndefOrPoison to avoid regressions
seen after a previous commit fixing #141034.
---
 llvm/include/llvm/CodeGen/SelectionDAGNodes.h |   6 +
 .../lib/CodeGen/SelectionDAG/SelectionDAG.cpp |  71 ++
 llvm/test/CodeGen/Thumb2/mve-vld3.ll  |   4 +-
 .../X86/merge-consecutive-loads-128.ll|  78 ++
 llvm/test/CodeGen/X86/mmx-build-vector.ll | 233 +-
 llvm/test/CodeGen/X86/pr62286.ll  |  14 +-
 .../CodeGen/X86/vector-shuffle-combining.ll   |  41 ++-
 .../zero_extend_vector_inreg_of_broadcast.ll  |   8 +-
 8 files changed, 191 insertions(+), 264 deletions(-)

diff --git a/llvm/include/llvm/CodeGen/SelectionDAGNodes.h 
b/llvm/include/llvm/CodeGen/SelectionDAGNodes.h
index a3675eecfea3f..08db31c63367d 100644
--- a/llvm/include/llvm/CodeGen/SelectionDAGNodes.h
+++ b/llvm/include/llvm/CodeGen/SelectionDAGNodes.h
@@ -1889,6 +1889,12 @@ LLVM_ABI SDValue peekThroughExtractSubvectors(SDValue V);
 /// If \p V is not a truncation, it is returned as-is.
 LLVM_ABI SDValue peekThroughTruncates(SDValue V);
 
+/// Recursively peek through INSERT_VECTOR_ELT nodes, returning the source
+/// vector operand of \p V, as long as \p V is an INSERT_VECTOR_ELT operation
+/// that do not insert into any of the demanded vector elts.
+LLVM_ABI SDValue peekThroughInsertVectorElt(SDValue V,
+const APInt &DemandedElts);
+
 /// Returns true if \p V is a bitwise not operation. Assumes that an all ones
 /// constant is canonicalized to be operand 1.
 LLVM_ABI bool isBitwiseNot(SDValue V, bool AllowUndefs = false);
diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp 
b/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp
index 3b4802d4b47b1..17fe550d38c55 100644
--- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp
@@ -5456,6 +5456,60 @@ bool 
SelectionDAG::isGuaranteedNotToBeUndefOrPoison(SDValue Op,
 }
 return true;
 
+  case ISD::INSERT_SUBVECTOR: {
+if (Op.getValueType().isScalableVector())
+  break;
+SDValue Src = Op.getOperand(0);
+SDValue Sub = Op.getOperand(1);
+uint64_t Idx = Op.getConstantOperandVal(2);
+unsigned NumSubElts = Sub.getValueType().getVectorNumElements();
+APInt DemandedSubElts = DemandedElts.extractBits(NumSubElts, Idx);
+APInt DemandedSrcElts = DemandedElts;
+DemandedSrcElts.clearBits(Idx, Idx + NumSubElts);
+
+if (!!DemandedSubElts && !isGuaranteedNotToBeUndefOrPoison(
+ Sub, DemandedSubElts, PoisonOnly, Depth + 1))
+  return false;
+if (!!DemandedSrcElts && !isGuaranteedNotToBeUndefOrPoison(
+ Src, DemandedSrcElts, PoisonOnly, Depth + 1))
+  return false;
+return true;
+  }
+
+  case ISD::INSERT_VECTOR_ELT: {
+SDValue InVec = Op.getOperand(0);
+SDValue InVal = Op.getOperand(1);
+SDValue EltNo = Op.getOperand(2);
+EVT VT = InVec.getValueType();
+auto *IndexC = dyn_cast(EltNo);
+if (IndexC && VT.isFixedLengthVector() &&
+IndexC->getZExtValue() < VT.getVectorNumElements()) {
+  if (DemandedElts[IndexC->getZExtValue()] &&
+  !isGuaranteedNotToBeUndefOrPoison(InVal, PoisonOnly, Depth + 1))
+return false;
+  APInt InVecDemandedElts = DemandedElts;
+  InVecDemandedElts.clearBit(IndexC->getZExtValue());
+  if (!!InVecDemandedElts &&
+  !isGuaranteedNotToBeUndefOrPoison(
+  peekThroughInsertVectorElt(InVec, InVecDemandedElts),
+  InVecDemandedElts, PoisonOnly, Depth + 1))
+return false;
+  return true;
+}
+break;
+  }
+
+  case ISD::SCALAR_TO_VECTOR:
+// Check upper (known undef) elements.
+if (DemandedElts.ugt(1) && !PoisonOnly)
+  return false;
+// Check element zero.
+if (DemandedElts[0] && !isGuaranteedNotToBeUndefOrPoison(Op.getOperand(0),
+ PoisonOnly,
+ Depth + 1))
+  return false;
+return true;
+
   case ISD::SPLAT_VECTOR:
 return isGuaranteedNotToBeUndefOrPoison(Op.getOperand(0), PoisonOnly,
 Depth + 1);
@@ -12508,6 +12562,23 @@ SDValue llvm::peekThroughTruncates(SDValue V) {
   return V;
 }
 
+SDValue llvm::peekThroughInsertVectorElt(SDValue V, const APInt &DemandedElts) 
{
+  while (V.getOpcode() == ISD::INSERT_VECTOR_ELT) {
+SDValue InVec = V.getOperand(0);
+SDValue EltNo = V.getOperand(2);
+EVT VT = InVec.getValueType();
+auto *IndexC = dyn_cast(EltNo);
+if (IndexC && VT.isF

[llvm-branch-commits] [llvm] [SelectionDAG] Deal with POISON for INSERT_VECTOR_ELT/INSERT_SUBVECTOR (part 3) (PR #143105)

2025-07-04 Thread Björn Pettersson via llvm-branch-commits

https://github.com/bjope updated 
https://github.com/llvm/llvm-project/pull/143105

From be4f7432d8f35a8b07dc745736dccac6ae742743 Mon Sep 17 00:00:00 2001
From: Bjorn Pettersson 
Date: Sat, 31 May 2025 09:37:27 +0200
Subject: [PATCH] [SelectionDAG] Deal with POISON for
 INSERT_VECTOR_ELT/INSERT_SUBVECTOR (part 3)

Target specific patches to avoid regressions seen after "part 1"
aiming at fixing github issue #141034.

One perhaps controversial change here is that convertToScalableVector
now uses POISON instead of UNDEF for any additional elements added
when converting to the scalable vector. This can avoid that we end
up with things like
  t31: nxv1f32 =
  t32: v2f32 = extract_subvector t31, Constant:i64<0>
  t38: nxv1f32 = insert_subvector undef:nxv1f32, t32, Constant:i64<0>
since if we instead try to insert into poison we can just use t31
instead of t38 without the risk that t31 would be more poisonous.
---
 llvm/include/llvm/CodeGen/SelectionDAG.h  |  11 +-
 .../Target/AArch64/AArch64ISelLowering.cpp|   9 +-
 llvm/lib/Target/RISCV/RISCVISelLowering.cpp   |  18 +--
 .../AArch64/sve-fixed-length-fp-vselect.ll|  81 +
 .../AArch64/sve-fixed-length-frame-offests.ll |   8 +-
 .../AArch64/sve-fixed-length-int-vselect.ll   | 108 ++
 .../AArch64/sve-fixed-length-masked-gather.ll |   6 +-
 ...-streaming-mode-fixed-length-fp-vselect.ll |  21 
 ...streaming-mode-fixed-length-int-vselect.ll |  28 -
 .../fixed-vectors-vfw-web-simplification.ll   |  90 +--
 .../fixed-vectors-vw-web-simplification.ll|  55 +++--
 11 files changed, 93 insertions(+), 342 deletions(-)

diff --git a/llvm/include/llvm/CodeGen/SelectionDAG.h 
b/llvm/include/llvm/CodeGen/SelectionDAG.h
index a98e46c587273..3abdafac4b411 100644
--- a/llvm/include/llvm/CodeGen/SelectionDAG.h
+++ b/llvm/include/llvm/CodeGen/SelectionDAG.h
@@ -953,8 +953,17 @@ class SelectionDAG {
   }
 
   /// Insert \p SubVec at the \p Idx element of \p Vec.
+  /// If \p SkipUndef is true and \p SubVec is UNDEF/POISON, then \p Vec is
+  /// returned.
   SDValue getInsertSubvector(const SDLoc &DL, SDValue Vec, SDValue SubVec,
- unsigned Idx) {
+ unsigned Idx, bool SkipUndef = false) {
+// Skipping insert of UNDEF could result in POISON elements remaining in 
the
+// resulting vector. The SkipUndef is useful in situations when getNode
+// can't reason well enough about ignoring the insert, e.g. when having
+// scalable vectors and the user of this method knows that the subvector
+// being replaced isn't POISON.
+if (SkipUndef && SubVec.isUndef())
+  return Vec;
 return getNode(ISD::INSERT_SUBVECTOR, DL, Vec.getValueType(), Vec, SubVec,
getVectorIdxConstant(Idx, DL));
   }
diff --git a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp 
b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
index fb8bd81c033af..761f7eaa13dc4 100644
--- a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
+++ b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
@@ -15125,11 +15125,14 @@ SDValue 
AArch64TargetLowering::LowerBUILD_VECTOR(SDValue Op,
 
   if (PreferDUPAndInsert) {
 // First, build a constant vector with the common element.
-SmallVector Ops(NumElts, Value);
+// Make sure to freeze the common element first, since we will use it also
+// for indices that should be UNDEF (so we want to avoid making those
+// elements more poisonous).
+SmallVector Ops(NumElts, DAG.getFreeze(Value));
 SDValue NewVector = LowerBUILD_VECTOR(DAG.getBuildVector(VT, DL, Ops), 
DAG);
 // Next, insert the elements that do not match the common value.
 for (unsigned I = 0; I < NumElts; ++I)
-  if (Op.getOperand(I) != Value)
+  if (Op.getOperand(I) != Value && !Op.getOperand(I).isUndef())
 NewVector =
 DAG.getNode(ISD::INSERT_VECTOR_ELT, DL, VT, NewVector,
 Op.getOperand(I), DAG.getConstant(I, DL, MVT::i64));
@@ -28721,7 +28724,7 @@ static SDValue convertToScalableVector(SelectionDAG 
&DAG, EVT VT, SDValue V) {
  "Expected a fixed length vector operand!");
   SDLoc DL(V);
   SDValue Zero = DAG.getConstant(0, DL, MVT::i64);
-  return DAG.getNode(ISD::INSERT_SUBVECTOR, DL, VT, DAG.getUNDEF(VT), V, Zero);
+  return DAG.getNode(ISD::INSERT_SUBVECTOR, DL, VT, DAG.getPOISON(VT), V, 
Zero);
 }
 
 // Shrink V so it's just big enough to maintain a VT's worth of data.
diff --git a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp 
b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
index 4f280c3e562b8..55e352ad21019 100644
--- a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
+++ b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
@@ -2859,7 +2859,7 @@ static SDValue convertToScalableVector(EVT VT, SDValue V, 
SelectionDAG &DAG,
   assert(V.getValueType().isFixedLengthVector() &&
  "Expected a fixed length vector operand!");
   SDLoc DL(V);
-  return DAG.getInsertSubvector(DL, DAG.getUNDE

[llvm-branch-commits] [mlir] [MLIR][OpenMP] Add canonical loop LLVM-IR lowering (PR #147069)

2025-07-04 Thread Michael Kruse via llvm-branch-commits

https://github.com/Meinersbur created 
https://github.com/llvm/llvm-project/pull/147069

Support for translating the operations introduced in #144785 to LLVM-IR.

>From da2613d525deb4edcf0fac41e865ca0510c75210 Mon Sep 17 00:00:00 2001
From: Michael Kruse 
Date: Fri, 4 Jul 2025 16:26:20 +0200
Subject: [PATCH] omp.canonical_loop and omp.unroll_heuristic lowering

---
 .../mlir/Target/LLVMIR/ModuleTranslation.h|  43 +
 .../Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp  |  10 +
 .../OpenMP/OpenMPToLLVMIRTranslation.cpp  |  78 
 .../LLVMIR/openmp-cli-canonical_loop.mlir | 175 ++
 .../LLVMIR/openmp-cli-unroll-heuristic01.mlir |  56 ++
 .../LLVMIR/openmp-cli-unroll-heuristic02.mlir |  93 ++
 6 files changed, 455 insertions(+)
 create mode 100644 mlir/test/Target/LLVMIR/openmp-cli-canonical_loop.mlir
 create mode 100644 mlir/test/Target/LLVMIR/openmp-cli-unroll-heuristic01.mlir
 create mode 100644 mlir/test/Target/LLVMIR/openmp-cli-unroll-heuristic02.mlir

diff --git a/mlir/include/mlir/Target/LLVMIR/ModuleTranslation.h 
b/mlir/include/mlir/Target/LLVMIR/ModuleTranslation.h
index 79e8bb6add0da..5d52cf3f04b6a 100644
--- a/mlir/include/mlir/Target/LLVMIR/ModuleTranslation.h
+++ b/mlir/include/mlir/Target/LLVMIR/ModuleTranslation.h
@@ -15,6 +15,7 @@
 #define MLIR_TARGET_LLVMIR_MODULETRANSLATION_H
 
 #include "mlir/Dialect/LLVMIR/LLVMInterfaces.h"
+#include "mlir/Dialect/OpenMP/OpenMPDialect.h"
 #include "mlir/IR/Operation.h"
 #include "mlir/IR/SymbolTable.h"
 #include "mlir/IR/Value.h"
@@ -24,6 +25,7 @@
 #include "mlir/Target/LLVMIR/TypeToLLVM.h"
 
 #include "llvm/ADT/SetVector.h"
+#include "llvm/Frontend/OpenMP/OMPIRBuilder.h"
 #include "llvm/IR/FPEnv.h"
 
 namespace llvm {
@@ -108,6 +110,41 @@ class ModuleTranslation {
 return blockMapping.lookup(block);
   }
 
+  /// Find the LLVM-IR loop that represents an MLIR loop.
+  llvm::CanonicalLoopInfo *lookupOMPLoop(omp::NewCliOp mlir) const {
+llvm::CanonicalLoopInfo *result = loopMapping.lookup(mlir);
+assert(result && "attempt to get non-existing loop");
+return result;
+  }
+
+  /// Find the LLVM-IR loop that represents an MLIR loop.
+  llvm::CanonicalLoopInfo *lookupOMPLoop(Value mlir) const {
+return lookupOMPLoop(mlir.getDefiningOp());
+  }
+
+  /// Mark an OpenMP loop as having been consumed.
+  void invalidateOmpLoop(omp::NewCliOp mlir) { loopMapping.erase(mlir); }
+
+  /// Mark an OpenMP loop as having been consumed.
+  void invalidateOmpLoop(Value mlir) {
+invalidateOmpLoop(mlir.getDefiningOp());
+  }
+
+  /// Map an MLIR OpenMP dialect CanonicalLoopInfo to its lowered LLVM-IR
+  /// OpenMPIRBuilder CanonicalLoopInfo
+  void mapOmpLoop(omp::NewCliOp mlir, llvm::CanonicalLoopInfo *llvm) {
+assert(llvm && "argument must be non-null");
+llvm::CanonicalLoopInfo *&cur = loopMapping[mlir];
+assert(cur == nullptr && "attempting to map a loop that is already 
mapped");
+cur = llvm;
+  }
+
+  /// Map an MLIR OpenMP dialect CanonicalLoopInfo to its lowered LLVM-IR
+  /// OpenMPIRBuilder CanonicalLoopInfo
+  void mapOmpLoop(Value mlir, llvm::CanonicalLoopInfo *llvm) {
+mapOmpLoop(mlir.getDefiningOp(), llvm);
+  }
+
   /// Stores the mapping between an MLIR operation with successors and a
   /// corresponding LLVM IR instruction.
   void mapBranch(Operation *mlir, llvm::Instruction *llvm) {
@@ -381,6 +418,12 @@ class ModuleTranslation {
   DenseMap valueMapping;
   DenseMap blockMapping;
 
+  /// List of not yet consumed MLIR loop handles (represented by an omp.new_cli
+  /// operation which creates a value of type CanonicalLoopInfoType) and their
+  /// LLVM-IR representation as CanonicalLoopInfo which is managed by the
+  /// OpenMPIRBuilder.
+  DenseMap loopMapping;
+
   /// A mapping between MLIR LLVM dialect terminators and LLVM IR terminators
   /// they are converted to. This allows for connecting PHI nodes to the source
   /// values after all operations are converted.
diff --git a/mlir/lib/Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp 
b/mlir/lib/Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp
index 7a0a7f86bc1e9..e77c4a0b94de9 100644
--- a/mlir/lib/Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp
+++ b/mlir/lib/Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp
@@ -42,6 +42,16 @@ template 
 struct OpenMPOpConversion : public ConvertOpToLLVMPattern {
   using ConvertOpToLLVMPattern::ConvertOpToLLVMPattern;
 
+  OpenMPOpConversion(LLVMTypeConverter &typeConverter,
+ PatternBenefit benefit = 1)
+  : ConvertOpToLLVMPattern(typeConverter, benefit) {
+// Operations using CanonicalLoopInfoType are lowered only by
+// mlir::translateModuleToLLVMIR() using the OpenMPIRBuilder. Until then,
+// the type and operations using it must be preserved.
+typeConverter.addConversion(
+[&](::mlir::omp::CanonicalLoopInfoType type) { return type; });
+  }
+
   LogicalResult
   matchAndRewrite(T op, typename T::Adaptor adaptor,
   ConversionPatternRewriter &rewr

[llvm-branch-commits] [llvm] release/20.x: [X86] Ignore NSW when DstSVT is i32 (#131755) (PR #147034)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-backend-x86

Author: None (llvmbot)


Changes

Backport 3d631914677b58a5479b310f480ac76e27d41e7e

Requested by: @nikic

---
Full diff: https://github.com/llvm/llvm-project/pull/147034.diff


2 Files Affected:

- (modified) llvm/lib/Target/X86/X86ISelLowering.cpp (+2-1) 
- (modified) llvm/test/CodeGen/X86/vector-trunc-nowrap.ll (+86) 


``diff
diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp 
b/llvm/lib/Target/X86/X86ISelLowering.cpp
index 4413fbb77f415..12c40b501f627 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.cpp
+++ b/llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -20889,7 +20889,8 @@ static SDValue matchTruncateWithPACK(unsigned 
&PackOpcode, EVT DstVT,
 return SDValue();
 
   unsigned MinSignBits = NumSrcEltBits - NumPackedSignBits;
-  if (Flags.hasNoSignedWrap() || MinSignBits < NumSignBits) {
+  if ((Flags.hasNoSignedWrap() && DstSVT != MVT::i32) ||
+  MinSignBits < NumSignBits) {
 PackOpcode = X86ISD::PACKSS;
 return In;
   }
diff --git a/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll 
b/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
index 2b8eedfbbdc9c..85cca4f6f9a57 100644
--- a/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
+++ b/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
@@ -1592,3 +1592,89 @@ entry:
   %1 = bitcast <8 x i8> %0 to i64
   ret i64 %1
 }
+
+define void @foo(<4 x i64> %a, <4 x i64> %b, ptr %p) 
"min-legal-vector-width"="256" "prefer-vector-width"="256" {
+; SSE-LABEL: foo:
+; SSE:   # %bb.0: # %entry
+; SSE-NEXT:shufps {{.*#+}} xmm0 = xmm0[0,2],xmm1[0,2]
+; SSE-NEXT:shufps {{.*#+}} xmm2 = xmm2[0,2],xmm3[0,2]
+; SSE-NEXT:movaps %xmm2, 16(%rdi)
+; SSE-NEXT:movaps %xmm0, (%rdi)
+; SSE-NEXT:retq
+;
+; AVX1-LABEL: foo:
+; AVX1:   # %bb.0: # %entry
+; AVX1-NEXT:vperm2f128 {{.*#+}} ymm2 = ymm0[2,3],ymm1[2,3]
+; AVX1-NEXT:vinsertf128 $1, %xmm1, %ymm0, %ymm0
+; AVX1-NEXT:vshufps {{.*#+}} ymm0 = ymm0[0,2],ymm2[0,2],ymm0[4,6],ymm2[4,6]
+; AVX1-NEXT:vmovups %ymm0, (%rdi)
+; AVX1-NEXT:vzeroupper
+; AVX1-NEXT:retq
+;
+; AVX2-SLOW-LABEL: foo:
+; AVX2-SLOW:   # %bb.0: # %entry
+; AVX2-SLOW-NEXT:vextractf128 $1, %ymm0, %xmm2
+; AVX2-SLOW-NEXT:vshufps {{.*#+}} xmm0 = xmm0[0,2],xmm2[0,2]
+; AVX2-SLOW-NEXT:vextractf128 $1, %ymm1, %xmm2
+; AVX2-SLOW-NEXT:vshufps {{.*#+}} xmm1 = xmm1[0,2],xmm2[0,2]
+; AVX2-SLOW-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-SLOW-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-SLOW-NEXT:vzeroupper
+; AVX2-SLOW-NEXT:retq
+;
+; AVX2-FAST-ALL-LABEL: foo:
+; AVX2-FAST-ALL:   # %bb.0: # %entry
+; AVX2-FAST-ALL-NEXT:vmovaps {{.*#+}} ymm2 = [0,2,4,6,4,6,6,7]
+; AVX2-FAST-ALL-NEXT:vpermps %ymm0, %ymm2, %ymm0
+; AVX2-FAST-ALL-NEXT:vpermps %ymm1, %ymm2, %ymm1
+; AVX2-FAST-ALL-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-FAST-ALL-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-FAST-ALL-NEXT:vzeroupper
+; AVX2-FAST-ALL-NEXT:retq
+;
+; AVX2-FAST-PERLANE-LABEL: foo:
+; AVX2-FAST-PERLANE:   # %bb.0: # %entry
+; AVX2-FAST-PERLANE-NEXT:vextractf128 $1, %ymm0, %xmm2
+; AVX2-FAST-PERLANE-NEXT:vshufps {{.*#+}} xmm0 = xmm0[0,2],xmm2[0,2]
+; AVX2-FAST-PERLANE-NEXT:vextractf128 $1, %ymm1, %xmm2
+; AVX2-FAST-PERLANE-NEXT:vshufps {{.*#+}} xmm1 = xmm1[0,2],xmm2[0,2]
+; AVX2-FAST-PERLANE-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-FAST-PERLANE-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-FAST-PERLANE-NEXT:vzeroupper
+; AVX2-FAST-PERLANE-NEXT:retq
+;
+; AVX512F-LABEL: foo:
+; AVX512F:   # %bb.0: # %entry
+; AVX512F-NEXT:# kill: def $ymm0 killed $ymm0 def $zmm0
+; AVX512F-NEXT:vinserti64x4 $1, %ymm1, %zmm0, %zmm0
+; AVX512F-NEXT:vpmovqd %zmm0, (%rdi)
+; AVX512F-NEXT:vzeroupper
+; AVX512F-NEXT:retq
+;
+; AVX512VL-LABEL: foo:
+; AVX512VL:   # %bb.0: # %entry
+; AVX512VL-NEXT:vpmovqd %ymm1, 16(%rdi)
+; AVX512VL-NEXT:vpmovqd %ymm0, (%rdi)
+; AVX512VL-NEXT:vzeroupper
+; AVX512VL-NEXT:retq
+;
+; AVX512BW-LABEL: foo:
+; AVX512BW:   # %bb.0: # %entry
+; AVX512BW-NEXT:# kill: def $ymm0 killed $ymm0 def $zmm0
+; AVX512BW-NEXT:vinserti64x4 $1, %ymm1, %zmm0, %zmm0
+; AVX512BW-NEXT:vpmovqd %zmm0, (%rdi)
+; AVX512BW-NEXT:vzeroupper
+; AVX512BW-NEXT:retq
+;
+; AVX512BWVL-LABEL: foo:
+; AVX512BWVL:   # %bb.0: # %entry
+; AVX512BWVL-NEXT:vpmovqd %ymm1, 16(%rdi)
+; AVX512BWVL-NEXT:vpmovqd %ymm0, (%rdi)
+; AVX512BWVL-NEXT:vzeroupper
+; AVX512BWVL-NEXT:retq
+entry:
+  %0 = shufflevector <4 x i64> %a, <4 x i64> %b, <8 x i32> 
+  %1 = trunc nsw <8 x i64> %0 to <8 x i32>
+  store <8 x i32> %1, ptr %p, align 16
+  ret void
+}

``




https://github.com/llvm/llvm-project/pull/147034
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] release/20.x: [X86] Ignore NSW when DstSVT is i32 (#131755) (PR #147034)

2025-07-04 Thread via llvm-branch-commits

https://github.com/llvmbot created 
https://github.com/llvm/llvm-project/pull/147034

Backport 3d631914677b58a5479b310f480ac76e27d41e7e

Requested by: @nikic

>From d21a84221a9dbd5af4296fc07d6a43c4d8bdf9e9 Mon Sep 17 00:00:00 2001
From: Phoebe Wang 
Date: Tue, 18 Mar 2025 13:04:23 +0100
Subject: [PATCH] [X86] Ignore NSW when DstSVT is i32 (#131755)

We don't have PACKSS for i64->i32.

Fixes: https://godbolt.org/z/qb8nxnPbK, which was introduced by ddd2f57b
(cherry picked from commit 3d631914677b58a5479b310f480ac76e27d41e7e)
---
 llvm/lib/Target/X86/X86ISelLowering.cpp  |  3 +-
 llvm/test/CodeGen/X86/vector-trunc-nowrap.ll | 86 
 2 files changed, 88 insertions(+), 1 deletion(-)

diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp 
b/llvm/lib/Target/X86/X86ISelLowering.cpp
index 4413fbb77f415..12c40b501f627 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.cpp
+++ b/llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -20889,7 +20889,8 @@ static SDValue matchTruncateWithPACK(unsigned 
&PackOpcode, EVT DstVT,
 return SDValue();
 
   unsigned MinSignBits = NumSrcEltBits - NumPackedSignBits;
-  if (Flags.hasNoSignedWrap() || MinSignBits < NumSignBits) {
+  if ((Flags.hasNoSignedWrap() && DstSVT != MVT::i32) ||
+  MinSignBits < NumSignBits) {
 PackOpcode = X86ISD::PACKSS;
 return In;
   }
diff --git a/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll 
b/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
index 2b8eedfbbdc9c..85cca4f6f9a57 100644
--- a/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
+++ b/llvm/test/CodeGen/X86/vector-trunc-nowrap.ll
@@ -1592,3 +1592,89 @@ entry:
   %1 = bitcast <8 x i8> %0 to i64
   ret i64 %1
 }
+
+define void @foo(<4 x i64> %a, <4 x i64> %b, ptr %p) 
"min-legal-vector-width"="256" "prefer-vector-width"="256" {
+; SSE-LABEL: foo:
+; SSE:   # %bb.0: # %entry
+; SSE-NEXT:shufps {{.*#+}} xmm0 = xmm0[0,2],xmm1[0,2]
+; SSE-NEXT:shufps {{.*#+}} xmm2 = xmm2[0,2],xmm3[0,2]
+; SSE-NEXT:movaps %xmm2, 16(%rdi)
+; SSE-NEXT:movaps %xmm0, (%rdi)
+; SSE-NEXT:retq
+;
+; AVX1-LABEL: foo:
+; AVX1:   # %bb.0: # %entry
+; AVX1-NEXT:vperm2f128 {{.*#+}} ymm2 = ymm0[2,3],ymm1[2,3]
+; AVX1-NEXT:vinsertf128 $1, %xmm1, %ymm0, %ymm0
+; AVX1-NEXT:vshufps {{.*#+}} ymm0 = ymm0[0,2],ymm2[0,2],ymm0[4,6],ymm2[4,6]
+; AVX1-NEXT:vmovups %ymm0, (%rdi)
+; AVX1-NEXT:vzeroupper
+; AVX1-NEXT:retq
+;
+; AVX2-SLOW-LABEL: foo:
+; AVX2-SLOW:   # %bb.0: # %entry
+; AVX2-SLOW-NEXT:vextractf128 $1, %ymm0, %xmm2
+; AVX2-SLOW-NEXT:vshufps {{.*#+}} xmm0 = xmm0[0,2],xmm2[0,2]
+; AVX2-SLOW-NEXT:vextractf128 $1, %ymm1, %xmm2
+; AVX2-SLOW-NEXT:vshufps {{.*#+}} xmm1 = xmm1[0,2],xmm2[0,2]
+; AVX2-SLOW-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-SLOW-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-SLOW-NEXT:vzeroupper
+; AVX2-SLOW-NEXT:retq
+;
+; AVX2-FAST-ALL-LABEL: foo:
+; AVX2-FAST-ALL:   # %bb.0: # %entry
+; AVX2-FAST-ALL-NEXT:vmovaps {{.*#+}} ymm2 = [0,2,4,6,4,6,6,7]
+; AVX2-FAST-ALL-NEXT:vpermps %ymm0, %ymm2, %ymm0
+; AVX2-FAST-ALL-NEXT:vpermps %ymm1, %ymm2, %ymm1
+; AVX2-FAST-ALL-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-FAST-ALL-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-FAST-ALL-NEXT:vzeroupper
+; AVX2-FAST-ALL-NEXT:retq
+;
+; AVX2-FAST-PERLANE-LABEL: foo:
+; AVX2-FAST-PERLANE:   # %bb.0: # %entry
+; AVX2-FAST-PERLANE-NEXT:vextractf128 $1, %ymm0, %xmm2
+; AVX2-FAST-PERLANE-NEXT:vshufps {{.*#+}} xmm0 = xmm0[0,2],xmm2[0,2]
+; AVX2-FAST-PERLANE-NEXT:vextractf128 $1, %ymm1, %xmm2
+; AVX2-FAST-PERLANE-NEXT:vshufps {{.*#+}} xmm1 = xmm1[0,2],xmm2[0,2]
+; AVX2-FAST-PERLANE-NEXT:vmovaps %xmm1, 16(%rdi)
+; AVX2-FAST-PERLANE-NEXT:vmovaps %xmm0, (%rdi)
+; AVX2-FAST-PERLANE-NEXT:vzeroupper
+; AVX2-FAST-PERLANE-NEXT:retq
+;
+; AVX512F-LABEL: foo:
+; AVX512F:   # %bb.0: # %entry
+; AVX512F-NEXT:# kill: def $ymm0 killed $ymm0 def $zmm0
+; AVX512F-NEXT:vinserti64x4 $1, %ymm1, %zmm0, %zmm0
+; AVX512F-NEXT:vpmovqd %zmm0, (%rdi)
+; AVX512F-NEXT:vzeroupper
+; AVX512F-NEXT:retq
+;
+; AVX512VL-LABEL: foo:
+; AVX512VL:   # %bb.0: # %entry
+; AVX512VL-NEXT:vpmovqd %ymm1, 16(%rdi)
+; AVX512VL-NEXT:vpmovqd %ymm0, (%rdi)
+; AVX512VL-NEXT:vzeroupper
+; AVX512VL-NEXT:retq
+;
+; AVX512BW-LABEL: foo:
+; AVX512BW:   # %bb.0: # %entry
+; AVX512BW-NEXT:# kill: def $ymm0 killed $ymm0 def $zmm0
+; AVX512BW-NEXT:vinserti64x4 $1, %ymm1, %zmm0, %zmm0
+; AVX512BW-NEXT:vpmovqd %zmm0, (%rdi)
+; AVX512BW-NEXT:vzeroupper
+; AVX512BW-NEXT:retq
+;
+; AVX512BWVL-LABEL: foo:
+; AVX512BWVL:   # %bb.0: # %entry
+; AVX512BWVL-NEXT:vpmovqd %ymm1, 16(%rdi)
+; AVX512BWVL-NEXT:vpmovqd %ymm0, (%rdi)
+; AVX512BWVL-NEXT:vzeroupper
+; AVX512BWVL-NEXT:retq
+entry:
+  %0 = shufflevector <4 x i64> %a, <4 x i64> %b, <8 x i32> 
+  %1 = trunc nsw <8 x i64> %0 to <8 x i32>
+  store <8 x i32> %1, ptr %p, align 16
+  ret void
+}

_

[llvm-branch-commits] [llvm] release/20.x: [X86] Ignore NSW when DstSVT is i32 (#131755) (PR #147034)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:

@RKSimon What do you think about merging this PR to the release branch?

https://github.com/llvm/llvm-project/pull/147034
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] release/20.x: [X86] Ignore NSW when DstSVT is i32 (#131755) (PR #147034)

2025-07-04 Thread via llvm-branch-commits

https://github.com/llvmbot milestoned 
https://github.com/llvm/llvm-project/pull/147034
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [BOLT][NFC] Update nfc-check-setup.py guidance (PR #146659)

2025-07-04 Thread Paschalis Mpeis via llvm-branch-commits

https://github.com/paschalis-mpeis updated 
https://github.com/llvm/llvm-project/pull/146659

>From 4284499a9286ceb7708531ae9b1108e25f58267c Mon Sep 17 00:00:00 2001
From: Paschalis Mpeis 
Date: Fri, 4 Jul 2025 14:54:58 +0100
Subject: [PATCH] [BOLT][NFC] Update nfc-check-setup.py guidance

---
 bolt/utils/nfc-check-setup.py | 53 ---
 1 file changed, 31 insertions(+), 22 deletions(-)

diff --git a/bolt/utils/nfc-check-setup.py b/bolt/utils/nfc-check-setup.py
index 18bf7522de17b..7191bbe122a9f 100755
--- a/bolt/utils/nfc-check-setup.py
+++ b/bolt/utils/nfc-check-setup.py
@@ -7,6 +7,8 @@
 import sys
 import textwrap
 
+msg_prefix="\n> NFC-Mode:"
+
 def get_relevant_bolt_changes(dir: str) -> str:
 # Return a list of bolt source changes that are relevant to testing.
 all_changes = subprocess.run(
@@ -49,7 +51,7 @@ def switch_back(
 # the HEAD is. Must be called after checking out the previous commit on all
 # exit paths.
 if switch_back:
-print("Switching back to current revision..")
+print(f"{msg_prefix} Switching back to current revision..")
 if stash:
 subprocess.run(shlex.split("git stash pop"), cwd=source_dir)
 subprocess.run(shlex.split(f"git checkout {old_ref}"), cwd=source_dir)
@@ -64,8 +66,10 @@ def main():
 parser = argparse.ArgumentParser(
 description=textwrap.dedent(
 """
-This script builds two versions of BOLT (with the current and
-previous revision).
+This script builds two versions of BOLT:
+llvm-bolt.new, using the current revision, and llvm-bolt.old using
+the previous revision. These can be used to check whether the
+current revision changes BOLT's functional behavior.
 """
 )
 )
@@ -104,7 +108,7 @@ def main():
 if not args.create_wrapper and len(wrapper_args) > 0:
 parser.parse_args()
 
-# find the repo directory
+# Find the repo directory.
 source_dir = None
 try:
 CMCacheFilename = f"{args.build_dir}/CMakeCache.txt"
@@ -118,13 +122,13 @@ def main():
 except Exception as e:
 sys.exit(e)
 
-# clean the previous llvm-bolt if it exists
+# Clean the previous llvm-bolt if it exists.
 bolt_path = f"{args.build_dir}/bin/llvm-bolt"
 if os.path.exists(bolt_path):
 os.remove(bolt_path)
 
-# build the current commit
-print("NFC-Setup: Building current revision..")
+# Build the current commit.
+print(f"{msg_prefix} Building current revision..")
 subprocess.run(
 shlex.split("cmake --build . --target llvm-bolt"), cwd=args.build_dir
 )
@@ -132,9 +136,8 @@ def main():
 if not os.path.exists(bolt_path):
 sys.exit(f"Failed to build the current revision: '{bolt_path}'")
 
-# rename llvm-bolt
+# Rename llvm-bolt and memorize the old hash for logging.
 os.replace(bolt_path, f"{bolt_path}.new")
-# memorize the old hash for logging
 old_ref = get_git_ref_or_rev(source_dir)
 
 if args.check_bolt_sources:
@@ -147,7 +150,7 @@ def main():
 print(f"BOLT source changes were found:\n{file_changes}")
 open(marker, "a").close()
 
-# determine whether a stash is needed
+# Determine whether a stash is needed.
 stash = subprocess.run(
 shlex.split("git status --porcelain"),
 cwd=source_dir,
@@ -156,32 +159,33 @@ def main():
 text=True,
 ).stdout
 if stash:
-# save local changes before checkout
+# Save local changes before checkout.
 subprocess.run(shlex.split("git stash push -u"), cwd=source_dir)
-# check out the previous/cmp commit
+
+# Check out the previous/cmp commit and get its commit hash for logging.
 subprocess.run(shlex.split(f"git checkout -f {args.cmp_rev}"), 
cwd=source_dir)
-# get the parent commit hash for logging
 new_ref = get_git_ref_or_rev(source_dir)
 
-# build the previous commit
-print("NFC-Setup: Building previous revision..")
+# Build the previous commit.
+print(f"{msg_prefix} Building previous revision..")
 subprocess.run(
 shlex.split("cmake --build . --target llvm-bolt"), cwd=args.build_dir
 )
 
-# rename llvm-bolt
+# Rename llvm-bolt.
 if not os.path.exists(bolt_path):
 print(f"Failed to build the previous revision: '{bolt_path}'")
 switch_back(args.switch_back, stash, source_dir, old_ref, new_ref)
 sys.exit(1)
 os.replace(bolt_path, f"{bolt_path}.old")
 
-# symlink llvm-bolt-wrapper
+# Symlink llvm-bolt-wrapper
 if args.create_wrapper:
+print(f"{msg_prefix} Creating llvm-bolt wrapper..")
 script_dir = os.path.dirname(os.path.abspath(__file__))
 wrapper_path = f"{script_dir}/llvm-bolt-wrapper.py"
 try:
-# set up llvm-bolt-wrapper.ini
+# Set up llvm-bolt-wrapper.ini
 ini = subprocess.che

[llvm-branch-commits] [mlir] [MLIR][OpenMP] Add canonical loop operations (PR #147061)

2025-07-04 Thread Michael Kruse via llvm-branch-commits

https://github.com/Meinersbur created 
https://github.com/llvm/llvm-project/pull/147061

Add the supporting OpenMP Dialect operations, types, and interfaces for 
modelling 

MLIR Operations:
 * omp.newcli
 * omp.canonical_loop

MLIR Types:
 * !omp.cli

MLIR Interfaces:
 * LoopTransformationInterface

As a first loop transformations to be able to use these new operation in 
follow-up PRs (#144785)
 * omp.unroll_heuristic 


If bikeshedding on the operation names, pretty formatting of operations inkl. 
future transformations such as `omp.tile`, and names of omp.cli values computed 
by `getAsmResultNames` (e.g. `%canonloop_s0`), I think this PR would be the 
right place.

>From c7ed06d92dc7e256bff5370eb3d74d3a43547625 Mon Sep 17 00:00:00 2001
From: Michael Kruse 
Date: Fri, 4 Jul 2025 14:50:46 +0200
Subject: [PATCH] Add omp.canonical_loop and omp.unroll modelling

---
 .../mlir/Dialect/OpenMP/OpenMPDialect.h   |   5 +
 .../mlir/Dialect/OpenMP/OpenMPOpBase.td   |  11 +
 mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td | 207 ++
 .../Dialect/OpenMP/OpenMPOpsInterfaces.td |  86 +
 mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp  | 353 ++
 .../OpenMP/cli-canonical_loop-invalid.mlir|  50 +++
 .../Dialect/OpenMP/cli-canonical_loop.mlir| 157 
 .../Dialect/OpenMP/cli-unroll-heuristic.mlir  |  59 +++
 8 files changed, 928 insertions(+)
 create mode 100644 mlir/test/Dialect/OpenMP/cli-canonical_loop-invalid.mlir
 create mode 100644 mlir/test/Dialect/OpenMP/cli-canonical_loop.mlir
 create mode 100644 mlir/test/Dialect/OpenMP/cli-unroll-heuristic.mlir

diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPDialect.h 
b/mlir/include/mlir/Dialect/OpenMP/OpenMPDialect.h
index ab11a6094e3e7..7cf738352ba47 100644
--- a/mlir/include/mlir/Dialect/OpenMP/OpenMPDialect.h
+++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPDialect.h
@@ -37,4 +37,9 @@
 #define GET_OP_CLASSES
 #include "mlir/Dialect/OpenMP/OpenMPOps.h.inc"
 
+namespace mlir::omp {
+/// Find the omp.new_cli, generator, and consumer of a canonical loop info.
+std::tuple decodeCli(mlir::Value cli);
+} // namespace mlir::omp
+
 #endif // MLIR_DIALECT_OPENMP_OPENMPDIALECT_H_
diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td 
b/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
index f3dd44d2c0717..bbcfb87fa03c6 100644
--- a/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
+++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
@@ -204,4 +204,15 @@ class OpenMP_Op traits = [],
   let regions = !if(singleRegion, (region AnyRegion:$region), (region));
 }
 
+
+// Base class for OpenMP loop transformations (that either consume or generate
+// loops)
+//
+// Doesn't actually create a C++ base class (only defines default values for
+// tablegen classes that derive from this). Use LoopTransformationInterface
+// instead for common operations.
+class OpenMPTransform_Op traits = []> :
+  OpenMP_Op], traits)  
> {
+}
+
 #endif  // OPENMP_OP_BASE
diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td 
b/mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td
index ac80926053a2d..703384a0680d0 100644
--- a/mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td
+++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td
@@ -22,6 +22,7 @@ include "mlir/Dialect/OpenMP/OpenMPOpBase.td"
 include "mlir/Interfaces/ControlFlowInterfaces.td"
 include "mlir/Interfaces/SideEffectInterfaces.td"
 include "mlir/IR/EnumAttr.td"
+include "mlir/IR/OpAsmInterface.td"
 include "mlir/IR/OpBase.td"
 include "mlir/IR/SymbolInterfaces.td"
 
@@ -356,6 +357,212 @@ def SingleOp : OpenMP_Op<"single", traits = [
   let hasVerifier = 1;
 }
 
+//===-===//
+// OpenMP Canonical Loop Info Type
+//===-===//
+
+def CanonicalLoopInfoType : OpenMP_Type<"CanonicalLoopInfo", "cli"> {
+  let summary = "Type for representing a reference to a canonical loop";
+  let description = [{
+A variable of type CanonicalLoopInfo refers to an OpenMP-compatible
+canonical loop in the same function. Values of this type are not
+available at runtime and therefore cannot be used by the program itself,
+i.e. an opaque type. It is similar to the transform dialect's
+`!transform.interface` type, but instead of implementing an interface
+for each transformation, the OpenMP dialect itself defines possible
+operations on this type.
+
+A value of type CanonicalLoopInfoType (in the following: CLI) value can be
+
+1. created by omp.new_cli.
+2. passed to omp.canonical_loop to associate the loop to that CLI. A CLI
+   can only be associated once.
+3. passed to an omp loop transformation operation that modifies the loop
+   associated with the CLI. The CLI is the "applyee" and the operation is
+   the consumer. A CLI can only be consumed once.
+4. passed to an omp loop transformation operation to associate the cli with
+   

[llvm-branch-commits] [llvm] [BOLT][NFC] Update nfc-check-setup.py guidance (PR #146659)

2025-07-04 Thread via llvm-branch-commits

github-actions[bot] wrote:




:warning: Python code formatter, darker found issues in your code. :warning:



You can test this locally with the following command:


``bash
darker --check --diff -r HEAD~1...HEAD bolt/utils/nfc-check-setup.py
``





View the diff from darker here.


``diff
--- nfc-check-setup.py  2025-07-04 14:10:54.00 +
+++ nfc-check-setup.py  2025-07-04 14:15:42.929615 +
@@ -5,11 +5,12 @@
 import shlex
 import subprocess
 import sys
 import textwrap
 
-msg_prefix="\n> NFC-Mode:"
+msg_prefix = "\n> NFC-Mode:"
+
 
 def get_relevant_bolt_changes(dir: str) -> str:
 # Return a list of bolt source changes that are relevant to testing.
 all_changes = subprocess.run(
 shlex.split("git show HEAD --name-only --pretty=''"),
@@ -209,10 +210,10 @@
 if args.create_wrapper:
 print(
 "Can run BOLT tests using:\n"
 "\tbin/llvm-lit -sv tools/bolt/test\nor\n"
 "\tbin/llvm-lit -sv tools/bolttests"
-)
+)
 
 
 if __name__ == "__main__":
 main()

``




https://github.com/llvm/llvm-project/pull/146659
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [BOLT][NFC] Update nfc-check-setup.py guidance (PR #146659)

2025-07-04 Thread Paschalis Mpeis via llvm-branch-commits

https://github.com/paschalis-mpeis updated 
https://github.com/llvm/llvm-project/pull/146659

>From 2b5e54e8f3ed5f29a495a92e4e93725c74df Mon Sep 17 00:00:00 2001
From: Paschalis Mpeis 
Date: Fri, 4 Jul 2025 14:54:58 +0100
Subject: [PATCH] [BOLT][NFC] Update nfc-check-setup.py guidance

---
 bolt/utils/nfc-check-setup.py | 53 ---
 1 file changed, 31 insertions(+), 22 deletions(-)

diff --git a/bolt/utils/nfc-check-setup.py b/bolt/utils/nfc-check-setup.py
index 18bf7522de17b..d8666e2158499 100755
--- a/bolt/utils/nfc-check-setup.py
+++ b/bolt/utils/nfc-check-setup.py
@@ -7,6 +7,8 @@
 import sys
 import textwrap
 
+msg_prefix = "\n> NFC-Mode:"
+
 def get_relevant_bolt_changes(dir: str) -> str:
 # Return a list of bolt source changes that are relevant to testing.
 all_changes = subprocess.run(
@@ -49,7 +51,7 @@ def switch_back(
 # the HEAD is. Must be called after checking out the previous commit on all
 # exit paths.
 if switch_back:
-print("Switching back to current revision..")
+print(f"{msg_prefix} Switching back to current revision..")
 if stash:
 subprocess.run(shlex.split("git stash pop"), cwd=source_dir)
 subprocess.run(shlex.split(f"git checkout {old_ref}"), cwd=source_dir)
@@ -64,8 +66,10 @@ def main():
 parser = argparse.ArgumentParser(
 description=textwrap.dedent(
 """
-This script builds two versions of BOLT (with the current and
-previous revision).
+This script builds two versions of BOLT:
+llvm-bolt.new, using the current revision, and llvm-bolt.old using
+the previous revision. These can be used to check whether the
+current revision changes BOLT's functional behavior.
 """
 )
 )
@@ -104,7 +108,7 @@ def main():
 if not args.create_wrapper and len(wrapper_args) > 0:
 parser.parse_args()
 
-# find the repo directory
+# Find the repo directory.
 source_dir = None
 try:
 CMCacheFilename = f"{args.build_dir}/CMakeCache.txt"
@@ -118,13 +122,13 @@ def main():
 except Exception as e:
 sys.exit(e)
 
-# clean the previous llvm-bolt if it exists
+# Clean the previous llvm-bolt if it exists.
 bolt_path = f"{args.build_dir}/bin/llvm-bolt"
 if os.path.exists(bolt_path):
 os.remove(bolt_path)
 
-# build the current commit
-print("NFC-Setup: Building current revision..")
+# Build the current commit.
+print(f"{msg_prefix} Building current revision..")
 subprocess.run(
 shlex.split("cmake --build . --target llvm-bolt"), cwd=args.build_dir
 )
@@ -132,9 +136,8 @@ def main():
 if not os.path.exists(bolt_path):
 sys.exit(f"Failed to build the current revision: '{bolt_path}'")
 
-# rename llvm-bolt
+# Rename llvm-bolt and memorize the old hash for logging.
 os.replace(bolt_path, f"{bolt_path}.new")
-# memorize the old hash for logging
 old_ref = get_git_ref_or_rev(source_dir)
 
 if args.check_bolt_sources:
@@ -147,7 +150,7 @@ def main():
 print(f"BOLT source changes were found:\n{file_changes}")
 open(marker, "a").close()
 
-# determine whether a stash is needed
+# Determine whether a stash is needed.
 stash = subprocess.run(
 shlex.split("git status --porcelain"),
 cwd=source_dir,
@@ -156,32 +159,33 @@ def main():
 text=True,
 ).stdout
 if stash:
-# save local changes before checkout
+# Save local changes before checkout.
 subprocess.run(shlex.split("git stash push -u"), cwd=source_dir)
-# check out the previous/cmp commit
+
+# Check out the previous/cmp commit and get its commit hash for logging.
 subprocess.run(shlex.split(f"git checkout -f {args.cmp_rev}"), 
cwd=source_dir)
-# get the parent commit hash for logging
 new_ref = get_git_ref_or_rev(source_dir)
 
-# build the previous commit
-print("NFC-Setup: Building previous revision..")
+# Build the previous commit.
+print(f"{msg_prefix} Building previous revision..")
 subprocess.run(
 shlex.split("cmake --build . --target llvm-bolt"), cwd=args.build_dir
 )
 
-# rename llvm-bolt
+# Rename llvm-bolt.
 if not os.path.exists(bolt_path):
 print(f"Failed to build the previous revision: '{bolt_path}'")
 switch_back(args.switch_back, stash, source_dir, old_ref, new_ref)
 sys.exit(1)
 os.replace(bolt_path, f"{bolt_path}.old")
 
-# symlink llvm-bolt-wrapper
+# Symlink llvm-bolt-wrapper
 if args.create_wrapper:
+print(f"{msg_prefix} Creating llvm-bolt wrapper..")
 script_dir = os.path.dirname(os.path.abspath(__file__))
 wrapper_path = f"{script_dir}/llvm-bolt-wrapper.py"
 try:
-# set up llvm-bolt-wrapper.ini
+# Set up llvm-bolt-wrapper.ini
 ini = subprocess.c

[llvm-branch-commits] [llvm] [BOLT][NFC] Update nfc-check-setup.py guidance (PR #146659)

2025-07-04 Thread Paschalis Mpeis via llvm-branch-commits


@@ -156,9 +158,8 @@ def main():
 os.replace(bolt_path, f"{bolt_path}.old")
 
 print(
-f"Build directory {args.build_dir} is ready to run BOLT tests, e.g.\n"
-"\tbin/llvm-lit -sv tools/bolt/test\nor\n"
-"\tbin/llvm-lit -sv tools/bolttests"
+f"Build directory {args.build_dir} is ready for NFC-Mode comparison "
+"between the two revisions."

paschalis-mpeis wrote:

Forced pushed to rebase and handle this.
`llvm-bolt` is available only when the `--create-wrapper` flag is used (as a 
wrapper).
In that case, the commands are valid and now printed.

Also applied a few more nits.

https://github.com/llvm/llvm-project/pull/146659
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] release/20.x: [X86] Ignore NSW when DstSVT is i32 (#131755) (PR #147034)

2025-07-04 Thread Simon Pilgrim via llvm-branch-commits

https://github.com/RKSimon approved this pull request.


https://github.com/llvm/llvm-project/pull/147034
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [AArch64][PAC] Combine signing with address materialization (PR #130809)

2025-07-04 Thread Anatoly Trosinenko via llvm-branch-commits

https://github.com/atrosinenko updated 
https://github.com/llvm/llvm-project/pull/130809

>From 4c5d1884605dbbb316b0764f48af199ad95818e9 Mon Sep 17 00:00:00 2001
From: Anatoly Trosinenko 
Date: Mon, 10 Mar 2025 15:14:55 +0300
Subject: [PATCH 1/2] [AArch64][PAC] Precommit tests on merging
 MOVaddr/LOADgotAUTH with PAC*

---
 .../GlobalISel/ptrauth-constant-in-code.ll| 76 +++
 .../AArch64/ptrauth-constant-in-code.ll   | 71 +
 2 files changed, 147 insertions(+)

diff --git a/llvm/test/CodeGen/AArch64/GlobalISel/ptrauth-constant-in-code.ll 
b/llvm/test/CodeGen/AArch64/GlobalISel/ptrauth-constant-in-code.ll
index 12a3448111fcb..140e29f942a79 100644
--- a/llvm/test/CodeGen/AArch64/GlobalISel/ptrauth-constant-in-code.ll
+++ b/llvm/test/CodeGen/AArch64/GlobalISel/ptrauth-constant-in-code.ll
@@ -78,6 +78,82 @@ define ptr @foo() {
   ret ptr ptrauth (ptr @g, i32 0)
 }
 
+;--- finalize-isel.ll
+
+; RUN: llc < finalize-isel.ll -mtriple aarch64-elf -mattr=+pauth 
-global-isel=1 \
+; RUN:   -verify-machineinstrs -global-isel-abort=1 -stop-after=finalize-isel 
| \
+; RUN:   FileCheck --check-prefixes=ISEL,ISEL-ELF %s
+; RUN: llc < finalize-isel.ll -mtriple arm64-apple-ios -mattr=+pauth 
-global-isel=1 \
+; RUN:   -verify-machineinstrs -global-isel-abort=1 -stop-after=finalize-isel 
| \
+; RUN:   FileCheck --check-prefixes=ISEL %s
+
+@const_table_local = dso_local constant [3 x ptr] [ptr null, ptr null, ptr 
null]
+@const_table_got = constant [3 x ptr] [ptr null, ptr null, ptr null]
+
+define void @store_signed_const_local(ptr %dest) {
+; ISEL-LABEL: name: store_signed_const_local
+; ISEL:   body:
+; ISEL: %0:gpr64common = COPY $x0
+; ISEL-NEXT:%10:gpr64common = MOVaddr target-flags(aarch64-page) 
@const_table_local + 8, target-flags(aarch64-pageoff, aarch64-nc) 
@const_table_local + 8
+; ISEL-NEXT:%2:gpr64noip = MOVKXi %0, 1234
+; ISEL-NEXT:%15:gpr64noip = COPY %0
+; ISEL-NEXT:%4:gpr64 = PAC %10, 2, 1234, %15, implicit-def dead $x17
+; ISEL-NEXT:%14:gpr64 = COPY %4
+; ISEL-NEXT:STRXui %14, %0, 0 :: (store (p0) into %ir.dest)
+; ISEL-NEXT:RET_ReallyLR
+  %dest.i = ptrtoint ptr %dest to i64
+  %discr = call i64 @llvm.ptrauth.blend(i64 %dest.i, i64 1234)
+  %signed.i = call i64 @llvm.ptrauth.sign(i64 ptrtoint (ptr getelementptr ([2 
x ptr], ptr @const_table_local, i32 0, i32 1) to i64), i32 2, i64 %discr)
+  %signed.ptr = inttoptr i64 %signed.i to ptr
+  store ptr %signed.ptr, ptr %dest
+  ret void
+}
+
+define void @store_signed_const_got(ptr %dest) {
+; ISEL-ELF-LABEL: name: store_signed_const_got
+; ISEL-ELF:   body:
+; ISEL-ELF: %0:gpr64common = COPY $x0
+; ISEL-ELF-NEXT:%7:gpr64common = LOADgotAUTH target-flags(aarch64-got) 
@const_table_got
+; ISEL-ELF-NEXT:%6:gpr64common = ADDXri %7, 8, 0
+; ISEL-ELF-NEXT:%2:gpr64noip = MOVKXi %0, 1234
+; ISEL-ELF-NEXT:%12:gpr64noip = COPY %0
+; ISEL-ELF-NEXT:%4:gpr64 = PAC %6, 2, 1234, %12, implicit-def dead $x17
+; ISEL-ELF-NEXT:%10:gpr64 = COPY %4
+; ISEL-ELF-NEXT:STRXui %10, %0, 0 :: (store (p0) into %ir.dest)
+; ISEL-ELF-NEXT:RET_ReallyLR
+  %dest.i = ptrtoint ptr %dest to i64
+  %discr = call i64 @llvm.ptrauth.blend(i64 %dest.i, i64 1234)
+  %signed.i = call i64 @llvm.ptrauth.sign(i64 ptrtoint (ptr getelementptr ([2 
x ptr], ptr @const_table_got, i32 0, i32 1) to i64), i32 2, i64 %discr)
+  %signed.ptr = inttoptr i64 %signed.i to ptr
+  store ptr %signed.ptr, ptr %dest
+  ret void
+}
+
+define void @store_signed_arg(ptr %dest, ptr %p) {
+; ISEL-LABEL: name: store_signed_arg
+; ISEL:   body:
+; ISEL: %0:gpr64common = COPY $x0
+; ISEL-NEXT:%1:gpr64common = COPY $x1
+; ISEL-NEXT:%3:gpr64noip = MOVKXi %0, 1234
+; ISEL-NEXT:%6:gpr64common = ADDXri %1, 8, 0
+; ISEL-NEXT:%12:gpr64noip = COPY %0
+; ISEL-NEXT:%8:gpr64 = PAC %6, 2, 1234, %12, implicit-def dead $x17
+; ISEL-NEXT:%10:gpr64 = COPY %8
+; ISEL-NEXT:STRXui %10, %0, 0 :: (store (p0) into %ir.dest)
+; ISEL-NEXT:RET_ReallyLR
+  %dest.i = ptrtoint ptr %dest to i64
+  %discr = call i64 @llvm.ptrauth.blend(i64 %dest.i, i64 1234)
+  %p.offset = getelementptr [2 x ptr], ptr %p, i32 0, i32 1
+  %p.offset.i = ptrtoint ptr %p.offset to i64
+  %signed.i = call i64 @llvm.ptrauth.sign(i64 %p.offset.i, i32 2, i64 %discr)
+  %signed.ptr = inttoptr i64 %signed.i to ptr
+  store ptr %signed.ptr, ptr %dest
+  ret void
+}
+
+!llvm.module.flags = !{!0}
+!0 = !{i32 8, !"ptrauth-elf-got", i32 1}
+
 ;--- ok.ll
 
 ; RUN: llc < ok.ll -mtriple aarch64-elf -mattr=+pauth -global-isel=1 \
diff --git a/llvm/test/CodeGen/AArch64/ptrauth-constant-in-code.ll 
b/llvm/test/CodeGen/AArch64/ptrauth-constant-in-code.ll
index 76339a7cc5791..429ff6e5489aa 100644
--- a/llvm/test/CodeGen/AArch64/ptrauth-constant-in-code.ll
+++ b/llvm/test/CodeGen/AArch64/ptrauth-constant-in-code.ll
@@ -69,6 +69,77 @@ define ptr @foo() {
   ret ptr ptrauth (ptr @g, i32 0)
 }
 
+;--- finalize-isel.ll
+
+; RUN: llc < final

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

https://github.com/joaosaffran updated 
https://github.com/llvm/llvm-project/pull/146785

>From a49aa19297811e5800ffce364d8d6a225109d93f Mon Sep 17 00:00:00 2001
From: joaosaffran 
Date: Thu, 26 Jun 2025 19:28:01 +
Subject: [PATCH 1/7] refactoring

---
 .../lib/Target/DirectX/DXContainerGlobals.cpp |  4 ++-
 llvm/lib/Target/DirectX/DXILRootSignature.cpp | 14 +++-
 llvm/lib/Target/DirectX/DXILRootSignature.h   | 33 +--
 3 files changed, 23 insertions(+), 28 deletions(-)

diff --git a/llvm/lib/Target/DirectX/DXContainerGlobals.cpp 
b/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
index 6c8ae8eaaea77..e076283b65193 100644
--- a/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
+++ b/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
@@ -160,11 +160,13 @@ void DXContainerGlobals::addRootSignature(Module &M,
 
   assert(MMI.EntryPropertyVec.size() == 1);
 
+  auto &RSA = getAnalysis().getRSInfo();
   auto &RSA = getAnalysis().getRSInfo();
   const Function *EntryFunction = MMI.EntryPropertyVec[0].Entry;
   const auto &RS = RSA.getDescForFunction(EntryFunction);
+  const auto &RS = RSA.getDescForFunction(EntryFunction);
 
-  if (!RS)
+  if (!RS )
 return;
 
   SmallString<256> Data;
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.cpp 
b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
index 5a53ea8a3631b..4094df160ef6f 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.cpp
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
@@ -554,12 +554,9 @@ analyzeModule(Module &M) {
 
 AnalysisKey RootSignatureAnalysis::Key;
 
-RootSignatureAnalysis::Result
-RootSignatureAnalysis::run(Module &M, ModuleAnalysisManager &AM) {
-  if (!AnalysisResult)
-AnalysisResult = std::make_unique(
-RootSignatureBindingInfo(analyzeModule(M)));
-  return *AnalysisResult;
+RootSignatureBindingInfo RootSignatureAnalysis::run(Module &M,
+ModuleAnalysisManager &AM) 
{
+  return RootSignatureBindingInfo(analyzeModule(M));
 }
 
 
//===--===//
@@ -638,9 +635,8 @@ PreservedAnalyses RootSignatureAnalysisPrinter::run(Module 
&M,
 
 
//===--===//
 bool RootSignatureAnalysisWrapper::runOnModule(Module &M) {
-  if (!FuncToRsMap)
-FuncToRsMap = std::make_unique(
-RootSignatureBindingInfo(analyzeModule(M)));
+  FuncToRsMap = std::make_unique(
+  RootSignatureBindingInfo(analyzeModule(M)));
   return false;
 }
 
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.h 
b/llvm/lib/Target/DirectX/DXILRootSignature.h
index 3832182277050..24b1a8d3d2abe 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.h
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.h
@@ -37,30 +37,28 @@ enum class RootSignatureElementKind {
 };
 
 class RootSignatureBindingInfo {
-private:
-  SmallDenseMap FuncToRsMap;
+  private:
+SmallDenseMap FuncToRsMap;
 
-public:
+  public:
   using iterator =
-  SmallDenseMap::iterator;
+SmallDenseMap::iterator;
 
-  RootSignatureBindingInfo() = default;
-  RootSignatureBindingInfo(
-  SmallDenseMap Map)
-  : FuncToRsMap(Map) {};
+  RootSignatureBindingInfo () = default;
+  RootSignatureBindingInfo(SmallDenseMap Map) : FuncToRsMap(Map) {};
 
   iterator find(const Function *F) { return FuncToRsMap.find(F); }
 
   iterator end() { return FuncToRsMap.end(); }
 
-  std::optional
-  getDescForFunction(const Function *F) {
+  std::optional getDescForFunction(const Function* 
F) {
 const auto FuncRs = find(F);
 if (FuncRs == end())
   return std::nullopt;
 
 return FuncRs->second;
   }
+  
 };
 
 class RootSignatureAnalysis : public AnalysisInfoMixin {
@@ -68,14 +66,13 @@ class RootSignatureAnalysis : public 
AnalysisInfoMixin {
   static AnalysisKey Key;
 
 public:
-  RootSignatureAnalysis() = default;
-
-  using Result = RootSignatureBindingInfo;
 
-  Result run(Module &M, ModuleAnalysisManager &AM);
+RootSignatureAnalysis() = default;
 
-private:
-  std::unique_ptr AnalysisResult;
+  using Result = RootSignatureBindingInfo;
+  
+  RootSignatureBindingInfo
+  run(Module &M, ModuleAnalysisManager &AM);
 };
 
 /// Wrapper pass for the legacy pass manager.
@@ -92,8 +89,8 @@ class RootSignatureAnalysisWrapper : public ModulePass {
 
   RootSignatureAnalysisWrapper() : ModulePass(ID) {}
 
-  RootSignatureBindingInfo &getRSInfo() { return *FuncToRsMap; }
-
+  RootSignatureBindingInfo& getRSInfo() {return *FuncToRsMap;}
+  
   bool runOnModule(Module &M) override;
 
   void getAnalysisUsage(AnalysisUsage &AU) const override;

>From d90676feb6bfc0ca8bbdaee5c347ecc49e396b5b Mon Sep 17 00:00:00 2001
From: joaosaffran 
Date: Thu, 26 Jun 2025 21:37:11 +
Subject: [PATCH 2/7] init refactoring

---
 .../SemaHLSL/RootSignature-Validation.hlsl| 42 +
 .../lib/Target/DirectX/DXContainerGlobals.cpp |  2 +-
 .../DXILPostOptimizationValidation.cpp| 47 

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

https://github.com/joaosaffran updated 
https://github.com/llvm/llvm-project/pull/146785

>From a49aa19297811e5800ffce364d8d6a225109d93f Mon Sep 17 00:00:00 2001
From: joaosaffran 
Date: Thu, 26 Jun 2025 19:28:01 +
Subject: [PATCH 1/8] refactoring

---
 .../lib/Target/DirectX/DXContainerGlobals.cpp |  4 ++-
 llvm/lib/Target/DirectX/DXILRootSignature.cpp | 14 +++-
 llvm/lib/Target/DirectX/DXILRootSignature.h   | 33 +--
 3 files changed, 23 insertions(+), 28 deletions(-)

diff --git a/llvm/lib/Target/DirectX/DXContainerGlobals.cpp 
b/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
index 6c8ae8eaaea77..e076283b65193 100644
--- a/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
+++ b/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
@@ -160,11 +160,13 @@ void DXContainerGlobals::addRootSignature(Module &M,
 
   assert(MMI.EntryPropertyVec.size() == 1);
 
+  auto &RSA = getAnalysis().getRSInfo();
   auto &RSA = getAnalysis().getRSInfo();
   const Function *EntryFunction = MMI.EntryPropertyVec[0].Entry;
   const auto &RS = RSA.getDescForFunction(EntryFunction);
+  const auto &RS = RSA.getDescForFunction(EntryFunction);
 
-  if (!RS)
+  if (!RS )
 return;
 
   SmallString<256> Data;
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.cpp 
b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
index 5a53ea8a3631b..4094df160ef6f 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.cpp
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
@@ -554,12 +554,9 @@ analyzeModule(Module &M) {
 
 AnalysisKey RootSignatureAnalysis::Key;
 
-RootSignatureAnalysis::Result
-RootSignatureAnalysis::run(Module &M, ModuleAnalysisManager &AM) {
-  if (!AnalysisResult)
-AnalysisResult = std::make_unique(
-RootSignatureBindingInfo(analyzeModule(M)));
-  return *AnalysisResult;
+RootSignatureBindingInfo RootSignatureAnalysis::run(Module &M,
+ModuleAnalysisManager &AM) 
{
+  return RootSignatureBindingInfo(analyzeModule(M));
 }
 
 
//===--===//
@@ -638,9 +635,8 @@ PreservedAnalyses RootSignatureAnalysisPrinter::run(Module 
&M,
 
 
//===--===//
 bool RootSignatureAnalysisWrapper::runOnModule(Module &M) {
-  if (!FuncToRsMap)
-FuncToRsMap = std::make_unique(
-RootSignatureBindingInfo(analyzeModule(M)));
+  FuncToRsMap = std::make_unique(
+  RootSignatureBindingInfo(analyzeModule(M)));
   return false;
 }
 
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.h 
b/llvm/lib/Target/DirectX/DXILRootSignature.h
index 3832182277050..24b1a8d3d2abe 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.h
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.h
@@ -37,30 +37,28 @@ enum class RootSignatureElementKind {
 };
 
 class RootSignatureBindingInfo {
-private:
-  SmallDenseMap FuncToRsMap;
+  private:
+SmallDenseMap FuncToRsMap;
 
-public:
+  public:
   using iterator =
-  SmallDenseMap::iterator;
+SmallDenseMap::iterator;
 
-  RootSignatureBindingInfo() = default;
-  RootSignatureBindingInfo(
-  SmallDenseMap Map)
-  : FuncToRsMap(Map) {};
+  RootSignatureBindingInfo () = default;
+  RootSignatureBindingInfo(SmallDenseMap Map) : FuncToRsMap(Map) {};
 
   iterator find(const Function *F) { return FuncToRsMap.find(F); }
 
   iterator end() { return FuncToRsMap.end(); }
 
-  std::optional
-  getDescForFunction(const Function *F) {
+  std::optional getDescForFunction(const Function* 
F) {
 const auto FuncRs = find(F);
 if (FuncRs == end())
   return std::nullopt;
 
 return FuncRs->second;
   }
+  
 };
 
 class RootSignatureAnalysis : public AnalysisInfoMixin {
@@ -68,14 +66,13 @@ class RootSignatureAnalysis : public 
AnalysisInfoMixin {
   static AnalysisKey Key;
 
 public:
-  RootSignatureAnalysis() = default;
-
-  using Result = RootSignatureBindingInfo;
 
-  Result run(Module &M, ModuleAnalysisManager &AM);
+RootSignatureAnalysis() = default;
 
-private:
-  std::unique_ptr AnalysisResult;
+  using Result = RootSignatureBindingInfo;
+  
+  RootSignatureBindingInfo
+  run(Module &M, ModuleAnalysisManager &AM);
 };
 
 /// Wrapper pass for the legacy pass manager.
@@ -92,8 +89,8 @@ class RootSignatureAnalysisWrapper : public ModulePass {
 
   RootSignatureAnalysisWrapper() : ModulePass(ID) {}
 
-  RootSignatureBindingInfo &getRSInfo() { return *FuncToRsMap; }
-
+  RootSignatureBindingInfo& getRSInfo() {return *FuncToRsMap;}
+  
   bool runOnModule(Module &M) override;
 
   void getAnalysisUsage(AnalysisUsage &AU) const override;

>From d90676feb6bfc0ca8bbdaee5c347ecc49e396b5b Mon Sep 17 00:00:00 2001
From: joaosaffran 
Date: Thu, 26 Jun 2025 21:37:11 +
Subject: [PATCH 2/8] init refactoring

---
 .../SemaHLSL/RootSignature-Validation.hlsl| 42 +
 .../lib/Target/DirectX/DXContainerGlobals.cpp |  2 +-
 .../DXILPostOptimizationValidation.cpp| 47 

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

https://github.com/joaosaffran updated 
https://github.com/llvm/llvm-project/pull/146785

>From a49aa19297811e5800ffce364d8d6a225109d93f Mon Sep 17 00:00:00 2001
From: joaosaffran 
Date: Thu, 26 Jun 2025 19:28:01 +
Subject: [PATCH 1/9] refactoring

---
 .../lib/Target/DirectX/DXContainerGlobals.cpp |  4 ++-
 llvm/lib/Target/DirectX/DXILRootSignature.cpp | 14 +++-
 llvm/lib/Target/DirectX/DXILRootSignature.h   | 33 +--
 3 files changed, 23 insertions(+), 28 deletions(-)

diff --git a/llvm/lib/Target/DirectX/DXContainerGlobals.cpp 
b/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
index 6c8ae8eaaea77..e076283b65193 100644
--- a/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
+++ b/llvm/lib/Target/DirectX/DXContainerGlobals.cpp
@@ -160,11 +160,13 @@ void DXContainerGlobals::addRootSignature(Module &M,
 
   assert(MMI.EntryPropertyVec.size() == 1);
 
+  auto &RSA = getAnalysis().getRSInfo();
   auto &RSA = getAnalysis().getRSInfo();
   const Function *EntryFunction = MMI.EntryPropertyVec[0].Entry;
   const auto &RS = RSA.getDescForFunction(EntryFunction);
+  const auto &RS = RSA.getDescForFunction(EntryFunction);
 
-  if (!RS)
+  if (!RS )
 return;
 
   SmallString<256> Data;
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.cpp 
b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
index 5a53ea8a3631b..4094df160ef6f 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.cpp
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
@@ -554,12 +554,9 @@ analyzeModule(Module &M) {
 
 AnalysisKey RootSignatureAnalysis::Key;
 
-RootSignatureAnalysis::Result
-RootSignatureAnalysis::run(Module &M, ModuleAnalysisManager &AM) {
-  if (!AnalysisResult)
-AnalysisResult = std::make_unique(
-RootSignatureBindingInfo(analyzeModule(M)));
-  return *AnalysisResult;
+RootSignatureBindingInfo RootSignatureAnalysis::run(Module &M,
+ModuleAnalysisManager &AM) 
{
+  return RootSignatureBindingInfo(analyzeModule(M));
 }
 
 
//===--===//
@@ -638,9 +635,8 @@ PreservedAnalyses RootSignatureAnalysisPrinter::run(Module 
&M,
 
 
//===--===//
 bool RootSignatureAnalysisWrapper::runOnModule(Module &M) {
-  if (!FuncToRsMap)
-FuncToRsMap = std::make_unique(
-RootSignatureBindingInfo(analyzeModule(M)));
+  FuncToRsMap = std::make_unique(
+  RootSignatureBindingInfo(analyzeModule(M)));
   return false;
 }
 
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.h 
b/llvm/lib/Target/DirectX/DXILRootSignature.h
index 3832182277050..24b1a8d3d2abe 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.h
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.h
@@ -37,30 +37,28 @@ enum class RootSignatureElementKind {
 };
 
 class RootSignatureBindingInfo {
-private:
-  SmallDenseMap FuncToRsMap;
+  private:
+SmallDenseMap FuncToRsMap;
 
-public:
+  public:
   using iterator =
-  SmallDenseMap::iterator;
+SmallDenseMap::iterator;
 
-  RootSignatureBindingInfo() = default;
-  RootSignatureBindingInfo(
-  SmallDenseMap Map)
-  : FuncToRsMap(Map) {};
+  RootSignatureBindingInfo () = default;
+  RootSignatureBindingInfo(SmallDenseMap Map) : FuncToRsMap(Map) {};
 
   iterator find(const Function *F) { return FuncToRsMap.find(F); }
 
   iterator end() { return FuncToRsMap.end(); }
 
-  std::optional
-  getDescForFunction(const Function *F) {
+  std::optional getDescForFunction(const Function* 
F) {
 const auto FuncRs = find(F);
 if (FuncRs == end())
   return std::nullopt;
 
 return FuncRs->second;
   }
+  
 };
 
 class RootSignatureAnalysis : public AnalysisInfoMixin {
@@ -68,14 +66,13 @@ class RootSignatureAnalysis : public 
AnalysisInfoMixin {
   static AnalysisKey Key;
 
 public:
-  RootSignatureAnalysis() = default;
-
-  using Result = RootSignatureBindingInfo;
 
-  Result run(Module &M, ModuleAnalysisManager &AM);
+RootSignatureAnalysis() = default;
 
-private:
-  std::unique_ptr AnalysisResult;
+  using Result = RootSignatureBindingInfo;
+  
+  RootSignatureBindingInfo
+  run(Module &M, ModuleAnalysisManager &AM);
 };
 
 /// Wrapper pass for the legacy pass manager.
@@ -92,8 +89,8 @@ class RootSignatureAnalysisWrapper : public ModulePass {
 
   RootSignatureAnalysisWrapper() : ModulePass(ID) {}
 
-  RootSignatureBindingInfo &getRSInfo() { return *FuncToRsMap; }
-
+  RootSignatureBindingInfo& getRSInfo() {return *FuncToRsMap;}
+  
   bool runOnModule(Module &M) override;
 
   void getAnalysisUsage(AnalysisUsage &AU) const override;

>From d90676feb6bfc0ca8bbdaee5c347ecc49e396b5b Mon Sep 17 00:00:00 2001
From: joaosaffran 
Date: Thu, 26 Jun 2025 21:37:11 +
Subject: [PATCH 2/9] init refactoring

---
 .../SemaHLSL/RootSignature-Validation.hlsl| 42 +
 .../lib/Target/DirectX/DXContainerGlobals.cpp |  2 +-
 .../DXILPostOptimizationValidation.cpp| 47 

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-hlsl

Author: None (joaosaffran)


Changes

DXC checks if registers are correctly bound to root signature descriptors. This 
implements the same check. 

Closes: [126645](https://github.com/llvm/llvm-project/issues/126645)

---
Full diff: https://github.com/llvm/llvm-project/pull/146785.diff


7 Files Affected:

- (added) clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl (+35) 
- (added) clang/test/SemaHLSL/RootSignature-Validation.hlsl (+33) 
- (modified) llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp 
(+133-3) 
- (modified) llvm/lib/Target/DirectX/DXILPostOptimizationValidation.h (+119) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-AllValidFlagCombinationsV1.ll
 (+2-2) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable.ll (+2-2) 
- (modified) llvm/test/CodeGen/DirectX/llc-pipeline.ll (+1) 


``diff
diff --git a/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl 
b/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl
new file mode 100644
index 0..b590ed67e7085
--- /dev/null
+++ b/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl
@@ -0,0 +1,35 @@
+// RUN: not %clang_dxc -T cs_6_6 -E CSMain %s 2>&1 | FileCheck %s
+
+// CHECK: error: register cbuffer (space=665, register=3) is not defined in 
Root Signature
+// CHECK: error: register srv (space=0, register=0) is not defined in Root 
Signature
+// CHECK: error: register uav (space=0, register=4294967295) is not defined in 
Root Signature
+
+
+#define ROOT_SIGNATURE \
+"CBV(b3, space=666, visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(SRV(t0, space=0, numDescriptors=1), 
visibility=SHADER_VISIBILITY_VERTEX), " \
+"DescriptorTable(Sampler(s0, numDescriptors=2), 
visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(UAV(u0, numDescriptors=unbounded), 
visibility=SHADER_VISIBILITY_ALL)"
+
+cbuffer CB : register(b3, space665) {
+  float a;
+}
+
+StructuredBuffer In : register(t0, space0);
+RWStructuredBuffer Out : register(u0);
+
+RWBuffer UAV : register(u4294967295);
+
+RWBuffer UAV1 : register(u2), UAV2 : register(u4);
+
+RWBuffer UAV3 : register(space0);
+
+
+
+// Compute Shader for UAV testing
+[numthreads(8, 8, 1)]
+[RootSignature(ROOT_SIGNATURE)]
+void CSMain(uint id : SV_GroupID)
+{
+Out[0] = a + id + In[0] + UAV[0] + UAV1[0] + UAV3[0];
+}
diff --git a/clang/test/SemaHLSL/RootSignature-Validation.hlsl 
b/clang/test/SemaHLSL/RootSignature-Validation.hlsl
new file mode 100644
index 0..5a7f5baf00619
--- /dev/null
+++ b/clang/test/SemaHLSL/RootSignature-Validation.hlsl
@@ -0,0 +1,33 @@
+// RUN: %clang_dxc -T cs_6_6 -E CSMain %s 2>&1 
+
+// expected-no-diagnostics
+
+
+#define ROOT_SIGNATURE \
+"CBV(b3, space=1, visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(SRV(t0, space=0, numDescriptors=1), 
visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(Sampler(s0, numDescriptors=2), 
visibility=SHADER_VISIBILITY_VERTEX), " \
+"DescriptorTable(UAV(u0, numDescriptors=unbounded), 
visibility=SHADER_VISIBILITY_ALL)"
+
+cbuffer CB : register(b3, space1) {
+  float a;
+}
+
+StructuredBuffer In : register(t0, space0);
+RWStructuredBuffer Out : register(u0);
+
+RWBuffer UAV : register(u4294967294);
+
+RWBuffer UAV1 : register(u2), UAV2 : register(u4);
+
+RWBuffer UAV3 : register(space0);
+
+
+
+// Compute Shader for UAV testing
+[numthreads(8, 8, 1)]
+[RootSignature(ROOT_SIGNATURE)]
+void CSMain(uint id : SV_GroupID)
+{
+Out[0] = a + id + In[0] + UAV[0] + UAV1[0] + UAV3[0];
+}
diff --git a/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp 
b/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
index 398dcbb8d1737..a52a04323514c 100644
--- a/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
+++ b/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
@@ -7,6 +7,7 @@
 
//===--===//
 
 #include "DXILPostOptimizationValidation.h"
+#include "DXILRootSignature.h"
 #include "DXILShaderFlags.h"
 #include "DirectX.h"
 #include "llvm/ADT/SmallString.h"
@@ -84,8 +85,60 @@ static void reportOverlappingBinding(Module &M, 
DXILResourceMap &DRM) {
   }
 }
 
+static void reportRegNotBound(Module &M, Twine Type,
+  ResourceInfo::ResourceBinding Binding) {
+  SmallString<128> Message;
+  raw_svector_ostream OS(Message);
+  OS << "register " << Type << " (space=" << Binding.Space
+ << ", register=" << Binding.LowerBound << ")"
+ << " is not defined in Root Signature";
+  M.getContext().diagnose(DiagnosticInfoGeneric(Message));
+}
+
+static dxbc::ShaderVisibility
+tripleToVisibility(llvm::Triple::EnvironmentType ET) {
+  assert((ET == Triple::Pixel || ET == Triple::Vertex ||
+  ET == Triple::Geometry || ET == Triple::Hull ||
+  ET == Triple::Domain || ET == Triple::Mesh ||
+  ET == Triple::Compute) &&
+   

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-clang

Author: None (joaosaffran)


Changes

DXC checks if registers are correctly bound to root signature descriptors. This 
implements the same check. 

Closes: [126645](https://github.com/llvm/llvm-project/issues/126645)

---
Full diff: https://github.com/llvm/llvm-project/pull/146785.diff


7 Files Affected:

- (added) clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl (+35) 
- (added) clang/test/SemaHLSL/RootSignature-Validation.hlsl (+33) 
- (modified) llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp 
(+133-3) 
- (modified) llvm/lib/Target/DirectX/DXILPostOptimizationValidation.h (+119) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-AllValidFlagCombinationsV1.ll
 (+2-2) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable.ll (+2-2) 
- (modified) llvm/test/CodeGen/DirectX/llc-pipeline.ll (+1) 


``diff
diff --git a/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl 
b/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl
new file mode 100644
index 0..b590ed67e7085
--- /dev/null
+++ b/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl
@@ -0,0 +1,35 @@
+// RUN: not %clang_dxc -T cs_6_6 -E CSMain %s 2>&1 | FileCheck %s
+
+// CHECK: error: register cbuffer (space=665, register=3) is not defined in 
Root Signature
+// CHECK: error: register srv (space=0, register=0) is not defined in Root 
Signature
+// CHECK: error: register uav (space=0, register=4294967295) is not defined in 
Root Signature
+
+
+#define ROOT_SIGNATURE \
+"CBV(b3, space=666, visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(SRV(t0, space=0, numDescriptors=1), 
visibility=SHADER_VISIBILITY_VERTEX), " \
+"DescriptorTable(Sampler(s0, numDescriptors=2), 
visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(UAV(u0, numDescriptors=unbounded), 
visibility=SHADER_VISIBILITY_ALL)"
+
+cbuffer CB : register(b3, space665) {
+  float a;
+}
+
+StructuredBuffer In : register(t0, space0);
+RWStructuredBuffer Out : register(u0);
+
+RWBuffer UAV : register(u4294967295);
+
+RWBuffer UAV1 : register(u2), UAV2 : register(u4);
+
+RWBuffer UAV3 : register(space0);
+
+
+
+// Compute Shader for UAV testing
+[numthreads(8, 8, 1)]
+[RootSignature(ROOT_SIGNATURE)]
+void CSMain(uint id : SV_GroupID)
+{
+Out[0] = a + id + In[0] + UAV[0] + UAV1[0] + UAV3[0];
+}
diff --git a/clang/test/SemaHLSL/RootSignature-Validation.hlsl 
b/clang/test/SemaHLSL/RootSignature-Validation.hlsl
new file mode 100644
index 0..5a7f5baf00619
--- /dev/null
+++ b/clang/test/SemaHLSL/RootSignature-Validation.hlsl
@@ -0,0 +1,33 @@
+// RUN: %clang_dxc -T cs_6_6 -E CSMain %s 2>&1 
+
+// expected-no-diagnostics
+
+
+#define ROOT_SIGNATURE \
+"CBV(b3, space=1, visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(SRV(t0, space=0, numDescriptors=1), 
visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(Sampler(s0, numDescriptors=2), 
visibility=SHADER_VISIBILITY_VERTEX), " \
+"DescriptorTable(UAV(u0, numDescriptors=unbounded), 
visibility=SHADER_VISIBILITY_ALL)"
+
+cbuffer CB : register(b3, space1) {
+  float a;
+}
+
+StructuredBuffer In : register(t0, space0);
+RWStructuredBuffer Out : register(u0);
+
+RWBuffer UAV : register(u4294967294);
+
+RWBuffer UAV1 : register(u2), UAV2 : register(u4);
+
+RWBuffer UAV3 : register(space0);
+
+
+
+// Compute Shader for UAV testing
+[numthreads(8, 8, 1)]
+[RootSignature(ROOT_SIGNATURE)]
+void CSMain(uint id : SV_GroupID)
+{
+Out[0] = a + id + In[0] + UAV[0] + UAV1[0] + UAV3[0];
+}
diff --git a/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp 
b/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
index 398dcbb8d1737..a52a04323514c 100644
--- a/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
+++ b/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
@@ -7,6 +7,7 @@
 
//===--===//
 
 #include "DXILPostOptimizationValidation.h"
+#include "DXILRootSignature.h"
 #include "DXILShaderFlags.h"
 #include "DirectX.h"
 #include "llvm/ADT/SmallString.h"
@@ -84,8 +85,60 @@ static void reportOverlappingBinding(Module &M, 
DXILResourceMap &DRM) {
   }
 }
 
+static void reportRegNotBound(Module &M, Twine Type,
+  ResourceInfo::ResourceBinding Binding) {
+  SmallString<128> Message;
+  raw_svector_ostream OS(Message);
+  OS << "register " << Type << " (space=" << Binding.Space
+ << ", register=" << Binding.LowerBound << ")"
+ << " is not defined in Root Signature";
+  M.getContext().diagnose(DiagnosticInfoGeneric(Message));
+}
+
+static dxbc::ShaderVisibility
+tripleToVisibility(llvm::Triple::EnvironmentType ET) {
+  assert((ET == Triple::Pixel || ET == Triple::Vertex ||
+  ET == Triple::Geometry || ET == Triple::Hull ||
+  ET == Triple::Domain || ET == Triple::Mesh ||
+  ET == Triple::Compute) &&
+  

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-backend-directx

Author: None (joaosaffran)


Changes

DXC checks if registers are correctly bound to root signature descriptors. This 
implements the same check. 

Closes: [126645](https://github.com/llvm/llvm-project/issues/126645)

---
Full diff: https://github.com/llvm/llvm-project/pull/146785.diff


7 Files Affected:

- (added) clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl (+35) 
- (added) clang/test/SemaHLSL/RootSignature-Validation.hlsl (+33) 
- (modified) llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp 
(+133-3) 
- (modified) llvm/lib/Target/DirectX/DXILPostOptimizationValidation.h (+119) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-AllValidFlagCombinationsV1.ll
 (+2-2) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable.ll (+2-2) 
- (modified) llvm/test/CodeGen/DirectX/llc-pipeline.ll (+1) 


``diff
diff --git a/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl 
b/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl
new file mode 100644
index 0..b590ed67e7085
--- /dev/null
+++ b/clang/test/SemaHLSL/RootSignature-Validation-Fail.hlsl
@@ -0,0 +1,35 @@
+// RUN: not %clang_dxc -T cs_6_6 -E CSMain %s 2>&1 | FileCheck %s
+
+// CHECK: error: register cbuffer (space=665, register=3) is not defined in 
Root Signature
+// CHECK: error: register srv (space=0, register=0) is not defined in Root 
Signature
+// CHECK: error: register uav (space=0, register=4294967295) is not defined in 
Root Signature
+
+
+#define ROOT_SIGNATURE \
+"CBV(b3, space=666, visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(SRV(t0, space=0, numDescriptors=1), 
visibility=SHADER_VISIBILITY_VERTEX), " \
+"DescriptorTable(Sampler(s0, numDescriptors=2), 
visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(UAV(u0, numDescriptors=unbounded), 
visibility=SHADER_VISIBILITY_ALL)"
+
+cbuffer CB : register(b3, space665) {
+  float a;
+}
+
+StructuredBuffer In : register(t0, space0);
+RWStructuredBuffer Out : register(u0);
+
+RWBuffer UAV : register(u4294967295);
+
+RWBuffer UAV1 : register(u2), UAV2 : register(u4);
+
+RWBuffer UAV3 : register(space0);
+
+
+
+// Compute Shader for UAV testing
+[numthreads(8, 8, 1)]
+[RootSignature(ROOT_SIGNATURE)]
+void CSMain(uint id : SV_GroupID)
+{
+Out[0] = a + id + In[0] + UAV[0] + UAV1[0] + UAV3[0];
+}
diff --git a/clang/test/SemaHLSL/RootSignature-Validation.hlsl 
b/clang/test/SemaHLSL/RootSignature-Validation.hlsl
new file mode 100644
index 0..5a7f5baf00619
--- /dev/null
+++ b/clang/test/SemaHLSL/RootSignature-Validation.hlsl
@@ -0,0 +1,33 @@
+// RUN: %clang_dxc -T cs_6_6 -E CSMain %s 2>&1 
+
+// expected-no-diagnostics
+
+
+#define ROOT_SIGNATURE \
+"CBV(b3, space=1, visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(SRV(t0, space=0, numDescriptors=1), 
visibility=SHADER_VISIBILITY_ALL), " \
+"DescriptorTable(Sampler(s0, numDescriptors=2), 
visibility=SHADER_VISIBILITY_VERTEX), " \
+"DescriptorTable(UAV(u0, numDescriptors=unbounded), 
visibility=SHADER_VISIBILITY_ALL)"
+
+cbuffer CB : register(b3, space1) {
+  float a;
+}
+
+StructuredBuffer In : register(t0, space0);
+RWStructuredBuffer Out : register(u0);
+
+RWBuffer UAV : register(u4294967294);
+
+RWBuffer UAV1 : register(u2), UAV2 : register(u4);
+
+RWBuffer UAV3 : register(space0);
+
+
+
+// Compute Shader for UAV testing
+[numthreads(8, 8, 1)]
+[RootSignature(ROOT_SIGNATURE)]
+void CSMain(uint id : SV_GroupID)
+{
+Out[0] = a + id + In[0] + UAV[0] + UAV1[0] + UAV3[0];
+}
diff --git a/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp 
b/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
index 398dcbb8d1737..a52a04323514c 100644
--- a/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
+++ b/llvm/lib/Target/DirectX/DXILPostOptimizationValidation.cpp
@@ -7,6 +7,7 @@
 
//===--===//
 
 #include "DXILPostOptimizationValidation.h"
+#include "DXILRootSignature.h"
 #include "DXILShaderFlags.h"
 #include "DirectX.h"
 #include "llvm/ADT/SmallString.h"
@@ -84,8 +85,60 @@ static void reportOverlappingBinding(Module &M, 
DXILResourceMap &DRM) {
   }
 }
 
+static void reportRegNotBound(Module &M, Twine Type,
+  ResourceInfo::ResourceBinding Binding) {
+  SmallString<128> Message;
+  raw_svector_ostream OS(Message);
+  OS << "register " << Type << " (space=" << Binding.Space
+ << ", register=" << Binding.LowerBound << ")"
+ << " is not defined in Root Signature";
+  M.getContext().diagnose(DiagnosticInfoGeneric(Message));
+}
+
+static dxbc::ShaderVisibility
+tripleToVisibility(llvm::Triple::EnvironmentType ET) {
+  assert((ET == Triple::Pixel || ET == Triple::Vertex ||
+  ET == Triple::Geometry || ET == Triple::Hull ||
+  ET == Triple::Domain || ET == Triple::Mesh ||
+  ET == Triple::Compu

[llvm-branch-commits] [clang] [llvm] [DirectX] Validate registers are bound to root signature (PR #146785)

2025-07-04 Thread via llvm-branch-commits

https://github.com/joaosaffran ready_for_review 
https://github.com/llvm/llvm-project/pull/146785
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [DirectX] Add missing verifications during `validate` of `DXILRootSignature` (PR #147111)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic created 
https://github.com/llvm/llvm-project/pull/147111

This pr resolves some discrepancies in verification during `validate` in 
`DXILRootSignature.cpp`.

Namely,
- `verifyDescriptorFlag` should be updated to check what flags are valid based 
on the root signature version, as reflected here 
https://github.com/llvm/wg-hlsl/pull/297.
- There is currently no verification that `numDescriptors > 0` which should be 
added to be compliant with DXC:  
https://github.com/microsoft/DirectXShaderCompiler/blob/4fcf67f78f7d6ffd286316112694a3ae000860e2/lib/DxilRootSignature/DxilRootSignatureValidator.cpp#L197.

- Updates `verifyDescriptorFlag` to check for valid flags based on version
- Add test to demonstrate updated flag verifications
- Adds `verifyNumDescriptors` to the validation of `DescriptorRange`s
- Add a test to demonstrate `numDescriptors` verification
- Updates a number of tests that mistakenly had an invalid `numDescriptors` 
specified

Resolves: https://github.com/llvm/llvm-project/issues/147107

>From ab274d239bd12e39fc91d7cc2fc7e899be274e55 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 4 Jul 2025 20:54:50 +
Subject: [PATCH 1/3] [HLSL][DirectX] Add `verifyNumDescriptors`

---
 .../Frontend/HLSL/RootSignatureValidations.h  |  1 +
 .../HLSL/RootSignatureValidations.cpp |  4 
 llvm/lib/Target/DirectX/DXILRootSignature.cpp |  3 +++
 ...-DescriptorTable-Invalid-NumDescriptors.ll | 19 +++
 4 files changed, 27 insertions(+)
 create mode 100644 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll

diff --git a/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h 
b/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
index 9b68a524432cc..bcef20530559d 100644
--- a/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
+++ b/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
@@ -31,6 +31,7 @@ bool verifyDescriptorFlag(uint32_t Flags);
 bool verifyRangeType(uint32_t Type);
 bool verifyDescriptorRangeFlag(uint32_t Version, uint32_t Type,
uint32_t FlagsVal);
+bool verifyNumDescriptors(uint32_t NumDescriptors);
 bool verifySamplerFilter(uint32_t Value);
 bool verifyAddress(uint32_t Address);
 bool verifyMipLODBias(float MipLODBias);
diff --git a/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp 
b/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
index b5b5fc0c74d83..6c238e0f04468 100644
--- a/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
+++ b/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
@@ -108,6 +108,10 @@ bool verifyDescriptorRangeFlag(uint32_t Version, uint32_t 
Type,
   return (Flags & ~Mask) == FlagT::None;
 }
 
+bool verifyNumDescriptors(uint32_t NumDescriptors) {
+  return NumDescriptors > 0;
+}
+
 bool verifySamplerFilter(uint32_t Value) {
   switch (Value) {
 #define FILTER(Num, Val) case llvm::to_underlying(dxbc::SamplerFilter::Val):
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.cpp 
b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
index e46b184a353f1..edad63bfe7ea7 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.cpp
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
@@ -447,6 +447,9 @@ static bool validate(LLVMContext *Ctx, const 
mcdxbc::RootSignatureDesc &RSD) {
 if (!llvm::hlsl::rootsig::verifyRegisterSpace(Range.RegisterSpace))
   return reportValueError(Ctx, "RegisterSpace", Range.RegisterSpace);
 
+if (!llvm::hlsl::rootsig::verifyNumDescriptors(Range.NumDescriptors))
+  return reportValueError(Ctx, "NumDescriptors", Range.NumDescriptors);
+
 if (!llvm::hlsl::rootsig::verifyDescriptorRangeFlag(
 RSD.Version, Range.RangeType, Range.Flags))
   return reportValueError(Ctx, "DescriptorFlag", Range.Flags);
diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll
new file mode 100644
index 0..99d126ee95443
--- /dev/null
+++ 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll
@@ -0,0 +1,19 @@
+; RUN: not opt -passes='print' %s -S -o - 2>&1 | 
FileCheck %s
+
+target triple = "dxil-unknown-shadermodel6.0-compute"
+
+; CHECK: error: Invalid value for NumDescriptors: 0
+; CHECK-NOT: Root Signature Definitions
+
+define void @main() #0 {
+entry:
+  ret void
+}
+attributes #0 = { "hlsl.numthreads"="1,1,1" "hlsl.shader"="compute" }
+
+
+!dx.rootsignatures = !{!2} ; list of function/root signature pairs
+!2 = !{ ptr @main, !3, i32 2 } ; function, root signature
+!3 = !{ !5 } ; list of root signature elements
+!5 = !{ !"DescriptorTable", i32 0, !6}
+!6 = !{ !"SRV", i32 0, i32 0, i32 10, i32 -1, i32 4 }

>From 56ae9d9316fd02b588ba67ddf1820c9bd80bae49 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 4 Jul 2025 20:59:09 +
Subject: [PA

[llvm-branch-commits] [llvm] [DirectX] Add missing verifications during `validate` of `DXILRootSignature` (PR #147111)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-backend-directx

Author: Finn Plummer (inbelic)


Changes

This pr resolves some discrepancies in verification during `validate` in 
`DXILRootSignature.cpp`.

Namely,
- `verifyDescriptorFlag` should be updated to check what flags are valid based 
on the root signature version, as reflected here 
https://github.com/llvm/wg-hlsl/pull/297.
- There is currently no verification that `numDescriptors > 0` which should 
be added to be compliant with DXC:  
https://github.com/microsoft/DirectXShaderCompiler/blob/4fcf67f78f7d6ffd286316112694a3ae000860e2/lib/DxilRootSignature/DxilRootSignatureValidator.cpp#L197.

- Updates `verifyDescriptorFlag` to check for valid flags based on version
- Add test to demonstrate updated flag verifications
- Adds `verifyNumDescriptors` to the validation of `DescriptorRange`s
- Add a test to demonstrate `numDescriptors` verification
- Updates a number of tests that mistakenly had an invalid `numDescriptors` 
specified

Resolves: https://github.com/llvm/llvm-project/issues/147107

---
Full diff: https://github.com/llvm/llvm-project/pull/147111.diff


10 Files Affected:

- (modified) llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h (+2-1) 
- (modified) llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp (+22-1) 
- (modified) llvm/lib/Target/DirectX/DXILRootSignature.cpp (+5-1) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-AllValidFlagCombinationsV1.ll
 (+2-2) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-Flag.ll
 (+1-1) 
- (added) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll
 (+19) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-RangeType.ll
 (+1-1) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-RegisterSpace.ll
 (+1-1) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable.ll (+2-2) 
- (modified) 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-Parameters.ll (+2-2) 


``diff
diff --git a/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h 
b/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
index 9b68a524432cc..03f4e2cf5bb8f 100644
--- a/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
+++ b/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
@@ -27,10 +27,11 @@ bool verifyRootFlag(uint32_t Flags);
 bool verifyVersion(uint32_t Version);
 bool verifyRegisterValue(uint32_t RegisterValue);
 bool verifyRegisterSpace(uint32_t RegisterSpace);
-bool verifyDescriptorFlag(uint32_t Flags);
+bool verifyRootDescriptorFlag(uint32_t Version, uint32_t FlagsVal);
 bool verifyRangeType(uint32_t Type);
 bool verifyDescriptorRangeFlag(uint32_t Version, uint32_t Type,
uint32_t FlagsVal);
+bool verifyNumDescriptors(uint32_t NumDescriptors);
 bool verifySamplerFilter(uint32_t Value);
 bool verifyAddress(uint32_t Address);
 bool verifyMipLODBias(float MipLODBias);
diff --git a/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp 
b/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
index b5b5fc0c74d83..48d6b8639b2dc 100644
--- a/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
+++ b/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
@@ -32,7 +32,24 @@ bool verifyRegisterSpace(uint32_t RegisterSpace) {
   return !(RegisterSpace >= 0xFFF0 && RegisterSpace <= 0x);
 }
 
-bool verifyDescriptorFlag(uint32_t Flags) { return (Flags & ~0xE) == 0; }
+bool verifyRootDescriptorFlag(uint32_t Version, uint32_t FlagsVal) {
+  using FlagT = dxbc::RootDescriptorFlags;
+  FlagT Flags = FlagT(FlagsVal);
+  if (Version == 1)
+return FlagsVal == FlagT::DataVolatile;
+
+  assert(Version == 2 && "Provided invalid root signature version");
+
+  // The data-specific flags are mutually exclusive.
+  FlagT DataFlags = FlagT::DataVolatile | FlagT::DataStatic |
+FlagT::DataStaticWhileSetAtExecute;
+
+  if (popcount(llvm::to_underlying(Flags & DataFlags)) > 1)
+return false;
+
+  // Only a data flag or no flags is valid
+  return (FlagsVal & ~0xE) == 0;
+}
 
 bool verifyRangeType(uint32_t Type) {
   switch (Type) {
@@ -108,6 +125,10 @@ bool verifyDescriptorRangeFlag(uint32_t Version, uint32_t 
Type,
   return (Flags & ~Mask) == FlagT::None;
 }
 
+bool verifyNumDescriptors(uint32_t NumDescriptors) {
+  return NumDescriptors > 0;
+}
+
 bool verifySamplerFilter(uint32_t Value) {
   switch (Value) {
 #define FILTER(Num, Val) case llvm::to_underlying(dxbc::SamplerFilter::Val):
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.cpp 
b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
index e46b184a353f1..37a60075514ef 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.cpp
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
@@ -432,7 +432,8 @@ static bool validate(LLVMContext *Ctx, const 
mcdxbc::RootSignatureDesc &R

[llvm-branch-commits] [llvm] [DirectX] Add missing verifications during `validate` of `DXILRootSignature` (PR #147111)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic updated 
https://github.com/llvm/llvm-project/pull/147111

>From ab274d239bd12e39fc91d7cc2fc7e899be274e55 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 4 Jul 2025 20:54:50 +
Subject: [PATCH 1/6] [HLSL][DirectX] Add `verifyNumDescriptors`

---
 .../Frontend/HLSL/RootSignatureValidations.h  |  1 +
 .../HLSL/RootSignatureValidations.cpp |  4 
 llvm/lib/Target/DirectX/DXILRootSignature.cpp |  3 +++
 ...-DescriptorTable-Invalid-NumDescriptors.ll | 19 +++
 4 files changed, 27 insertions(+)
 create mode 100644 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll

diff --git a/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h 
b/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
index 9b68a524432cc..bcef20530559d 100644
--- a/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
+++ b/llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h
@@ -31,6 +31,7 @@ bool verifyDescriptorFlag(uint32_t Flags);
 bool verifyRangeType(uint32_t Type);
 bool verifyDescriptorRangeFlag(uint32_t Version, uint32_t Type,
uint32_t FlagsVal);
+bool verifyNumDescriptors(uint32_t NumDescriptors);
 bool verifySamplerFilter(uint32_t Value);
 bool verifyAddress(uint32_t Address);
 bool verifyMipLODBias(float MipLODBias);
diff --git a/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp 
b/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
index b5b5fc0c74d83..6c238e0f04468 100644
--- a/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
+++ b/llvm/lib/Frontend/HLSL/RootSignatureValidations.cpp
@@ -108,6 +108,10 @@ bool verifyDescriptorRangeFlag(uint32_t Version, uint32_t 
Type,
   return (Flags & ~Mask) == FlagT::None;
 }
 
+bool verifyNumDescriptors(uint32_t NumDescriptors) {
+  return NumDescriptors > 0;
+}
+
 bool verifySamplerFilter(uint32_t Value) {
   switch (Value) {
 #define FILTER(Num, Val) case llvm::to_underlying(dxbc::SamplerFilter::Val):
diff --git a/llvm/lib/Target/DirectX/DXILRootSignature.cpp 
b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
index e46b184a353f1..edad63bfe7ea7 100644
--- a/llvm/lib/Target/DirectX/DXILRootSignature.cpp
+++ b/llvm/lib/Target/DirectX/DXILRootSignature.cpp
@@ -447,6 +447,9 @@ static bool validate(LLVMContext *Ctx, const 
mcdxbc::RootSignatureDesc &RSD) {
 if (!llvm::hlsl::rootsig::verifyRegisterSpace(Range.RegisterSpace))
   return reportValueError(Ctx, "RegisterSpace", Range.RegisterSpace);
 
+if (!llvm::hlsl::rootsig::verifyNumDescriptors(Range.NumDescriptors))
+  return reportValueError(Ctx, "NumDescriptors", Range.NumDescriptors);
+
 if (!llvm::hlsl::rootsig::verifyDescriptorRangeFlag(
 RSD.Version, Range.RangeType, Range.Flags))
   return reportValueError(Ctx, "DescriptorFlag", Range.Flags);
diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll
new file mode 100644
index 0..99d126ee95443
--- /dev/null
+++ 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-Invalid-NumDescriptors.ll
@@ -0,0 +1,19 @@
+; RUN: not opt -passes='print' %s -S -o - 2>&1 | 
FileCheck %s
+
+target triple = "dxil-unknown-shadermodel6.0-compute"
+
+; CHECK: error: Invalid value for NumDescriptors: 0
+; CHECK-NOT: Root Signature Definitions
+
+define void @main() #0 {
+entry:
+  ret void
+}
+attributes #0 = { "hlsl.numthreads"="1,1,1" "hlsl.shader"="compute" }
+
+
+!dx.rootsignatures = !{!2} ; list of function/root signature pairs
+!2 = !{ ptr @main, !3, i32 2 } ; function, root signature
+!3 = !{ !5 } ; list of root signature elements
+!5 = !{ !"DescriptorTable", i32 0, !6}
+!6 = !{ !"SRV", i32 0, i32 0, i32 10, i32 -1, i32 4 }

>From 56ae9d9316fd02b588ba67ddf1820c9bd80bae49 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Fri, 4 Jul 2025 20:59:09 +
Subject: [PATCH 2/6] fix up testcases using invalid num descriptors

---
 ...ootSignature-DescriptorTable-AllValidFlagCombinationsV1.ll | 4 ++--
 .../RootSignature-DescriptorTable-Invalid-Flag.ll | 2 +-
 .../RootSignature-DescriptorTable-Invalid-RangeType.ll| 2 +-
 .../RootSignature-DescriptorTable-Invalid-RegisterSpace.ll| 2 +-
 .../DirectX/ContainerData/RootSignature-DescriptorTable.ll| 4 ++--
 .../CodeGen/DirectX/ContainerData/RootSignature-Parameters.ll | 4 ++--
 6 files changed, 9 insertions(+), 9 deletions(-)

diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-AllValidFlagCombinationsV1.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-AllValidFlagCombinationsV1.ll
index 9d89dbdd9107b..053721de1eb1f 100644
--- 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-DescriptorTable-AllValidFlagCombinationsV1.ll
+++ 
b/llvm/test/CodeGen/DirectX/ContainerData/RootS

[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits


@@ -744,8 +758,7 @@ static DiagnosedSilenceableFailure
 getThreadIdBuilder(std::optional transformOp,
scf::ForallOp forallOp, ArrayRef blockSizes,
int64_t warpSize, GpuIdBuilder &gpuIdBuilder) {
-  auto mappingAttr = cast(
-  forallOp.getMapping()->getValue().front());
+  auto mappingAttr = forallOp.getDeviceMappingAttrs().front();

ftynse wrote:

Nit: now that there's no more cast on the RHS, please expand `auto`.

https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits


@@ -78,7 +78,8 @@ struct GpuIdBuilder {
 /// If `useLinearMapping` is true, the `idBuilder` method returns nD values
 /// used for indexing rewrites as well as 1D sizes for predicate generation.
 struct GpuBlockIdBuilder : public GpuIdBuilder {
-  GpuBlockIdBuilder(MLIRContext *ctx, bool useLinearMapping = false);

ftynse wrote:

Could you please the comments above to reflect this new argument? Here and 
below.

https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits


@@ -60,8 +60,51 @@ def DeviceMappingAttrInterface : 
AttrInterface<"DeviceMappingAttrInterface"> {
   ];
 }
 
+def DeviceMaskingAttrInterface : AttrInterface<"DeviceMaskingAttrInterface"> {
+  let cppNamespace = "::mlir";
+  let description = [{
+Attribute interface describing how to filter the processing units that a
+region is mapped to.
+
+A popcount can be applied to determine the logical linear index that a
+physical processing unit is responsible for.
+  }];
+
+ let methods = [
+InterfaceMethod<
+  /*desc=*/[{
+Return the logical active id for a given physical id.
+Expects a physicalLinearMappingId of I64Type.
+  }],
+  /*retTy=*/"Value",
+  /*methodName=*/"getLogicalLinearMappingId",
+  /*args=*/(ins "OpBuilder&":$builder, "Value":$physicalLinearMappingId)
+>,
+InterfaceMethod<
+  /*desc=*/[{
+Return the dynamic condition determining whether a given physical id is
+active under the mask.
+Expects a physicalLinearMappingId of I64Type.
+  }],
+  /*retTy=*/"Value",
+  /*methodName=*/"getIsActiveIdPredicate",
+  /*args=*/(ins "OpBuilder&":$builder, "Value":$physicalLinearMappingId)
+>,
+InterfaceMethod<
+  /*desc=*/[{
+Return the maximal number of pysical ids supported.

ftynse wrote:

```suggestion
Return the maximal number of physical ids supported.
```

https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits


@@ -60,8 +60,51 @@ def DeviceMappingAttrInterface : 
AttrInterface<"DeviceMappingAttrInterface"> {
   ];
 }
 
+def DeviceMaskingAttrInterface : AttrInterface<"DeviceMaskingAttrInterface"> {
+  let cppNamespace = "::mlir";
+  let description = [{
+Attribute interface describing how to filter the processing units that a
+region is mapped to.
+
+A popcount can be applied to determine the logical linear index that a
+physical processing unit is responsible for.
+  }];
+
+ let methods = [
+InterfaceMethod<
+  /*desc=*/[{
+Return the logical active id for a given physical id.
+Expects a physicalLinearMappingId of I64Type.
+  }],
+  /*retTy=*/"Value",
+  /*methodName=*/"getLogicalLinearMappingId",

ftynse wrote:

Optional naming nit: `bulidFoo` or `createFoo` instead of `getFoo` will make it 
clearer that some IR is being constructed.

https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits


@@ -60,8 +60,51 @@ def DeviceMappingAttrInterface : 
AttrInterface<"DeviceMappingAttrInterface"> {
   ];
 }
 
+def DeviceMaskingAttrInterface : AttrInterface<"DeviceMaskingAttrInterface"> {
+  let cppNamespace = "::mlir";
+  let description = [{
+Attribute interface describing how to filter the processing units that a
+region is mapped to.
+
+A popcount can be applied to determine the logical linear index that a
+physical processing unit is responsible for.
+  }];

ftynse wrote:

Could you please document what is understood by physical and logical ID here 
and how either of those can be linear.

https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits

https://github.com/ftynse edited 
https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits

https://github.com/ftynse approved this pull request.

Please address comments, okay otherwise

https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits


@@ -252,6 +252,24 @@ def GPULaneMappingAttr
   }];
 }
 
+def GPUMappingMaskAttr : GPU_Attr<"GPUMappingMask", "mask", [
+  DeclareAttrInterfaceMethods ] >  {
+  let parameters = (ins "uint64_t":$mask);
+  let assemblyFormat = "`<` params `>`";
+  let description = [{
+Attribute describing how to filter the processing units that a
+region is mapped to.
+
+In the first implementation the masking is a bitfield that specifies for
+each processing unit whether it is active or not.
+
+In the future, we may want to implement this as a symbol to refer to
+dynamically defined values.
+
+Extending op semantics with an operand is deemed too intrusive at this 
time.

ftynse wrote:

I think this rather belongs to code documentation or some rationale document, 
or even a commit message, not user-facing documentation.

https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][SCF][GPU] Add DeviceMaskingAttrInterface support to scf::Foral… (PR #146943)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits


@@ -60,8 +60,51 @@ def DeviceMappingAttrInterface : 
AttrInterface<"DeviceMappingAttrInterface"> {
   ];
 }
 
+def DeviceMaskingAttrInterface : AttrInterface<"DeviceMaskingAttrInterface"> {
+  let cppNamespace = "::mlir";
+  let description = [{
+Attribute interface describing how to filter the processing units that a
+region is mapped to.
+
+A popcount can be applied to determine the logical linear index that a
+physical processing unit is responsible for.

ftynse wrote:

I'm not sure this part of the documentation is understandable by itself. It 
seems to imply that the attribute is systematically a bitfield, and I'm not 
sure I fully understand how a popcount is always needed to get a logical linear 
index.

https://github.com/llvm/llvm-project/pull/146943
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [mlir] [mlir][GPU][transform] Add gpu_to_rocdl conversion pattern to transfo… (PR #146962)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits


@@ -129,6 +131,42 @@ LogicalResult 
transform::ApplyGPUSubgroupReduceToNVVMConversionPatternsOp::
   return success();
 }
 
+void transform::ApplyGPUToROCDLConversionPatternsOp::populatePatterns(
+TypeConverter &typeConverter, RewritePatternSet &patterns) {
+  auto &llvmTypeConverter = static_cast(typeConverter);
+  populateGpuMemorySpaceAttributeConversions(
+  llvmTypeConverter, [](AddressSpace space) {
+switch (space) {
+case AddressSpace::Global:
+  return 1;
+case AddressSpace::Workgroup:
+  return 3;
+case AddressSpace::Private:
+  return 5;

ftynse wrote:

Are you sure these address spaces are correct for ROCDL?

https://github.com/llvm/llvm-project/pull/146962
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [mlir] [mlir][GPU][transform] Add gpu_to_rocdl conversion pattern to transfo… (PR #146962)

2025-07-04 Thread Oleksandr Alex Zinenko via llvm-branch-commits

https://github.com/ftynse approved this pull request.

Sounds good assuming the address space indices are correct.

https://github.com/llvm/llvm-project/pull/146962
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147094)

2025-07-04 Thread Finn Plummer via llvm-branch-commits


@@ -1064,21 +1064,25 @@ SemaHLSL::ActOnStartRootSignatureDecl(StringRef 
Signature) {
 
 void SemaHLSL::ActOnFinishRootSignatureDecl(
 SourceLocation Loc, IdentifierInfo *DeclIdent,
-SmallVector &Elements) {
+ArrayRef RootElements) {
+
+  if (handleRootSignatureElements(RootElements, Loc))
+return;
+
+  SmallVector Elements;
+  for (auto &RootSigElement : RootElements)
+Elements.push_back(RootSigElement.getElement());
 
   auto *SignatureDecl = HLSLRootSignatureDecl::Create(
   SemaRef.getASTContext(), /*DeclContext=*/SemaRef.CurContext, Loc,
   DeclIdent, SemaRef.getLangOpts().HLSLRootSigVer, Elements);
 
-  if (handleRootSignatureDecl(SignatureDecl, Loc))
-return;
-
   SignatureDecl->setImplicit();
   SemaRef.PushOnScopeChains(SignatureDecl, SemaRef.getCurScope());
 }
 
-bool SemaHLSL::handleRootSignatureDecl(HLSLRootSignatureDecl *D,
-   SourceLocation Loc) {
+bool SemaHLSL::handleRootSignatureElements(
+ArrayRef Elements, SourceLocation Loc) {

inbelic wrote:

```suggestion
ArrayRef Elements) {
```
We no longer are required to use `Loc`

https://github.com/llvm/llvm-project/pull/147094
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147094)

2025-07-04 Thread Finn Plummer via llvm-branch-commits


@@ -1103,9 +1107,15 @@ bool 
SemaHLSL::handleRootSignatureDecl(HLSLRootSignatureDecl *D,
   using ResourceRange = llvm::hlsl::rootsig::ResourceRange;
   using GroupT = std::pair;
 
+  // Introduce a mapping from the collected RangeInfos back to the
+  // RootSignatureElement that will retain its diagnostics info
+  llvm::DenseMap InfoIndexMap;

inbelic wrote:

```suggestion
  llvm::SmallDenseMap InfoIndexMap;
```

https://github.com/llvm/llvm-project/pull/147094
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147094)

2025-07-04 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic ready_for_review 
https://github.com/llvm/llvm-project/pull/147094
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL][RootSignature] Retain `SourceLocation` of `RootElement` for `SemaHLSL` diagnostics (PR #147094)

2025-07-04 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-hlsl

Author: Finn Plummer (inbelic)


Changes

At the moment, when we report diagnostics from `SemaHLSL` we only provide the 
source location of the root signature attr. This allows for significantly less 
helpful diagnostics (for eg. reporting resource range overlaps).

This pr implements a way to retain the source location of a root element when 
it is parsed, so that we can output the `SourceLocation` of each root element 
that causes the overlap in the diagnostics during semantic analysis.

This pr defines a wrapper struct `clang::hlsl::RootSignatureElement` in 
`SemaHLSL` that will contain the underlying `RootElement` and can hold any 
additional diagnostic information. This struct will be what is used in 
`HLSLRootSignatureParser` and in `SemaHLSL`. Then the diagnostic information 
will be stripped and the underlying element will be stored in the 
`RootSignatureDecl`.

For the reporting of diagnostics, we can now use the retained `SourceLocation` 
of each `RootElement` when reporting the range overlap, and we can add a `note` 
diagnostic to highlight the other root element as well.

- Defines `RootSignatureElement` in the `hlsl` namespace in `SemaHLSL` (defined 
in `SemaHLSL` because `Parse` has a dependency on `Sema`)
- Updates parsing logic to construct `RootSignatureElement`s and retain the 
source loction in `ParseHLSLRootSignature`
- Updates `SemaHLSL` when it constructs the `RootSignatureDecl` to take the new 
`RootSignatureElement` and store the underlying `RootElement`
- Updates the current tests to ensure the new `note` diagnostic is produced and 
that the `SourceLocation` is seen
- Adds a test to demonstrate the `SourceLocation` of both elements being 
correctly pointed out

Resolves: https://github.com/llvm/llvm-project/issues/145819

---

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


9 Files Affected:

- (modified) clang/include/clang/Basic/DiagnosticSemaKinds.td (+1) 
- (modified) clang/include/clang/Parse/ParseHLSLRootSignature.h (+4-2) 
- (modified) clang/include/clang/Sema/SemaHLSL.h (+25-4) 
- (modified) clang/lib/Parse/ParseDeclCXX.cpp (+1-1) 
- (modified) clang/lib/Parse/ParseHLSLRootSignature.cpp (+19-8) 
- (modified) clang/lib/Sema/SemaHLSL.cpp (+38-10) 
- (modified) clang/test/SemaHLSL/RootSignature-resource-ranges-err.hlsl (+41) 
- (modified) clang/unittests/Parse/ParseHLSLRootSignatureTest.cpp (+74-73) 
- (modified) llvm/include/llvm/Frontend/HLSL/RootSignatureValidations.h (+3) 


``diff
diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td 
b/clang/include/clang/Basic/DiagnosticSemaKinds.td
index 968edd967e0c5..4fe0abb972a61 100644
--- a/clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -13079,6 +13079,7 @@ def err_hlsl_resource_range_overlap: Error<
   "resource ranges %sub{subst_hlsl_format_ranges}0,1,2,3 and 
%sub{subst_hlsl_format_ranges}4,5,6,7 "
   "overlap within space = %8 and visibility = "
   "%select{All|Vertex|Hull|Domain|Geometry|Pixel|Amplification|Mesh}9">;
+def note_hlsl_resource_range_here: Note<"overlapping resource range here">;
 
 // Layout randomization diagnostics.
 def err_non_designated_init_used : Error<
diff --git a/clang/include/clang/Parse/ParseHLSLRootSignature.h 
b/clang/include/clang/Parse/ParseHLSLRootSignature.h
index b0ef617a13c28..9ef5b64d7b4a5 100644
--- a/clang/include/clang/Parse/ParseHLSLRootSignature.h
+++ b/clang/include/clang/Parse/ParseHLSLRootSignature.h
@@ -17,6 +17,7 @@
 #include "clang/Basic/DiagnosticParse.h"
 #include "clang/Lex/LexHLSLRootSignature.h"
 #include "clang/Lex/Preprocessor.h"
+#include "clang/Sema/SemaHLSL.h"
 
 #include "llvm/ADT/SmallVector.h"
 #include "llvm/ADT/StringRef.h"
@@ -29,7 +30,7 @@ namespace hlsl {
 class RootSignatureParser {
 public:
   RootSignatureParser(llvm::dxbc::RootSignatureVersion Version,
-  SmallVector &Elements,
+  SmallVector &Elements,
   StringLiteral *Signature, Preprocessor &PP);
 
   /// Consumes tokens from the Lexer and constructs the in-memory
@@ -196,7 +197,8 @@ class RootSignatureParser {
 
 private:
   llvm::dxbc::RootSignatureVersion Version;
-  SmallVector &Elements;
+  SmallVector &Elements;
+
   clang::StringLiteral *Signature;
   RootSignatureLexer Lexer;
   clang::Preprocessor &PP;
diff --git a/clang/include/clang/Sema/SemaHLSL.h 
b/clang/include/clang/Sema/SemaHLSL.h
index 7d7eae4db532c..910e0e640796b 100644
--- a/clang/include/clang/Sema/SemaHLSL.h
+++ b/clang/include/clang/Sema/SemaHLSL.h
@@ -32,6 +32,25 @@ class ParsedAttr;
 class Scope;
 class VarDecl;
 
+namespace hlsl {
+
+// Introduce a wrapper struct around the underlying RootElement. This structure
+// will retain extra clang diagnostic information that is not available in 
llvm.
+struct RootSignatureElement {
+  RootSignatureElement(SourceLocation Loc,
+  

[llvm-branch-commits] [llvm] [DirectX] Improve error handling and validation in root signature parsing (PR #144577)

2025-07-04 Thread Deric C. via llvm-branch-commits

https://github.com/Icohedron approved this pull request.


https://github.com/llvm/llvm-project/pull/144577
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [DirectX] Improve error accumulation in root signature parsing (PR #144465)

2025-07-04 Thread Deric C. via llvm-branch-commits

https://github.com/Icohedron approved this pull request.

Looks fine to me

https://github.com/llvm/llvm-project/pull/144465
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [NFC][HLSL] Move resource range logic from `SemaHLSL` to `RootSignatureValidations` (PR #147117)

2025-07-04 Thread Deric C. via llvm-branch-commits

https://github.com/Icohedron approved this pull request.


https://github.com/llvm/llvm-project/pull/147117
___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits